Deleted Added
full compact
read.c (8870) read.c (26926)
1/*-
2 * Copyright (c) 1992, 1993
3 * The Regents of the University of California. All rights reserved.
4 *
5 * This code is derived from software contributed to Berkeley by
6 * Christos Zoulas of Cornell University.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 * must display the following acknowledgement:
18 * This product includes software developed by the University of
19 * California, Berkeley and its contributors.
20 * 4. Neither the name of the University nor the names of its contributors
21 * may be used to endorse or promote products derived from this software
22 * without specific prior written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 * SUCH DAMAGE.
35 */
36
37#if !defined(lint) && !defined(SCCSID)
38static char sccsid[] = "@(#)read.c 8.1 (Berkeley) 6/4/93";
39
40#endif /* not lint && not SCCSID */
41/*
42 * read.c: Clean this junk up! This is horrible code.
43 * Terminal read functions
44 */
45#include "sys.h"
46#include <sys/errno.h>
47#include <unistd.h>
48#include <stdlib.h>
49extern int errno;
50#include "el.h"
51
52#define OKCMD -1
53
54private int read__fixio __P((int, int));
55private int read_preread __P((EditLine *));
56private int read_getcmd __P((EditLine *, el_action_t *, char *));
57
58#ifdef DEBUG_EDIT
59private void
60read_debug(el)
61 EditLine *el;
62{
63
64 if (el->el_line.cursor > el->el_line.lastchar)
65 (void) fprintf(el->el_errfile, "cursor > lastchar\r\n");
66 if (el->el_line.cursor < el->el_line.buffer)
67 (void) fprintf(el->el_errfile, "cursor < buffer\r\n");
68 if (el->el_line.cursor > el->el_line.limit)
69 (void) fprintf(el->el_errfile, "cursor > limit\r\n");
70 if (el->el_line.lastchar > el->el_line.limit)
71 (void) fprintf(el->el_errfile, "lastchar > limit\r\n");
72 if (el->el_line.limit != &el->el_line.buffer[EL_BUFSIZ - 2])
73 (void) fprintf(el->el_errfile, "limit != &buffer[EL_BUFSIZ-2]\r\n");
74}
75#endif /* DEBUG_EDIT */
76
77/* read__fixio():
78 * Try to recover from a read error
79 */
80private int
81read__fixio(fd, e)
82 int fd, e;
83{
84 switch (e) {
85 case -1: /* Make sure that the code is reachable */
86
87#ifdef EWOULDBLOCK
88 case EWOULDBLOCK:
1/*-
2 * Copyright (c) 1992, 1993
3 * The Regents of the University of California. All rights reserved.
4 *
5 * This code is derived from software contributed to Berkeley by
6 * Christos Zoulas of Cornell University.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 * must display the following acknowledgement:
18 * This product includes software developed by the University of
19 * California, Berkeley and its contributors.
20 * 4. Neither the name of the University nor the names of its contributors
21 * may be used to endorse or promote products derived from this software
22 * without specific prior written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 * SUCH DAMAGE.
35 */
36
37#if !defined(lint) && !defined(SCCSID)
38static char sccsid[] = "@(#)read.c 8.1 (Berkeley) 6/4/93";
39
40#endif /* not lint && not SCCSID */
41/*
42 * read.c: Clean this junk up! This is horrible code.
43 * Terminal read functions
44 */
45#include "sys.h"
46#include <sys/errno.h>
47#include <unistd.h>
48#include <stdlib.h>
49extern int errno;
50#include "el.h"
51
52#define OKCMD -1
53
54private int read__fixio __P((int, int));
55private int read_preread __P((EditLine *));
56private int read_getcmd __P((EditLine *, el_action_t *, char *));
57
58#ifdef DEBUG_EDIT
59private void
60read_debug(el)
61 EditLine *el;
62{
63
64 if (el->el_line.cursor > el->el_line.lastchar)
65 (void) fprintf(el->el_errfile, "cursor > lastchar\r\n");
66 if (el->el_line.cursor < el->el_line.buffer)
67 (void) fprintf(el->el_errfile, "cursor < buffer\r\n");
68 if (el->el_line.cursor > el->el_line.limit)
69 (void) fprintf(el->el_errfile, "cursor > limit\r\n");
70 if (el->el_line.lastchar > el->el_line.limit)
71 (void) fprintf(el->el_errfile, "lastchar > limit\r\n");
72 if (el->el_line.limit != &el->el_line.buffer[EL_BUFSIZ - 2])
73 (void) fprintf(el->el_errfile, "limit != &buffer[EL_BUFSIZ-2]\r\n");
74}
75#endif /* DEBUG_EDIT */
76
77/* read__fixio():
78 * Try to recover from a read error
79 */
80private int
81read__fixio(fd, e)
82 int fd, e;
83{
84 switch (e) {
85 case -1: /* Make sure that the code is reachable */
86
87#ifdef EWOULDBLOCK
88 case EWOULDBLOCK:
89# define TRY_AGAIN
89# ifndef TRY_AGAIN
90# define TRY_AGAIN
91# endif
90#endif /* EWOULDBLOCK */
91
92#if defined(POSIX) && defined(EAGAIN)
93# if defined(EWOULDBLOCK) && EWOULDBLOCK != EAGAIN
94 case EAGAIN:
92#endif /* EWOULDBLOCK */
93
94#if defined(POSIX) && defined(EAGAIN)
95# if defined(EWOULDBLOCK) && EWOULDBLOCK != EAGAIN
96 case EAGAIN:
95# define TRY_AGAIN
97# ifndef TRY_AGAIN
98# define TRY_AGAIN
99# endif
96# endif /* EWOULDBLOCK && EWOULDBLOCK != EAGAIN */
97#endif /* POSIX && EAGAIN */
98
99 e = 0;
100#ifdef TRY_AGAIN
101# if defined(F_SETFL) && defined(O_NDELAY)
102 if ((e = fcntl(fd, F_GETFL, 0)) == -1)
103 return -1;
104
105 if (fcntl(fd, F_SETFL, e & ~O_NDELAY) == -1)
106 return -1;
107 else
108 e = 1;
109# endif /* F_SETFL && O_NDELAY */
110
111# ifdef FIONBIO
112 if (ioctl(fd, FIONBIO, (ioctl_t) &e) == -1)
113 return -1;
114 else
115 e = 1;
116# endif /* FIONBIO */
117
118#endif /* TRY_AGAIN */
119 return e ? 0 : -1;
120
121 case EINTR:
122 return 0;
123
124 default:
125 return -1;
126 }
127}
128
129
130/* read_preread():
131 * Try to read the stuff in the input queue;
132 */
133private int
134read_preread(el)
135 EditLine *el;
136{
137 int chrs = 0;
138
139 if (el->el_chared.c_macro.nline) {
140 el_free((ptr_t) el->el_chared.c_macro.nline);
141 el->el_chared.c_macro.nline = NULL;
142 }
143
144 if (el->el_tty.t_mode == ED_IO)
145 return 0;
146
147#ifdef FIONREAD
148 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) &chrs);
149 if (chrs > 0) {
150 char buf[EL_BUFSIZ];
151
152 chrs = read(el->el_infd, buf, (size_t) MIN(chrs, EL_BUFSIZ - 1));
153 if (chrs > 0) {
154 buf[chrs] = '\0';
155 el->el_chared.c_macro.nline = strdup(buf);
156 el_push(el->el_chared.c_macro.nline);
157 }
158 }
159#endif /* FIONREAD */
160
161 return chrs > 0;
162}
163
164
165/* el_push():
166 * Push a macro
167 */
168public void
169el_push(el, str)
170 EditLine *el;
171 const char *str;
172{
173 c_macro_t *ma = &el->el_chared.c_macro;
174
175 if (str != NULL && ma->level + 1 < EL_MAXMACRO) {
176 ma->level++;
177 ma->macro[ma->level] = (char *) str;
178 }
179 else {
180 term_beep(el);
181 term__flush();
182 }
183}
184
185
186/* read_getcmd():
187 * Return next command from the input stream.
188 */
189private int
190read_getcmd(el, cmdnum, ch)
191 EditLine *el;
192 el_action_t *cmdnum;
193 char *ch;
194{
195 el_action_t cmd = 0;
196 int num;
197
198 while (cmd == 0 || cmd == ED_SEQUENCE_LEAD_IN) {
199 if ((num = el_getc(el, ch)) != 1) /* if EOF or error */
200 return num;
201
202#ifdef KANJI
203 if ((*ch & 0200)) {
204 el->el_state.metanext = 0;
205 cmd = CcViMap[' '];
206 break;
207 }
208 else
209#endif /* KANJI */
210
211 if (el->el_state.metanext) {
212 el->el_state.metanext = 0;
213 *ch |= 0200;
214 }
215 cmd = el->el_map.current[(unsigned char) *ch];
216 if (cmd == ED_SEQUENCE_LEAD_IN) {
217 key_value_t val;
218 switch (key_get(el, ch, &val)) {
219 case XK_CMD:
220 cmd = val.cmd;
221 break;
222 case XK_STR:
223 el_push(el, val.str);
224 break;
225#ifdef notyet
226 case XK_EXE:
227 /* XXX: In the future to run a user function */
228 RunCommand(val.str);
229 break;
230#endif
231 default:
232 abort();
233 break;
234 }
235 }
236 if (el->el_map.alt == NULL)
237 el->el_map.current = el->el_map.key;
238 }
239 *cmdnum = cmd;
240 return OKCMD;
241}
242
243
244/* el_getc():
245 * Read a character
246 */
247public int
248el_getc(el, cp)
249 EditLine *el;
250 char *cp;
251{
252 int num_read;
253 unsigned char tcp;
254 int tried = 0;
255
256 c_macro_t *ma = &el->el_chared.c_macro;
257
258 term__flush();
259 for (;;) {
260 if (ma->level < 0) {
261 if (!read_preread(el))
262 break;
263 }
264 if (ma->level < 0)
265 break;
266
267 if (*ma->macro[ma->level] == 0) {
268 ma->level--;
269 continue;
270 }
271 *cp = *ma->macro[ma->level]++ & 0377;
272 if (*ma->macro[ma->level] == 0) { /* Needed for QuoteMode On */
273 ma->level--;
274 }
275 return 1;
276 }
277
278#ifdef DEBUG_READ
279 (void) fprintf(el->el_errfile, "Turning raw mode on\n");
280#endif /* DEBUG_READ */
281 if (tty_rawmode(el) < 0) /* make sure the tty is set up correctly */
282 return 0;
283
284#ifdef DEBUG_READ
285 (void) fprintf(el->el_errfile, "Reading a character\n");
286#endif /* DEBUG_READ */
287 while ((num_read = read(el->el_infd, (char *) &tcp, 1)) == -1)
288 if (!tried && read__fixio(el->el_infd, errno) == 0)
289 tried = 1;
290 else {
291 *cp = '\0';
292 return -1;
293 }
294#ifdef DEBUG_READ
295 (void) fprintf(el->el_errfile, "Got it %c\n", tcp);
296#endif /* DEBUG_READ */
297 *cp = tcp;
298 return num_read;
299}
300
301
302
303public const char *
304el_gets(el, nread)
305 EditLine *el;
306 int *nread;
307{
308 int retval;
309 el_action_t cmdnum = 0;
310 int num; /* how many chars we have read at NL */
311 char ch;
312
313 if (el->el_flags & HANDLE_SIGNALS)
314 sig_set(el);
315
316 re_clear_display(el); /* reset the display stuff */
317 ch_reset(el);
318
319#ifdef FIONREAD
320 if (el->el_tty.t_mode == EX_IO && ma->level < 0) {
321 long chrs = 0;
322
323 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) &chrs);
324 if (chrs == 0) {
325 if (tty_rawmode(el) < 0) {
326 if (nread)
327 *nread = 0;
328 return NULL;
329 }
330 }
331 }
332#endif /* FIONREAD */
333
334 re_refresh(el); /* print the prompt */
335
336 for (num = OKCMD; num == OKCMD;) { /* while still editing this line */
337#ifdef DEBUG_EDIT
338 read_debug(el);
339#endif /* DEBUG_EDIT */
340 /* if EOF or error */
341 if ((num = read_getcmd(el, &cmdnum, &ch)) != OKCMD) {
342#ifdef DEBUG_READ
343 (void) fprintf(el->el_errfile, "Returning from el_gets %d\n", num);
344#endif /* DEBUG_READ */
345 break;
346 }
347
348 if (cmdnum >= el->el_map.nfunc) { /* BUG CHECK command */
349#ifdef DEBUG_EDIT
350 (void) fprintf(el->el_errfile,
351 "ERROR: illegal command from key 0%o\r\n", ch);
352#endif /* DEBUG_EDIT */
353 continue; /* try again */
354 }
355
356 /* now do the real command */
357#ifdef DEBUG_READ
358 {
359 el_bindings_t *b;
360 for (b = el->el_map.help; b->name; b++)
361 if (b->func == cmdnum)
362 break;
363 if (b->name)
364 (void) fprintf(el->el_errfile, "Executing %s\n", b->name);
365 else
366 (void) fprintf(el->el_errfile, "Error command = %d\n", cmdnum);
367 }
368#endif /* DEBUG_READ */
369 retval = (*el->el_map.func[cmdnum])(el, ch);
370
371 /* save the last command here */
372 el->el_state.lastcmd = cmdnum;
373
374 /* use any return value */
375 switch (retval) {
376 case CC_CURSOR:
377 el->el_state.argument = 1;
378 el->el_state.doingarg = 0;
379 re_refresh_cursor(el);
380 break;
381
100# endif /* EWOULDBLOCK && EWOULDBLOCK != EAGAIN */
101#endif /* POSIX && EAGAIN */
102
103 e = 0;
104#ifdef TRY_AGAIN
105# if defined(F_SETFL) && defined(O_NDELAY)
106 if ((e = fcntl(fd, F_GETFL, 0)) == -1)
107 return -1;
108
109 if (fcntl(fd, F_SETFL, e & ~O_NDELAY) == -1)
110 return -1;
111 else
112 e = 1;
113# endif /* F_SETFL && O_NDELAY */
114
115# ifdef FIONBIO
116 if (ioctl(fd, FIONBIO, (ioctl_t) &e) == -1)
117 return -1;
118 else
119 e = 1;
120# endif /* FIONBIO */
121
122#endif /* TRY_AGAIN */
123 return e ? 0 : -1;
124
125 case EINTR:
126 return 0;
127
128 default:
129 return -1;
130 }
131}
132
133
134/* read_preread():
135 * Try to read the stuff in the input queue;
136 */
137private int
138read_preread(el)
139 EditLine *el;
140{
141 int chrs = 0;
142
143 if (el->el_chared.c_macro.nline) {
144 el_free((ptr_t) el->el_chared.c_macro.nline);
145 el->el_chared.c_macro.nline = NULL;
146 }
147
148 if (el->el_tty.t_mode == ED_IO)
149 return 0;
150
151#ifdef FIONREAD
152 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) &chrs);
153 if (chrs > 0) {
154 char buf[EL_BUFSIZ];
155
156 chrs = read(el->el_infd, buf, (size_t) MIN(chrs, EL_BUFSIZ - 1));
157 if (chrs > 0) {
158 buf[chrs] = '\0';
159 el->el_chared.c_macro.nline = strdup(buf);
160 el_push(el->el_chared.c_macro.nline);
161 }
162 }
163#endif /* FIONREAD */
164
165 return chrs > 0;
166}
167
168
169/* el_push():
170 * Push a macro
171 */
172public void
173el_push(el, str)
174 EditLine *el;
175 const char *str;
176{
177 c_macro_t *ma = &el->el_chared.c_macro;
178
179 if (str != NULL && ma->level + 1 < EL_MAXMACRO) {
180 ma->level++;
181 ma->macro[ma->level] = (char *) str;
182 }
183 else {
184 term_beep(el);
185 term__flush();
186 }
187}
188
189
190/* read_getcmd():
191 * Return next command from the input stream.
192 */
193private int
194read_getcmd(el, cmdnum, ch)
195 EditLine *el;
196 el_action_t *cmdnum;
197 char *ch;
198{
199 el_action_t cmd = 0;
200 int num;
201
202 while (cmd == 0 || cmd == ED_SEQUENCE_LEAD_IN) {
203 if ((num = el_getc(el, ch)) != 1) /* if EOF or error */
204 return num;
205
206#ifdef KANJI
207 if ((*ch & 0200)) {
208 el->el_state.metanext = 0;
209 cmd = CcViMap[' '];
210 break;
211 }
212 else
213#endif /* KANJI */
214
215 if (el->el_state.metanext) {
216 el->el_state.metanext = 0;
217 *ch |= 0200;
218 }
219 cmd = el->el_map.current[(unsigned char) *ch];
220 if (cmd == ED_SEQUENCE_LEAD_IN) {
221 key_value_t val;
222 switch (key_get(el, ch, &val)) {
223 case XK_CMD:
224 cmd = val.cmd;
225 break;
226 case XK_STR:
227 el_push(el, val.str);
228 break;
229#ifdef notyet
230 case XK_EXE:
231 /* XXX: In the future to run a user function */
232 RunCommand(val.str);
233 break;
234#endif
235 default:
236 abort();
237 break;
238 }
239 }
240 if (el->el_map.alt == NULL)
241 el->el_map.current = el->el_map.key;
242 }
243 *cmdnum = cmd;
244 return OKCMD;
245}
246
247
248/* el_getc():
249 * Read a character
250 */
251public int
252el_getc(el, cp)
253 EditLine *el;
254 char *cp;
255{
256 int num_read;
257 unsigned char tcp;
258 int tried = 0;
259
260 c_macro_t *ma = &el->el_chared.c_macro;
261
262 term__flush();
263 for (;;) {
264 if (ma->level < 0) {
265 if (!read_preread(el))
266 break;
267 }
268 if (ma->level < 0)
269 break;
270
271 if (*ma->macro[ma->level] == 0) {
272 ma->level--;
273 continue;
274 }
275 *cp = *ma->macro[ma->level]++ & 0377;
276 if (*ma->macro[ma->level] == 0) { /* Needed for QuoteMode On */
277 ma->level--;
278 }
279 return 1;
280 }
281
282#ifdef DEBUG_READ
283 (void) fprintf(el->el_errfile, "Turning raw mode on\n");
284#endif /* DEBUG_READ */
285 if (tty_rawmode(el) < 0) /* make sure the tty is set up correctly */
286 return 0;
287
288#ifdef DEBUG_READ
289 (void) fprintf(el->el_errfile, "Reading a character\n");
290#endif /* DEBUG_READ */
291 while ((num_read = read(el->el_infd, (char *) &tcp, 1)) == -1)
292 if (!tried && read__fixio(el->el_infd, errno) == 0)
293 tried = 1;
294 else {
295 *cp = '\0';
296 return -1;
297 }
298#ifdef DEBUG_READ
299 (void) fprintf(el->el_errfile, "Got it %c\n", tcp);
300#endif /* DEBUG_READ */
301 *cp = tcp;
302 return num_read;
303}
304
305
306
307public const char *
308el_gets(el, nread)
309 EditLine *el;
310 int *nread;
311{
312 int retval;
313 el_action_t cmdnum = 0;
314 int num; /* how many chars we have read at NL */
315 char ch;
316
317 if (el->el_flags & HANDLE_SIGNALS)
318 sig_set(el);
319
320 re_clear_display(el); /* reset the display stuff */
321 ch_reset(el);
322
323#ifdef FIONREAD
324 if (el->el_tty.t_mode == EX_IO && ma->level < 0) {
325 long chrs = 0;
326
327 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) &chrs);
328 if (chrs == 0) {
329 if (tty_rawmode(el) < 0) {
330 if (nread)
331 *nread = 0;
332 return NULL;
333 }
334 }
335 }
336#endif /* FIONREAD */
337
338 re_refresh(el); /* print the prompt */
339
340 for (num = OKCMD; num == OKCMD;) { /* while still editing this line */
341#ifdef DEBUG_EDIT
342 read_debug(el);
343#endif /* DEBUG_EDIT */
344 /* if EOF or error */
345 if ((num = read_getcmd(el, &cmdnum, &ch)) != OKCMD) {
346#ifdef DEBUG_READ
347 (void) fprintf(el->el_errfile, "Returning from el_gets %d\n", num);
348#endif /* DEBUG_READ */
349 break;
350 }
351
352 if (cmdnum >= el->el_map.nfunc) { /* BUG CHECK command */
353#ifdef DEBUG_EDIT
354 (void) fprintf(el->el_errfile,
355 "ERROR: illegal command from key 0%o\r\n", ch);
356#endif /* DEBUG_EDIT */
357 continue; /* try again */
358 }
359
360 /* now do the real command */
361#ifdef DEBUG_READ
362 {
363 el_bindings_t *b;
364 for (b = el->el_map.help; b->name; b++)
365 if (b->func == cmdnum)
366 break;
367 if (b->name)
368 (void) fprintf(el->el_errfile, "Executing %s\n", b->name);
369 else
370 (void) fprintf(el->el_errfile, "Error command = %d\n", cmdnum);
371 }
372#endif /* DEBUG_READ */
373 retval = (*el->el_map.func[cmdnum])(el, ch);
374
375 /* save the last command here */
376 el->el_state.lastcmd = cmdnum;
377
378 /* use any return value */
379 switch (retval) {
380 case CC_CURSOR:
381 el->el_state.argument = 1;
382 el->el_state.doingarg = 0;
383 re_refresh_cursor(el);
384 break;
385
386 case CC_REDISPLAY:
387 re_clear_lines(el);
388 re_clear_display(el);
389 /* FALLTHROUGH */
390
382 case CC_REFRESH:
383 el->el_state.argument = 1;
384 el->el_state.doingarg = 0;
385 re_refresh(el);
386 break;
387
388 case CC_NORM: /* normal char */
389 el->el_state.argument = 1;
390 el->el_state.doingarg = 0;
391 break;
392
393 case CC_ARGHACK: /* Suggested by Rich Salz */
394 /* <rsalz@pineapple.bbn.com> */
395 break; /* keep going... */
396
397 case CC_EOF: /* end of file typed */
398 num = 0;
399 break;
400
401 case CC_NEWLINE: /* normal end of line */
402 num = el->el_line.lastchar - el->el_line.buffer;
403 break;
404
405 case CC_FATAL: /* fatal error, reset to known state */
406#ifdef DEBUG_READ
407 (void) fprintf(el->el_errfile, "*** editor fatal ERROR ***\r\n\n");
408#endif /* DEBUG_READ */
409 /* put (real) cursor in a known place */
410 re_clear_display(el); /* reset the display stuff */
411 ch_reset(el); /* reset the input pointers */
412 re_refresh(el); /* print the prompt again */
413 el->el_state.argument = 1;
414 el->el_state.doingarg = 0;
415 break;
416
417 case CC_ERROR:
418 default: /* functions we don't know about */
419#ifdef DEBUG_READ
420 (void) fprintf(el->el_errfile, "*** editor ERROR ***\r\n\n");
421#endif /* DEBUG_READ */
422 el->el_state.argument = 1;
423 el->el_state.doingarg = 0;
424 term_beep(el);
425 term__flush();
426 break;
427 }
428 }
429
430 (void) tty_cookedmode(el); /* make sure the tty is set up correctly */
431 term__flush(); /* flush any buffered output */
432 if (el->el_flags & HANDLE_SIGNALS)
433 sig_clr(el);
434 if (nread)
435 *nread = num;
436 return num ? el->el_line.buffer : NULL;
437}
391 case CC_REFRESH:
392 el->el_state.argument = 1;
393 el->el_state.doingarg = 0;
394 re_refresh(el);
395 break;
396
397 case CC_NORM: /* normal char */
398 el->el_state.argument = 1;
399 el->el_state.doingarg = 0;
400 break;
401
402 case CC_ARGHACK: /* Suggested by Rich Salz */
403 /* <rsalz@pineapple.bbn.com> */
404 break; /* keep going... */
405
406 case CC_EOF: /* end of file typed */
407 num = 0;
408 break;
409
410 case CC_NEWLINE: /* normal end of line */
411 num = el->el_line.lastchar - el->el_line.buffer;
412 break;
413
414 case CC_FATAL: /* fatal error, reset to known state */
415#ifdef DEBUG_READ
416 (void) fprintf(el->el_errfile, "*** editor fatal ERROR ***\r\n\n");
417#endif /* DEBUG_READ */
418 /* put (real) cursor in a known place */
419 re_clear_display(el); /* reset the display stuff */
420 ch_reset(el); /* reset the input pointers */
421 re_refresh(el); /* print the prompt again */
422 el->el_state.argument = 1;
423 el->el_state.doingarg = 0;
424 break;
425
426 case CC_ERROR:
427 default: /* functions we don't know about */
428#ifdef DEBUG_READ
429 (void) fprintf(el->el_errfile, "*** editor ERROR ***\r\n\n");
430#endif /* DEBUG_READ */
431 el->el_state.argument = 1;
432 el->el_state.doingarg = 0;
433 term_beep(el);
434 term__flush();
435 break;
436 }
437 }
438
439 (void) tty_cookedmode(el); /* make sure the tty is set up correctly */
440 term__flush(); /* flush any buffered output */
441 if (el->el_flags & HANDLE_SIGNALS)
442 sig_clr(el);
443 if (nread)
444 *nread = num;
445 return num ? el->el_line.buffer : NULL;
446}