db_input.c revision 623
1238106Sdes/*
2238106Sdes * Mach Operating System
3238106Sdes * Copyright (c) 1991,1990 Carnegie Mellon University
4238106Sdes * All Rights Reserved.
5238106Sdes *
6238106Sdes * Permission to use, copy, modify and distribute this software and its
7238106Sdes * documentation is hereby granted, provided that both the copyright
8238106Sdes * notice and this permission notice appear in all copies of the
9238106Sdes * software, derivative works or modified versions, and any portions
10238106Sdes * thereof, and that both notices appear in supporting documentation.
11238106Sdes *
12238106Sdes * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
13238106Sdes * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
14238106Sdes * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
15238106Sdes *
16238106Sdes * Carnegie Mellon requests users of this software to return to
17238106Sdes *
18238106Sdes *  Software Distribution Coordinator  or  Software.Distribution@CS.CMU.EDU
19238106Sdes *  School of Computer Science
20238106Sdes *  Carnegie Mellon University
21238106Sdes *  Pittsburgh PA 15213-3890
22238106Sdes *
23238106Sdes * any improvements or extensions that they make and grant Carnegie the
24266114Sdes * rights to redistribute these changes.
25266114Sdes *
26266114Sdes *	$Id$
27266114Sdes */
28266114Sdes
29266114Sdes/*
30266114Sdes *	Author: David B. Golub, Carnegie Mellon University
31266114Sdes *	Date:	7/90
32266114Sdes */
33266114Sdes
34238106Sdes#include "param.h"
35238106Sdes#include "proc.h"
36238106Sdes#include <ddb/db_output.h>
37238106Sdes
38238106Sdes/*
39238106Sdes * Character input and editing.
40238106Sdes */
41238106Sdes
42238106Sdes/*
43238106Sdes * We don't track output position while editing input,
44255579Sdes * since input always ends with a new-line.  We just
45255579Sdes * reset the line position at the end.
46238106Sdes */
47238106Sdeschar *	db_lbuf_start;	/* start of input line buffer */
48238106Sdeschar *	db_lbuf_end;	/* end of input line buffer */
49238106Sdeschar *	db_lc;		/* current character */
50238106Sdeschar *	db_le;		/* one past last character */
51238106Sdes
52238106Sdes#define	CTRL(c)		((c) & 0x1f)
53238106Sdes#define	isspace(c)	((c) == ' ' || (c) == '\t')
54238106Sdes#define	BLANK		' '
55238106Sdes#define	BACKUP		'\b'
56238106Sdes
57238106Sdesvoid
58238106Sdesdb_putstring(s, count)
59238106Sdes	char	*s;
60266114Sdes	int	count;
61266114Sdes{
62238106Sdes	while (--count >= 0)
63238106Sdes	    cnputc(*s++);
64238106Sdes}
65238106Sdes
66238106Sdesvoid
67238106Sdesdb_putnchars(c, count)
68238106Sdes	int	c;
69238106Sdes	int	count;
70238106Sdes{
71238106Sdes	while (--count >= 0)
72238106Sdes	    cnputc(c);
73238106Sdes}
74238106Sdes
75238106Sdes/*
76238106Sdes * Delete N characters, forward or backward
77238106Sdes */
78238106Sdes#define	DEL_FWD		0
79238106Sdes#define	DEL_BWD		1
80238106Sdesvoid
81238106Sdesdb_delete(n, bwd)
82238106Sdes	int	n;
83238106Sdes	int	bwd;
84238106Sdes{
85238106Sdes	register char *p;
86238106Sdes
87238106Sdes	if (bwd) {
88238106Sdes	    db_lc -= n;
89238106Sdes	    db_putnchars(BACKUP, n);
90238106Sdes	}
91238106Sdes	for (p = db_lc; p < db_le-n; p++) {
92238106Sdes	    *p = *(p+n);
93238106Sdes	    cnputc(*p);
94238106Sdes	}
95238106Sdes	db_putnchars(BLANK, n);
96238106Sdes	db_putnchars(BACKUP, db_le - db_lc);
97238106Sdes	db_le -= n;
98238106Sdes}
99238106Sdes
100238106Sdes/* returns TRUE at end-of-line */
101238106Sdesint
102238106Sdesdb_inputchar(c)
103238106Sdes	int	c;
104238106Sdes{
105238106Sdes	switch (c) {
106238106Sdes	    case CTRL('b'):
107238106Sdes		/* back up one character */
108238106Sdes		if (db_lc > db_lbuf_start) {
109238106Sdes		    cnputc(BACKUP);
110238106Sdes		    db_lc--;
111266114Sdes		}
112266114Sdes		break;
113266114Sdes	    case CTRL('f'):
114266114Sdes		/* forward one character */
115266114Sdes		if (db_lc < db_le) {
116266114Sdes		    cnputc(*db_lc);
117266114Sdes		    db_lc++;
118266114Sdes		}
119266114Sdes		break;
120266114Sdes	    case CTRL('a'):
121266114Sdes		/* beginning of line */
122266114Sdes		while (db_lc > db_lbuf_start) {
123266114Sdes		    cnputc(BACKUP);
124266114Sdes		    db_lc--;
125266114Sdes		}
126266114Sdes		break;
127266114Sdes	    case CTRL('e'):
128266114Sdes		/* end of line */
129266114Sdes		while (db_lc < db_le) {
130266114Sdes		    cnputc(*db_lc);
131266114Sdes		    db_lc++;
132266114Sdes		}
133266114Sdes		break;
134266114Sdes	    case CTRL('h'):
135266114Sdes	    case 0177:
136238106Sdes		/* erase previous character */
137238106Sdes		if (db_lc > db_lbuf_start)
138238106Sdes		    db_delete(1, DEL_BWD);
139238106Sdes		break;
140238106Sdes	    case CTRL('d'):
141238106Sdes		/* erase next character */
142238106Sdes		if (db_lc < db_le)
143238106Sdes		    db_delete(1, DEL_FWD);
144238106Sdes		break;
145238106Sdes	    case CTRL('k'):
146238106Sdes		/* delete to end of line */
147238106Sdes		if (db_lc < db_le)
148266114Sdes		    db_delete(db_le - db_lc, DEL_FWD);
149238106Sdes		break;
150238106Sdes	    case CTRL('t'):
151255579Sdes		/* twiddle last 2 characters */
152		if (db_lc >= db_lbuf_start + 2) {
153		    c = db_lc[-2];
154		    db_lc[-2] = db_lc[-1];
155		    db_lc[-1] = c;
156		    cnputc(BACKUP);
157		    cnputc(BACKUP);
158		    cnputc(db_lc[-2]);
159		    cnputc(db_lc[-1]);
160		}
161		break;
162	    case CTRL('r'):
163		db_putstring("^R\n", 3);
164		if (db_le > db_lbuf_start) {
165		    db_putstring(db_lbuf_start, db_le - db_lbuf_start);
166		    db_putnchars(BACKUP, db_le - db_lc);
167		}
168		break;
169	    case '\n':
170	    case '\r':
171		*db_le++ = c;
172		return (1);
173	    default:
174		if (db_le == db_lbuf_end) {
175		    cnputc('\007');
176		}
177		else if (c >= ' ' && c <= '~') {
178		    register char *p;
179
180		    for (p = db_le; p > db_lc; p--)
181			*p = *(p-1);
182		    *db_lc++ = c;
183		    db_le++;
184		    cnputc(c);
185		    db_putstring(db_lc, db_le - db_lc);
186		    db_putnchars(BACKUP, db_le - db_lc);
187		}
188		break;
189	}
190	return (0);
191}
192
193int
194db_readline(lstart, lsize)
195	char *	lstart;
196	int	lsize;
197{
198	db_force_whitespace();	/* synch output position */
199
200	db_lbuf_start = lstart;
201	db_lbuf_end   = lstart + lsize;
202	db_lc = lstart;
203	db_le = lstart;
204
205	while (!db_inputchar(cngetc()))
206	    continue;
207
208	db_putchar('\n');	/* synch output position */
209
210	*db_le = 0;
211	return (db_le - db_lbuf_start);
212}
213
214void
215db_check_interrupt()
216{
217	register int	c;
218
219	c = cnmaygetc();
220	switch (c) {
221	    case -1:		/* no character */
222		return;
223
224	    case CTRL('c'):
225		db_error((char *)0);
226		/*NOTREACHED*/
227
228	    case CTRL('s'):
229		do {
230		    c = cnmaygetc();
231		    if (c == CTRL('c'))
232			db_error((char *)0);
233		} while (c != CTRL('q'));
234		break;
235
236	    default:
237		/* drop on floor */
238		break;
239	}
240}
241
242cnmaygetc ()
243{
244	return (-1);
245}
246
247/* called from kdb_trap in db_interface.c */
248cnpollc (flag)
249{
250}
251