db_input.c revision 1.1
1/*
2 * Mach Operating System
3 * Copyright (c) 1991,1990 Carnegie Mellon University
4 * All Rights Reserved.
5 *
6 * Permission to use, copy, modify and distribute this software and its
7 * documentation is hereby granted, provided that both the copyright
8 * notice and this permission notice appear in all copies of the
9 * software, derivative works or modified versions, and any portions
10 * thereof, and that both notices appear in supporting documentation.
11 *
12 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
13 * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
14 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
15 *
16 * Carnegie Mellon requests users of this software to return to
17 *
18 *  Software Distribution Coordinator  or  Software.Distribution@CS.CMU.EDU
19 *  School of Computer Science
20 *  Carnegie Mellon University
21 *  Pittsburgh PA 15213-3890
22 *
23 * any improvements or extensions that they make and grant Carnegie the
24 * rights to redistribute these changes.
25 */
26/*
27 * HISTORY
28 * $Log: db_input.c,v $
29 * Revision 1.1  1993/03/21 09:45:37  cgd
30 * Initial revision
31 *
32 * Revision 1.1  1992/03/25  21:45:10  pace
33 * Initial revision
34 *
35 * Revision 2.4  91/02/14  14:41:53  mrt
36 * 	Add input line editing.
37 * 	[90/11/11            dbg]
38 *
39 * Revision 2.3  91/02/05  17:06:32  mrt
40 * 	Changed to new Mach copyright
41 * 	[91/01/31  16:18:13  mrt]
42 *
43 * Revision 2.2  90/08/27  21:51:03  dbg
44 * 	Reduce lint.
45 * 	[90/08/07            dbg]
46 * 	Created.
47 * 	[90/07/25            dbg]
48 *
49 */
50/*
51 *	Author: David B. Golub, Carnegie Mellon University
52 *	Date:	7/90
53 */
54
55#include "param.h"
56#include "proc.h"
57#include <ddb/db_output.h>
58
59/*
60 * Character input and editing.
61 */
62
63/*
64 * We don't track output position while editing input,
65 * since input always ends with a new-line.  We just
66 * reset the line position at the end.
67 */
68char *	db_lbuf_start;	/* start of input line buffer */
69char *	db_lbuf_end;	/* end of input line buffer */
70char *	db_lc;		/* current character */
71char *	db_le;		/* one past last character */
72
73#define	CTRL(c)		((c) & 0x1f)
74#define	isspace(c)	((c) == ' ' || (c) == '\t')
75#define	BLANK		' '
76#define	BACKUP		'\b'
77
78void
79db_putstring(s, count)
80	char	*s;
81	int	count;
82{
83	while (--count >= 0)
84	    cnputc(*s++);
85}
86
87void
88db_putnchars(c, count)
89	int	c;
90	int	count;
91{
92	while (--count >= 0)
93	    cnputc(c);
94}
95
96/*
97 * Delete N characters, forward or backward
98 */
99#define	DEL_FWD		0
100#define	DEL_BWD		1
101void
102db_delete(n, bwd)
103	int	n;
104	int	bwd;
105{
106	register char *p;
107
108	if (bwd) {
109	    db_lc -= n;
110	    db_putnchars(BACKUP, n);
111	}
112	for (p = db_lc; p < db_le-n; p++) {
113	    *p = *(p+n);
114	    cnputc(*p);
115	}
116	db_putnchars(BLANK, n);
117	db_putnchars(BACKUP, db_le - db_lc);
118	db_le -= n;
119}
120
121/* returns TRUE at end-of-line */
122int
123db_inputchar(c)
124	int	c;
125{
126	switch (c) {
127	    case CTRL('b'):
128		/* back up one character */
129		if (db_lc > db_lbuf_start) {
130		    cnputc(BACKUP);
131		    db_lc--;
132		}
133		break;
134	    case CTRL('f'):
135		/* forward one character */
136		if (db_lc < db_le) {
137		    cnputc(*db_lc);
138		    db_lc++;
139		}
140		break;
141	    case CTRL('a'):
142		/* beginning of line */
143		while (db_lc > db_lbuf_start) {
144		    cnputc(BACKUP);
145		    db_lc--;
146		}
147		break;
148	    case CTRL('e'):
149		/* end of line */
150		while (db_lc < db_le) {
151		    cnputc(*db_lc);
152		    db_lc++;
153		}
154		break;
155	    case CTRL('h'):
156	    case 0177:
157		/* erase previous character */
158		if (db_lc > db_lbuf_start)
159		    db_delete(1, DEL_BWD);
160		break;
161	    case CTRL('d'):
162		/* erase next character */
163		if (db_lc < db_le)
164		    db_delete(1, DEL_FWD);
165		break;
166	    case CTRL('k'):
167		/* delete to end of line */
168		if (db_lc < db_le)
169		    db_delete(db_le - db_lc, DEL_FWD);
170		break;
171	    case CTRL('t'):
172		/* twiddle last 2 characters */
173		if (db_lc >= db_lbuf_start + 2) {
174		    c = db_lc[-2];
175		    db_lc[-2] = db_lc[-1];
176		    db_lc[-1] = c;
177		    cnputc(BACKUP);
178		    cnputc(BACKUP);
179		    cnputc(db_lc[-2]);
180		    cnputc(db_lc[-1]);
181		}
182		break;
183	    case CTRL('r'):
184		db_putstring("^R\n", 3);
185		if (db_le > db_lbuf_start) {
186		    db_putstring(db_lbuf_start, db_le - db_lbuf_start);
187		    db_putnchars(BACKUP, db_le - db_lc);
188		}
189		break;
190	    case '\n':
191	    case '\r':
192		*db_le++ = c;
193		return (1);
194	    default:
195		if (db_le == db_lbuf_end) {
196		    cnputc('\007');
197		}
198		else if (c >= ' ' && c <= '~') {
199		    register char *p;
200
201		    for (p = db_le; p > db_lc; p--)
202			*p = *(p-1);
203		    *db_lc++ = c;
204		    db_le++;
205		    cnputc(c);
206		    db_putstring(db_lc, db_le - db_lc);
207		    db_putnchars(BACKUP, db_le - db_lc);
208		}
209		break;
210	}
211	return (0);
212}
213
214int
215db_readline(lstart, lsize)
216	char *	lstart;
217	int	lsize;
218{
219	db_force_whitespace();	/* synch output position */
220
221	db_lbuf_start = lstart;
222	db_lbuf_end   = lstart + lsize;
223	db_lc = lstart;
224	db_le = lstart;
225
226	while (!db_inputchar(cngetc()))
227	    continue;
228
229	db_putchar('\n');	/* synch output position */
230
231	*db_le = 0;
232	return (db_le - db_lbuf_start);
233}
234
235void
236db_check_interrupt()
237{
238	register int	c;
239
240	c = cnmaygetc();
241	switch (c) {
242	    case -1:		/* no character */
243		return;
244
245	    case CTRL('c'):
246		db_error((char *)0);
247		/*NOTREACHED*/
248
249	    case CTRL('s'):
250		do {
251		    c = cnmaygetc();
252		    if (c == CTRL('c'))
253			db_error((char *)0);
254		} while (c != CTRL('q'));
255		break;
256
257	    default:
258		/* drop on floor */
259		break;
260	}
261}
262
263cnmaygetc ()
264{
265	return (-1);
266}
267
268/* called from kdb_trap in db_interface.c */
269cnpollc (flag)
270{
271}
272