read.c (225736) | read.c (237738) |
---|---|
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 --- 15 unchanged lines hidden (view full) --- 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 * | 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 --- 15 unchanged lines hidden (view full) --- 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 * |
32 * $NetBSD: read.c,v 1.40 2007/03/01 21:41:45 christos Exp $ | 32 * $NetBSD: read.c,v 1.52 2009/07/22 15:57:00 christos Exp $ |
33 */ 34 35#if !defined(lint) && !defined(SCCSID) 36static char sccsid[] = "@(#)read.c 8.1 (Berkeley) 6/4/93"; 37#endif /* not lint && not SCCSID */ 38#include <sys/cdefs.h> | 33 */ 34 35#if !defined(lint) && !defined(SCCSID) 36static char sccsid[] = "@(#)read.c 8.1 (Berkeley) 6/4/93"; 37#endif /* not lint && not SCCSID */ 38#include <sys/cdefs.h> |
39__FBSDID("$FreeBSD: stable/9/lib/libedit/read.c 220370 2011-04-05 18:41:01Z obrien $"); | 39__FBSDID("$FreeBSD: stable/9/lib/libedit/read.c 237738 2012-06-29 03:01:38Z pfg $"); |
40 41/* 42 * read.c: Clean this junk up! This is horrible code. 43 * Terminal read functions 44 */ 45#include "sys.h" 46#include <errno.h> 47#include <fcntl.h> 48#include <unistd.h> 49#include <stdlib.h> 50#include "el.h" 51 | 40 41/* 42 * read.c: Clean this junk up! This is horrible code. 43 * Terminal read functions 44 */ 45#include "sys.h" 46#include <errno.h> 47#include <fcntl.h> 48#include <unistd.h> 49#include <stdlib.h> 50#include "el.h" 51 |
52#define OKCMD -1 | 52#define OKCMD -1 /* must be -1! */ |
53 54private int read__fixio(int, int); 55private int read_preread(EditLine *); 56private int read_char(EditLine *, char *); 57private int read_getcmd(EditLine *, el_action_t *, char *); 58private void read_pop(c_macro_t *); 59 60/* read_init(): --- 104 unchanged lines hidden (view full) --- 165 e = 1; 166 } 167#endif /* FIONBIO */ 168 169#endif /* TRY_AGAIN */ 170 return (e ? 0 : -1); 171 172 case EINTR: | 53 54private int read__fixio(int, int); 55private int read_preread(EditLine *); 56private int read_char(EditLine *, char *); 57private int read_getcmd(EditLine *, el_action_t *, char *); 58private void read_pop(c_macro_t *); 59 60/* read_init(): --- 104 unchanged lines hidden (view full) --- 165 e = 1; 166 } 167#endif /* FIONBIO */ 168 169#endif /* TRY_AGAIN */ 170 return (e ? 0 : -1); 171 172 case EINTR: |
173 return (0); | 173 return (-1); |
174 175 default: 176 return (-1); 177 } 178} 179 180 181/* read_preread(): --- 35 unchanged lines hidden (view full) --- 217 218 if (str != NULL && ma->level + 1 < EL_MAXMACRO) { 219 ma->level++; 220 if ((ma->macro[ma->level] = el_strdup(str)) != NULL) 221 return; 222 ma->level--; 223 } 224 term_beep(el); | 174 175 default: 176 return (-1); 177 } 178} 179 180 181/* read_preread(): --- 35 unchanged lines hidden (view full) --- 217 218 if (str != NULL && ma->level + 1 < EL_MAXMACRO) { 219 ma->level++; 220 if ((ma->macro[ma->level] = el_strdup(str)) != NULL) 221 return; 222 ma->level--; 223 } 224 term_beep(el); |
225 term__flush(); | 225 term__flush(el); |
226} 227 228 229/* read_getcmd(): 230 * Return next command from the input stream. 231 */ 232private int 233read_getcmd(EditLine *el, el_action_t *cmdnum, char *ch) 234{ 235 el_action_t cmd; 236 int num; 237 | 226} 227 228 229/* read_getcmd(): 230 * Return next command from the input stream. 231 */ 232private int 233read_getcmd(EditLine *el, el_action_t *cmdnum, char *ch) 234{ 235 el_action_t cmd; 236 int num; 237 |
238 el->el_errno = 0; |
|
238 do { | 239 do { |
239 if ((num = el_getc(el, ch)) != 1) /* if EOF or error */ | 240 if ((num = el_getc(el, ch)) != 1) { /* if EOF or error */ 241 el->el_errno = num == 0 ? 0 : errno; |
240 return (num); | 242 return (num); |
243 } |
|
241 242#ifdef KANJI 243 if ((*ch & 0200)) { 244 el->el_state.metanext = 0; 245 cmd = CcViMap[' ']; 246 break; 247 } else 248#endif /* KANJI */ --- 32 unchanged lines hidden (view full) --- 281 282 283/* read_char(): 284 * Read a character from the tty. 285 */ 286private int 287read_char(EditLine *el, char *cp) 288{ | 244 245#ifdef KANJI 246 if ((*ch & 0200)) { 247 el->el_state.metanext = 0; 248 cmd = CcViMap[' ']; 249 break; 250 } else 251#endif /* KANJI */ --- 32 unchanged lines hidden (view full) --- 284 285 286/* read_char(): 287 * Read a character from the tty. 288 */ 289private int 290read_char(EditLine *el, char *cp) 291{ |
289 int num_read; | 292 ssize_t num_read; |
290 int tried = 0; 291 | 293 int tried = 0; 294 |
292 while ((num_read = read(el->el_infd, cp, 1)) == -1) | 295 again: 296 el->el_signal->sig_no = 0; 297 while ((num_read = read(el->el_infd, cp, 1)) == -1) { 298 if (el->el_signal->sig_no == SIGCONT) { 299 sig_set(el); 300 el_set(el, EL_REFRESH); 301 goto again; 302 } |
293 if (!tried && read__fixio(el->el_infd, errno) == 0) 294 tried = 1; 295 else { 296 *cp = '\0'; 297 return (-1); 298 } | 303 if (!tried && read__fixio(el->el_infd, errno) == 0) 304 tried = 1; 305 else { 306 *cp = '\0'; 307 return (-1); 308 } |
299 300 return (num_read); | 309 } 310 return (int)num_read; |
301} 302 303/* read_pop(): 304 * Pop a macro from the stack 305 */ 306private void 307read_pop(c_macro_t *ma) 308{ 309 int i; 310 311 el_free(ma->macro[0]); | 311} 312 313/* read_pop(): 314 * Pop a macro from the stack 315 */ 316private void 317read_pop(c_macro_t *ma) 318{ 319 int i; 320 321 el_free(ma->macro[0]); |
312 for (i = ma->level--; i > 0; i--) 313 ma->macro[i - 1] = ma->macro[i]; | 322 for (i = 0; i < ma->level; i++) 323 ma->macro[i] = ma->macro[i + 1]; 324 ma->level--; |
314 ma->offset = 0; 315} 316 317/* el_getc(): 318 * Read a character 319 */ 320public int 321el_getc(EditLine *el, char *cp) 322{ 323 int num_read; 324 c_macro_t *ma = &el->el_chared.c_macro; 325 | 325 ma->offset = 0; 326} 327 328/* el_getc(): 329 * Read a character 330 */ 331public int 332el_getc(EditLine *el, char *cp) 333{ 334 int num_read; 335 c_macro_t *ma = &el->el_chared.c_macro; 336 |
326 term__flush(); | 337 term__flush(el); |
327 for (;;) { 328 if (ma->level < 0) { 329 if (!read_preread(el)) 330 break; 331 } 332 333 if (ma->level < 0) 334 break; --- 42 unchanged lines hidden (view full) --- 377 /* This is relatively cheap, and things go terribly wrong if 378 we have the wrong size. */ 379 el_resize(el); 380 re_clear_display(el); /* reset the display stuff */ 381 ch_reset(el, 0); 382 re_refresh(el); /* print the prompt */ 383 384 if (el->el_flags & UNBUFFERED) | 338 for (;;) { 339 if (ma->level < 0) { 340 if (!read_preread(el)) 341 break; 342 } 343 344 if (ma->level < 0) 345 break; --- 42 unchanged lines hidden (view full) --- 388 /* This is relatively cheap, and things go terribly wrong if 389 we have the wrong size. */ 390 el_resize(el); 391 re_clear_display(el); /* reset the display stuff */ 392 ch_reset(el, 0); 393 re_refresh(el); /* print the prompt */ 394 395 if (el->el_flags & UNBUFFERED) |
385 term__flush(); | 396 term__flush(el); |
386} 387 388protected void 389read_finish(EditLine *el) 390{ 391 if ((el->el_flags & UNBUFFERED) == 0) 392 (void) tty_cookedmode(el); 393 if (el->el_flags & HANDLE_SIGNALS) 394 sig_clr(el); 395} 396 397public const char * 398el_gets(EditLine *el, int *nread) 399{ 400 int retval; 401 el_action_t cmdnum = 0; 402 int num; /* how many chars we have read at NL */ 403 char ch; 404 int crlf = 0; | 397} 398 399protected void 400read_finish(EditLine *el) 401{ 402 if ((el->el_flags & UNBUFFERED) == 0) 403 (void) tty_cookedmode(el); 404 if (el->el_flags & HANDLE_SIGNALS) 405 sig_clr(el); 406} 407 408public const char * 409el_gets(EditLine *el, int *nread) 410{ 411 int retval; 412 el_action_t cmdnum = 0; 413 int num; /* how many chars we have read at NL */ 414 char ch; 415 int crlf = 0; |
416 int nrb; |
|
405#ifdef FIONREAD 406 c_macro_t *ma = &el->el_chared.c_macro; 407#endif /* FIONREAD */ 408 | 417#ifdef FIONREAD 418 c_macro_t *ma = &el->el_chared.c_macro; 419#endif /* FIONREAD */ 420 |
421 if (nread == NULL) 422 nread = &nrb; 423 *nread = 0; 424 |
|
409 if (el->el_flags & NO_TTY) { 410 char *cp = el->el_line.buffer; 411 size_t idx; 412 | 425 if (el->el_flags & NO_TTY) { 426 char *cp = el->el_line.buffer; 427 size_t idx; 428 |
413 while ((*el->el_read.read_char)(el, cp) == 1) { | 429 while ((num = (*el->el_read.read_char)(el, cp)) == 1) { |
414 /* make sure there is space for next character */ 415 if (cp + 1 >= el->el_line.limit) { 416 idx = (cp - el->el_line.buffer); 417 if (!ch_enlargebufs(el, 2)) 418 break; 419 cp = &el->el_line.buffer[idx]; 420 } 421 cp++; 422 if (el->el_flags & UNBUFFERED) 423 break; 424 if (cp[-1] == '\r' || cp[-1] == '\n') 425 break; 426 } | 430 /* make sure there is space for next character */ 431 if (cp + 1 >= el->el_line.limit) { 432 idx = (cp - el->el_line.buffer); 433 if (!ch_enlargebufs(el, 2)) 434 break; 435 cp = &el->el_line.buffer[idx]; 436 } 437 cp++; 438 if (el->el_flags & UNBUFFERED) 439 break; 440 if (cp[-1] == '\r' || cp[-1] == '\n') 441 break; 442 } |
443 if (num == -1) { 444 if (errno == EINTR) 445 cp = el->el_line.buffer; 446 el->el_errno = errno; 447 } |
|
427 428 el->el_line.cursor = el->el_line.lastchar = cp; 429 *cp = '\0'; | 448 449 el->el_line.cursor = el->el_line.lastchar = cp; 450 *cp = '\0'; |
430 if (nread) 431 *nread = el->el_line.cursor - el->el_line.buffer; 432 return (el->el_line.buffer); | 451 *nread = (int)(el->el_line.cursor - el->el_line.buffer); 452 goto done; |
433 } 434 435 436#ifdef FIONREAD 437 if (el->el_tty.t_mode == EX_IO && ma->level < 0) { 438 long chrs = 0; 439 440 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) & chrs); 441 if (chrs == 0) { 442 if (tty_rawmode(el) < 0) { | 453 } 454 455 456#ifdef FIONREAD 457 if (el->el_tty.t_mode == EX_IO && ma->level < 0) { 458 long chrs = 0; 459 460 (void) ioctl(el->el_infd, FIONREAD, (ioctl_t) & chrs); 461 if (chrs == 0) { 462 if (tty_rawmode(el) < 0) { |
443 if (nread) 444 *nread = 0; | 463 errno = 0; 464 *nread = 0; |
445 return (NULL); 446 } 447 } 448 } 449#endif /* FIONREAD */ 450 451 if ((el->el_flags & UNBUFFERED) == 0) 452 read_prepare(el); 453 454 if (el->el_flags & EDIT_DISABLED) { 455 char *cp; 456 size_t idx; | 465 return (NULL); 466 } 467 } 468 } 469#endif /* FIONREAD */ 470 471 if ((el->el_flags & UNBUFFERED) == 0) 472 read_prepare(el); 473 474 if (el->el_flags & EDIT_DISABLED) { 475 char *cp; 476 size_t idx; |
477 |
|
457 if ((el->el_flags & UNBUFFERED) == 0) 458 cp = el->el_line.buffer; 459 else 460 cp = el->el_line.lastchar; 461 | 478 if ((el->el_flags & UNBUFFERED) == 0) 479 cp = el->el_line.buffer; 480 else 481 cp = el->el_line.lastchar; 482 |
462 term__flush(); | 483 term__flush(el); |
463 | 484 |
464 while ((*el->el_read.read_char)(el, cp) == 1) { | 485 while ((num = (*el->el_read.read_char)(el, cp)) == 1) { |
465 /* make sure there is space next character */ 466 if (cp + 1 >= el->el_line.limit) { 467 idx = (cp - el->el_line.buffer); 468 if (!ch_enlargebufs(el, 2)) 469 break; 470 cp = &el->el_line.buffer[idx]; 471 } | 486 /* make sure there is space next character */ 487 if (cp + 1 >= el->el_line.limit) { 488 idx = (cp - el->el_line.buffer); 489 if (!ch_enlargebufs(el, 2)) 490 break; 491 cp = &el->el_line.buffer[idx]; 492 } |
472 if (*cp == 4) /* ought to be stty eof */ 473 break; | |
474 cp++; 475 crlf = cp[-1] == '\r' || cp[-1] == '\n'; 476 if (el->el_flags & UNBUFFERED) 477 break; 478 if (crlf) 479 break; 480 } 481 | 493 cp++; 494 crlf = cp[-1] == '\r' || cp[-1] == '\n'; 495 if (el->el_flags & UNBUFFERED) 496 break; 497 if (crlf) 498 break; 499 } 500 |
501 if (num == -1) { 502 if (errno == EINTR) 503 cp = el->el_line.buffer; 504 el->el_errno = errno; 505 } 506 |
|
482 el->el_line.cursor = el->el_line.lastchar = cp; 483 *cp = '\0'; | 507 el->el_line.cursor = el->el_line.lastchar = cp; 508 *cp = '\0'; |
484 if (nread) 485 *nread = el->el_line.cursor - el->el_line.buffer; 486 return (el->el_line.buffer); | 509 goto done; |
487 } 488 489 for (num = OKCMD; num == OKCMD;) { /* while still editing this 490 * line */ 491#ifdef DEBUG_EDIT 492 read_debug(el); 493#endif /* DEBUG_EDIT */ 494 /* if EOF or error */ 495 if ((num = read_getcmd(el, &cmdnum, &ch)) != OKCMD) { 496#ifdef DEBUG_READ 497 (void) fprintf(el->el_errfile, 498 "Returning from el_gets %d\n", num); 499#endif /* DEBUG_READ */ 500 break; 501 } | 510 } 511 512 for (num = OKCMD; num == OKCMD;) { /* while still editing this 513 * line */ 514#ifdef DEBUG_EDIT 515 read_debug(el); 516#endif /* DEBUG_EDIT */ 517 /* if EOF or error */ 518 if ((num = read_getcmd(el, &cmdnum, &ch)) != OKCMD) { 519#ifdef DEBUG_READ 520 (void) fprintf(el->el_errfile, 521 "Returning from el_gets %d\n", num); 522#endif /* DEBUG_READ */ 523 break; 524 } |
502 if ((unsigned int)cmdnum >= el->el_map.nfunc) { /* BUG CHECK command */ | 525 if (el->el_errno == EINTR) { 526 el->el_line.buffer[0] = '\0'; 527 el->el_line.lastchar = 528 el->el_line.cursor = el->el_line.buffer; 529 break; 530 } 531 if ((unsigned int)cmdnum >= (unsigned int)el->el_map.nfunc) { /* BUG CHECK command */ |
503#ifdef DEBUG_EDIT 504 (void) fprintf(el->el_errfile, 505 "ERROR: illegal command from key 0%o\r\n", ch); 506#endif /* DEBUG_EDIT */ 507 continue; /* try again */ 508 } 509 /* now do the real command */ 510#ifdef DEBUG_READ --- 65 unchanged lines hidden (view full) --- 576 else if (num == -1) { 577 *el->el_line.lastchar++ = CONTROL('d'); 578 el->el_line.cursor = el->el_line.lastchar; 579 num = 1; 580 } 581 break; 582 583 case CC_NEWLINE: /* normal end of line */ | 532#ifdef DEBUG_EDIT 533 (void) fprintf(el->el_errfile, 534 "ERROR: illegal command from key 0%o\r\n", ch); 535#endif /* DEBUG_EDIT */ 536 continue; /* try again */ 537 } 538 /* now do the real command */ 539#ifdef DEBUG_READ --- 65 unchanged lines hidden (view full) --- 605 else if (num == -1) { 606 *el->el_line.lastchar++ = CONTROL('d'); 607 el->el_line.cursor = el->el_line.lastchar; 608 num = 1; 609 } 610 break; 611 612 case CC_NEWLINE: /* normal end of line */ |
584 num = el->el_line.lastchar - el->el_line.buffer; | 613 num = (int)(el->el_line.lastchar - el->el_line.buffer); |
585 break; 586 587 case CC_FATAL: /* fatal error, reset to known state */ 588#ifdef DEBUG_READ 589 (void) fprintf(el->el_errfile, 590 "*** editor fatal ERROR ***\r\n\n"); 591#endif /* DEBUG_READ */ 592 /* put (real) cursor in a known place */ --- 4 unchanged lines hidden (view full) --- 597 598 case CC_ERROR: 599 default: /* functions we don't know about */ 600#ifdef DEBUG_READ 601 (void) fprintf(el->el_errfile, 602 "*** editor ERROR ***\r\n\n"); 603#endif /* DEBUG_READ */ 604 term_beep(el); | 614 break; 615 616 case CC_FATAL: /* fatal error, reset to known state */ 617#ifdef DEBUG_READ 618 (void) fprintf(el->el_errfile, 619 "*** editor fatal ERROR ***\r\n\n"); 620#endif /* DEBUG_READ */ 621 /* put (real) cursor in a known place */ --- 4 unchanged lines hidden (view full) --- 626 627 case CC_ERROR: 628 default: /* functions we don't know about */ 629#ifdef DEBUG_READ 630 (void) fprintf(el->el_errfile, 631 "*** editor ERROR ***\r\n\n"); 632#endif /* DEBUG_READ */ 633 term_beep(el); |
605 term__flush(); | 634 term__flush(el); |
606 break; 607 } 608 el->el_state.argument = 1; 609 el->el_state.doingarg = 0; 610 el->el_chared.c_vcmd.action = NOP; 611 if (el->el_flags & UNBUFFERED) 612 break; 613 } 614 | 635 break; 636 } 637 el->el_state.argument = 1; 638 el->el_state.doingarg = 0; 639 el->el_chared.c_vcmd.action = NOP; 640 if (el->el_flags & UNBUFFERED) 641 break; 642 } 643 |
615 term__flush(); /* flush any buffered output */ | 644 term__flush(el); /* flush any buffered output */ |
616 /* make sure the tty is set up correctly */ 617 if ((el->el_flags & UNBUFFERED) == 0) { 618 read_finish(el); | 645 /* make sure the tty is set up correctly */ 646 if ((el->el_flags & UNBUFFERED) == 0) { 647 read_finish(el); |
619 if (nread) 620 *nread = num; | 648 *nread = num != -1 ? num : 0; |
621 } else { | 649 } else { |
622 if (nread) 623 *nread = el->el_line.lastchar - el->el_line.buffer; | 650 *nread = (int)(el->el_line.lastchar - el->el_line.buffer); |
624 } | 651 } |
625 return (num ? el->el_line.buffer : NULL); | 652done: 653 if (*nread == 0) { 654 if (num == -1) { 655 *nread = -1; 656 errno = el->el_errno; 657 } 658 return NULL; 659 } else 660 return el->el_line.buffer; |
626} | 661} |