1 /* $NetBSD: readline.c,v 1.113 2014/10/18 08:33:23 snj Exp $ */ 2 3 /*- 4 * Copyright (c) 1997 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Jaromir Dolecek. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 #include "config.h" 33 #if !defined(lint) && !defined(SCCSID) 34 __RCSID("$NetBSD: readline.c,v 1.113 2014/10/18 08:33:23 snj Exp $"); 35 #endif /* not lint && not SCCSID */ 36 #include <sys/cdefs.h> 37 __FBSDID("$FreeBSD$"); 38 39 #include <sys/types.h> 40 #include <sys/stat.h> 41 #include <stdio.h> 42 #include <dirent.h> 43 #include <string.h> 44 #include <pwd.h> 45 #include <ctype.h> 46 #include <stdlib.h> 47 #include <unistd.h> 48 #include <limits.h> 49 #include <errno.h> 50 #include <fcntl.h> 51 #include <setjmp.h> 52 #include <vis.h> 53 54 #include "readline/readline.h" 55 #include "el.h" 56 #include "fcns.h" /* for EL_NUM_FCNS */ 57 #include "histedit.h" 58 #include "filecomplete.h" 59 60 void rl_prep_terminal(int); 61 void rl_deprep_terminal(void); 62 63 /* for rl_complete() */ 64 #define TAB '\r' 65 66 /* see comment at the #ifdef for sense of this */ 67 /* #define GDB_411_HACK */ 68 69 /* readline compatibility stuff - look at readline sources/documentation */ 70 /* to see what these variables mean */ 71 const char *rl_library_version = "EditLine wrapper"; 72 int rl_readline_version = RL_READLINE_VERSION; 73 static char empty[] = { '\0' }; 74 static char expand_chars[] = { ' ', '\t', '\n', '=', '(', '\0' }; 75 static char break_chars[] = { ' ', '\t', '\n', '"', '\\', '\'', '`', '@', '$', 76 '>', '<', '=', ';', '|', '&', '{', '(', '\0' }; 77 char *rl_readline_name = empty; 78 FILE *rl_instream = NULL; 79 FILE *rl_outstream = NULL; 80 int rl_point = 0; 81 int rl_end = 0; 82 char *rl_line_buffer = NULL; 83 VCPFunction *rl_linefunc = NULL; 84 int rl_done = 0; 85 VFunction *rl_event_hook = NULL; 86 KEYMAP_ENTRY_ARRAY emacs_standard_keymap, 87 emacs_meta_keymap, 88 emacs_ctlx_keymap; 89 /* 90 * The following is not implemented; we always catch signals in the 91 * libedit fashion: set handlers on entry to el_gets() and clear them 92 * on the way out. This simplistic approach works for most cases; if 93 * it does not work for your application, please let us know. 94 */ 95 int rl_catch_signals = 1; 96 int rl_catch_sigwinch = 1; 97 98 int history_base = 1; /* probably never subject to change */ 99 int history_length = 0; 100 int max_input_history = 0; 101 char history_expansion_char = '!'; 102 char history_subst_char = '^'; 103 char *history_no_expand_chars = expand_chars; 104 Function *history_inhibit_expansion_function = NULL; 105 char *history_arg_extract(int start, int end, const char *str); 106 107 int rl_inhibit_completion = 0; 108 int rl_attempted_completion_over = 0; 109 char *rl_basic_word_break_characters = break_chars; 110 char *rl_completer_word_break_characters = NULL; 111 char *rl_completer_quote_characters = NULL; 112 Function *rl_completion_entry_function = NULL; 113 char *(*rl_completion_word_break_hook)(void) = NULL; 114 CPPFunction *rl_attempted_completion_function = NULL; 115 Function *rl_pre_input_hook = NULL; 116 Function *rl_startup1_hook = NULL; 117 int (*rl_getc_function)(FILE *) = NULL; 118 char *rl_terminal_name = NULL; 119 int rl_already_prompted = 0; 120 int rl_filename_completion_desired = 0; 121 int rl_ignore_completion_duplicates = 0; 122 int readline_echoing_p = 1; 123 int _rl_print_completions_horizontally = 0; 124 VFunction *rl_redisplay_function = NULL; 125 Function *rl_startup_hook = NULL; 126 VFunction *rl_completion_display_matches_hook = NULL; 127 VFunction *rl_prep_term_function = (VFunction *)rl_prep_terminal; 128 VFunction *rl_deprep_term_function = (VFunction *)rl_deprep_terminal; 129 KEYMAP_ENTRY_ARRAY emacs_meta_keymap; 130 131 /* 132 * The current prompt string. 133 */ 134 char *rl_prompt = NULL; 135 /* 136 * This is set to character indicating type of completion being done by 137 * rl_complete_internal(); this is available for application completion 138 * functions. 139 */ 140 int rl_completion_type = 0; 141 142 /* 143 * If more than this number of items results from query for possible 144 * completions, we ask user if they are sure to really display the list. 145 */ 146 int rl_completion_query_items = 100; 147 148 /* 149 * List of characters which are word break characters, but should be left 150 * in the parsed text when it is passed to the completion function. 151 * Shell uses this to help determine what kind of completing to do. 152 */ 153 char *rl_special_prefixes = NULL; 154 155 /* 156 * This is the character appended to the completed words if at the end of 157 * the line. Default is ' ' (a space). 158 */ 159 int rl_completion_append_character = ' '; 160 161 /* stuff below is used internally by libedit for readline emulation */ 162 163 static History *h = NULL; 164 static EditLine *e = NULL; 165 static Function *map[256]; 166 static jmp_buf topbuf; 167 168 /* internal functions */ 169 static unsigned char _el_rl_complete(EditLine *, int); 170 static unsigned char _el_rl_tstp(EditLine *, int); 171 static char *_get_prompt(EditLine *); 172 static int _getc_function(EditLine *, char *); 173 static HIST_ENTRY *_move_history(int); 174 static int _history_expand_command(const char *, size_t, size_t, 175 char **); 176 static char *_rl_compat_sub(const char *, const char *, 177 const char *, int); 178 static int _rl_event_read_char(EditLine *, char *); 179 static void _rl_update_pos(void); 180 181 182 /* ARGSUSED */ 183 static char * 184 _get_prompt(EditLine *el __attribute__((__unused__))) 185 { 186 rl_already_prompted = 1; 187 return rl_prompt; 188 } 189 190 191 /* 192 * generic function for moving around history 193 */ 194 static HIST_ENTRY * 195 _move_history(int op) 196 { 197 HistEvent ev; 198 static HIST_ENTRY rl_he; 199 200 if (history(h, &ev, op) != 0) 201 return NULL; 202 203 rl_he.line = ev.str; 204 rl_he.data = NULL; 205 206 return &rl_he; 207 } 208 209 210 /* 211 * read one key from user defined input function 212 */ 213 static int 214 /*ARGSUSED*/ 215 _getc_function(EditLine *el __attribute__((__unused__)), char *c) 216 { 217 int i; 218 219 i = (*rl_getc_function)(NULL); 220 if (i == -1) 221 return 0; 222 *c = (char)i; 223 return 1; 224 } 225 226 static void 227 _resize_fun(EditLine *el, void *a) 228 { 229 const LineInfo *li; 230 char **ap = a; 231 232 li = el_line(el); 233 /* a cheesy way to get rid of const cast. */ 234 *ap = memchr(li->buffer, *li->buffer, (size_t)1); 235 } 236 237 static const char * 238 _default_history_file(void) 239 { 240 struct passwd *p; 241 static char *path; 242 size_t len; 243 244 if (path) 245 return path; 246 247 if ((p = getpwuid(getuid())) == NULL) 248 return NULL; 249 250 len = strlen(p->pw_dir) + sizeof("/.history"); 251 if ((path = malloc(len)) == NULL) 252 return NULL; 253 254 (void)snprintf(path, len, "%s/.history", p->pw_dir); 255 return path; 256 } 257 258 /* 259 * READLINE compatibility stuff 260 */ 261 262 /* 263 * Set the prompt 264 */ 265 int 266 rl_set_prompt(const char *prompt) 267 { 268 char *p; 269 270 if (!prompt) 271 prompt = ""; 272 if (rl_prompt != NULL && strcmp(rl_prompt, prompt) == 0) 273 return 0; 274 if (rl_prompt) 275 el_free(rl_prompt); 276 rl_prompt = strdup(prompt); 277 if (rl_prompt == NULL) 278 return -1; 279 280 while ((p = strchr(rl_prompt, RL_PROMPT_END_IGNORE)) != NULL) 281 *p = RL_PROMPT_START_IGNORE; 282 283 return 0; 284 } 285 286 /* 287 * initialize rl compat stuff 288 */ 289 int 290 rl_initialize(void) 291 { 292 HistEvent ev; 293 int editmode = 1; 294 struct termios t; 295 296 if (e != NULL) 297 el_end(e); 298 if (h != NULL) 299 history_end(h); 300 301 if (!rl_instream) 302 rl_instream = stdin; 303 if (!rl_outstream) 304 rl_outstream = stdout; 305 306 /* 307 * See if we don't really want to run the editor 308 */ 309 if (tcgetattr(fileno(rl_instream), &t) != -1 && (t.c_lflag & ECHO) == 0) 310 editmode = 0; 311 312 e = el_init(rl_readline_name, rl_instream, rl_outstream, stderr); 313 314 if (!editmode) 315 el_set(e, EL_EDITMODE, 0); 316 317 h = history_init(); 318 if (!e || !h) 319 return -1; 320 321 history(h, &ev, H_SETSIZE, INT_MAX); /* unlimited */ 322 history_length = 0; 323 max_input_history = INT_MAX; 324 el_set(e, EL_HIST, history, h); 325 326 /* Setup resize function */ 327 el_set(e, EL_RESIZE, _resize_fun, &rl_line_buffer); 328 329 /* setup getc function if valid */ 330 if (rl_getc_function) 331 el_set(e, EL_GETCFN, _getc_function); 332 333 /* for proper prompt printing in readline() */ 334 if (rl_set_prompt("") == -1) { 335 history_end(h); 336 el_end(e); 337 return -1; 338 } 339 el_set(e, EL_PROMPT, _get_prompt, RL_PROMPT_START_IGNORE); 340 el_set(e, EL_SIGNAL, rl_catch_signals); 341 342 /* set default mode to "emacs"-style and read setting afterwards */ 343 /* so this can be overridden */ 344 el_set(e, EL_EDITOR, "emacs"); 345 if (rl_terminal_name != NULL) 346 el_set(e, EL_TERMINAL, rl_terminal_name); 347 else 348 el_get(e, EL_TERMINAL, &rl_terminal_name); 349 350 /* 351 * Word completion - this has to go AFTER rebinding keys 352 * to emacs-style. 353 */ 354 el_set(e, EL_ADDFN, "rl_complete", 355 "ReadLine compatible completion function", 356 _el_rl_complete); 357 el_set(e, EL_BIND, "^I", "rl_complete", NULL); 358 359 /* 360 * Send TSTP when ^Z is pressed. 361 */ 362 el_set(e, EL_ADDFN, "rl_tstp", 363 "ReadLine compatible suspend function", 364 _el_rl_tstp); 365 el_set(e, EL_BIND, "^Z", "rl_tstp", NULL); 366 367 /* read settings from configuration file */ 368 el_source(e, NULL); 369 370 /* 371 * Unfortunately, some applications really do use rl_point 372 * and rl_line_buffer directly. 373 */ 374 _resize_fun(e, &rl_line_buffer); 375 _rl_update_pos(); 376 377 if (rl_startup_hook) 378 (*rl_startup_hook)(NULL, 0); 379 380 return 0; 381 } 382 383 384 /* 385 * read one line from input stream and return it, chomping 386 * trailing newline (if there is any) 387 */ 388 char * 389 readline(const char *p) 390 { 391 HistEvent ev; 392 const char * volatile prompt = p; 393 int count; 394 const char *ret; 395 char *buf; 396 static int used_event_hook; 397 398 if (e == NULL || h == NULL) 399 rl_initialize(); 400 401 rl_done = 0; 402 403 (void)setjmp(topbuf); 404 405 /* update prompt accordingly to what has been passed */ 406 if (rl_set_prompt(prompt) == -1) 407 return NULL; 408 409 if (rl_pre_input_hook) 410 (*rl_pre_input_hook)(NULL, 0); 411 412 if (rl_event_hook && !(e->el_flags&NO_TTY)) { 413 el_set(e, EL_GETCFN, _rl_event_read_char); 414 used_event_hook = 1; 415 } 416 417 if (!rl_event_hook && used_event_hook) { 418 el_set(e, EL_GETCFN, EL_BUILTIN_GETCFN); 419 used_event_hook = 0; 420 } 421 422 rl_already_prompted = 0; 423 424 /* get one line from input stream */ 425 ret = el_gets(e, &count); 426 427 if (ret && count > 0) { 428 int lastidx; 429 430 buf = strdup(ret); 431 if (buf == NULL) 432 return NULL; 433 lastidx = count - 1; 434 if (buf[lastidx] == '\n') 435 buf[lastidx] = '\0'; 436 } else 437 buf = NULL; 438 439 history(h, &ev, H_GETSIZE); 440 history_length = ev.num; 441 442 return buf; 443 } 444 445 /* 446 * history functions 447 */ 448 449 /* 450 * is normally called before application starts to use 451 * history expansion functions 452 */ 453 void 454 using_history(void) 455 { 456 if (h == NULL || e == NULL) 457 rl_initialize(); 458 } 459 460 461 /* 462 * substitute ``what'' with ``with'', returning resulting string; if 463 * globally == 1, substitutes all occurrences of what, otherwise only the 464 * first one 465 */ 466 static char * 467 _rl_compat_sub(const char *str, const char *what, const char *with, 468 int globally) 469 { 470 const char *s; 471 char *r, *result; 472 size_t len, with_len, what_len; 473 474 len = strlen(str); 475 with_len = strlen(with); 476 what_len = strlen(what); 477 478 /* calculate length we need for result */ 479 s = str; 480 while (*s) { 481 if (*s == *what && !strncmp(s, what, what_len)) { 482 len += with_len - what_len; 483 if (!globally) 484 break; 485 s += what_len; 486 } else 487 s++; 488 } 489 r = result = el_malloc((len + 1) * sizeof(*r)); 490 if (result == NULL) 491 return NULL; 492 s = str; 493 while (*s) { 494 if (*s == *what && !strncmp(s, what, what_len)) { 495 (void)strncpy(r, with, with_len); 496 r += with_len; 497 s += what_len; 498 if (!globally) { 499 (void)strcpy(r, s); 500 return result; 501 } 502 } else 503 *r++ = *s++; 504 } 505 *r = '\0'; 506 return result; 507 } 508 509 static char *last_search_pat; /* last !?pat[?] search pattern */ 510 static char *last_search_match; /* last !?pat[?] that matched */ 511 512 const char * 513 get_history_event(const char *cmd, int *cindex, int qchar) 514 { 515 int idx, sign, sub, num, begin, ret; 516 size_t len; 517 char *pat; 518 const char *rptr; 519 HistEvent ev; 520 521 idx = *cindex; 522 if (cmd[idx++] != history_expansion_char) 523 return NULL; 524 525 /* find out which event to take */ 526 if (cmd[idx] == history_expansion_char || cmd[idx] == '\0') { 527 if (history(h, &ev, H_FIRST) != 0) 528 return NULL; 529 *cindex = cmd[idx]? (idx + 1):idx; 530 return ev.str; 531 } 532 sign = 0; 533 if (cmd[idx] == '-') { 534 sign = 1; 535 idx++; 536 } 537 538 if ('0' <= cmd[idx] && cmd[idx] <= '9') { 539 HIST_ENTRY *rl_he; 540 541 num = 0; 542 while (cmd[idx] && '0' <= cmd[idx] && cmd[idx] <= '9') { 543 num = num * 10 + cmd[idx] - '0'; 544 idx++; 545 } 546 if (sign) 547 num = history_length - num + 1; 548 549 if (!(rl_he = history_get(num))) 550 return NULL; 551 552 *cindex = idx; 553 return rl_he->line; 554 } 555 sub = 0; 556 if (cmd[idx] == '?') { 557 sub = 1; 558 idx++; 559 } 560 begin = idx; 561 while (cmd[idx]) { 562 if (cmd[idx] == '\n') 563 break; 564 if (sub && cmd[idx] == '?') 565 break; 566 if (!sub && (cmd[idx] == ':' || cmd[idx] == ' ' 567 || cmd[idx] == '\t' || cmd[idx] == qchar)) 568 break; 569 idx++; 570 } 571 len = (size_t)idx - (size_t)begin; 572 if (sub && cmd[idx] == '?') 573 idx++; 574 if (sub && len == 0 && last_search_pat && *last_search_pat) 575 pat = last_search_pat; 576 else if (len == 0) 577 return NULL; 578 else { 579 if ((pat = el_malloc((len + 1) * sizeof(*pat))) == NULL) 580 return NULL; 581 (void)strncpy(pat, cmd + begin, len); 582 pat[len] = '\0'; 583 } 584 585 if (history(h, &ev, H_CURR) != 0) { 586 if (pat != last_search_pat) 587 el_free(pat); 588 return NULL; 589 } 590 num = ev.num; 591 592 if (sub) { 593 if (pat != last_search_pat) { 594 if (last_search_pat) 595 el_free(last_search_pat); 596 last_search_pat = pat; 597 } 598 ret = history_search(pat, -1); 599 } else 600 ret = history_search_prefix(pat, -1); 601 602 if (ret == -1) { 603 /* restore to end of list on failed search */ 604 history(h, &ev, H_FIRST); 605 (void)fprintf(rl_outstream, "%s: Event not found\n", pat); 606 if (pat != last_search_pat) 607 el_free(pat); 608 return NULL; 609 } 610 611 if (sub && len) { 612 if (last_search_match && last_search_match != pat) 613 el_free(last_search_match); 614 last_search_match = pat; 615 } 616 617 if (pat != last_search_pat) 618 el_free(pat); 619 620 if (history(h, &ev, H_CURR) != 0) 621 return NULL; 622 *cindex = idx; 623 rptr = ev.str; 624 625 /* roll back to original position */ 626 (void)history(h, &ev, H_SET, num); 627 628 return rptr; 629 } 630 631 /* 632 * the real function doing history expansion - takes as argument command 633 * to do and data upon which the command should be executed 634 * does expansion the way I've understood readline documentation 635 * 636 * returns 0 if data was not modified, 1 if it was and 2 if the string 637 * should be only printed and not executed; in case of error, 638 * returns -1 and *result points to NULL 639 * it's the caller's responsibility to free() the string returned in *result 640 */ 641 static int 642 _history_expand_command(const char *command, size_t offs, size_t cmdlen, 643 char **result) 644 { 645 char *tmp, *search = NULL, *aptr; 646 const char *ptr, *cmd; 647 static char *from = NULL, *to = NULL; 648 int start, end, idx, has_mods = 0; 649 int p_on = 0, g_on = 0; 650 651 *result = NULL; 652 aptr = NULL; 653 ptr = NULL; 654 655 /* First get event specifier */ 656 idx = 0; 657 658 if (strchr(":^*$", command[offs + 1])) { 659 char str[4]; 660 /* 661 * "!:" is shorthand for "!!:". 662 * "!^", "!*" and "!$" are shorthand for 663 * "!!:^", "!!:*" and "!!:$" respectively. 664 */ 665 str[0] = str[1] = '!'; 666 str[2] = '0'; 667 ptr = get_history_event(str, &idx, 0); 668 idx = (command[offs + 1] == ':')? 1:0; 669 has_mods = 1; 670 } else { 671 if (command[offs + 1] == '#') { 672 /* use command so far */ 673 if ((aptr = el_malloc((offs + 1) * sizeof(*aptr))) 674 == NULL) 675 return -1; 676 (void)strncpy(aptr, command, offs); 677 aptr[offs] = '\0'; 678 idx = 1; 679 } else { 680 int qchar; 681 682 qchar = (offs > 0 && command[offs - 1] == '"')? '"':0; 683 ptr = get_history_event(command + offs, &idx, qchar); 684 } 685 has_mods = command[offs + (size_t)idx] == ':'; 686 } 687 688 if (ptr == NULL && aptr == NULL) 689 return -1; 690 691 if (!has_mods) { 692 *result = strdup(aptr ? aptr : ptr); 693 if (aptr) 694 el_free(aptr); 695 if (*result == NULL) 696 return -1; 697 return 1; 698 } 699 700 cmd = command + offs + idx + 1; 701 702 /* Now parse any word designators */ 703 704 if (*cmd == '%') /* last word matched by ?pat? */ 705 tmp = strdup(last_search_match? last_search_match:""); 706 else if (strchr("^*$-0123456789", *cmd)) { 707 start = end = -1; 708 if (*cmd == '^') 709 start = end = 1, cmd++; 710 else if (*cmd == '$') 711 start = -1, cmd++; 712 else if (*cmd == '*') 713 start = 1, cmd++; 714 else if (*cmd == '-' || isdigit((unsigned char) *cmd)) { 715 start = 0; 716 while (*cmd && '0' <= *cmd && *cmd <= '9') 717 start = start * 10 + *cmd++ - '0'; 718 719 if (*cmd == '-') { 720 if (isdigit((unsigned char) cmd[1])) { 721 cmd++; 722 end = 0; 723 while (*cmd && '0' <= *cmd && *cmd <= '9') 724 end = end * 10 + *cmd++ - '0'; 725 } else if (cmd[1] == '$') { 726 cmd += 2; 727 end = -1; 728 } else { 729 cmd++; 730 end = -2; 731 } 732 } else if (*cmd == '*') 733 end = -1, cmd++; 734 else 735 end = start; 736 } 737 tmp = history_arg_extract(start, end, aptr? aptr:ptr); 738 if (tmp == NULL) { 739 (void)fprintf(rl_outstream, "%s: Bad word specifier", 740 command + offs + idx); 741 if (aptr) 742 el_free(aptr); 743 return -1; 744 } 745 } else 746 tmp = strdup(aptr? aptr:ptr); 747 748 if (aptr) 749 el_free(aptr); 750 751 if (*cmd == '\0' || ((size_t)(cmd - (command + offs)) >= cmdlen)) { 752 *result = tmp; 753 return 1; 754 } 755 756 for (; *cmd; cmd++) { 757 if (*cmd == ':') 758 continue; 759 else if (*cmd == 'h') { /* remove trailing path */ 760 if ((aptr = strrchr(tmp, '/')) != NULL) 761 *aptr = '\0'; 762 } else if (*cmd == 't') { /* remove leading path */ 763 if ((aptr = strrchr(tmp, '/')) != NULL) { 764 aptr = strdup(aptr + 1); 765 el_free(tmp); 766 tmp = aptr; 767 } 768 } else if (*cmd == 'r') { /* remove trailing suffix */ 769 if ((aptr = strrchr(tmp, '.')) != NULL) 770 *aptr = '\0'; 771 } else if (*cmd == 'e') { /* remove all but suffix */ 772 if ((aptr = strrchr(tmp, '.')) != NULL) { 773 aptr = strdup(aptr); 774 el_free(tmp); 775 tmp = aptr; 776 } 777 } else if (*cmd == 'p') /* print only */ 778 p_on = 1; 779 else if (*cmd == 'g') 780 g_on = 2; 781 else if (*cmd == 's' || *cmd == '&') { 782 char *what, *with, delim; 783 size_t len, from_len; 784 size_t size; 785 786 if (*cmd == '&' && (from == NULL || to == NULL)) 787 continue; 788 else if (*cmd == 's') { 789 delim = *(++cmd), cmd++; 790 size = 16; 791 what = el_realloc(from, size * sizeof(*what)); 792 if (what == NULL) { 793 el_free(from); 794 el_free(tmp); 795 return 0; 796 } 797 len = 0; 798 for (; *cmd && *cmd != delim; cmd++) { 799 if (*cmd == '\\' && cmd[1] == delim) 800 cmd++; 801 if (len >= size) { 802 char *nwhat; 803 nwhat = el_realloc(what, 804 (size <<= 1) * 805 sizeof(*nwhat)); 806 if (nwhat == NULL) { 807 el_free(what); 808 el_free(tmp); 809 return 0; 810 } 811 what = nwhat; 812 } 813 what[len++] = *cmd; 814 } 815 what[len] = '\0'; 816 from = what; 817 if (*what == '\0') { 818 el_free(what); 819 if (search) { 820 from = strdup(search); 821 if (from == NULL) { 822 el_free(tmp); 823 return 0; 824 } 825 } else { 826 from = NULL; 827 el_free(tmp); 828 return -1; 829 } 830 } 831 cmd++; /* shift after delim */ 832 if (!*cmd) 833 continue; 834 835 size = 16; 836 with = el_realloc(to, size * sizeof(*with)); 837 if (with == NULL) { 838 el_free(to); 839 el_free(tmp); 840 return -1; 841 } 842 len = 0; 843 from_len = strlen(from); 844 for (; *cmd && *cmd != delim; cmd++) { 845 if (len + from_len + 1 >= size) { 846 char *nwith; 847 size += from_len + 1; 848 nwith = el_realloc(with, 849 size * sizeof(*nwith)); 850 if (nwith == NULL) { 851 el_free(with); 852 el_free(tmp); 853 return -1; 854 } 855 with = nwith; 856 } 857 if (*cmd == '&') { 858 /* safe */ 859 (void)strcpy(&with[len], from); 860 len += from_len; 861 continue; 862 } 863 if (*cmd == '\\' 864 && (*(cmd + 1) == delim 865 || *(cmd + 1) == '&')) 866 cmd++; 867 with[len++] = *cmd; 868 } 869 with[len] = '\0'; 870 to = with; 871 } 872 873 aptr = _rl_compat_sub(tmp, from, to, g_on); 874 if (aptr) { 875 el_free(tmp); 876 tmp = aptr; 877 } 878 g_on = 0; 879 } 880 } 881 *result = tmp; 882 return p_on? 2:1; 883 } 884 885 886 /* 887 * csh-style history expansion 888 */ 889 int 890 history_expand(char *str, char **output) 891 { 892 int ret = 0; 893 size_t idx, i, size; 894 char *tmp, *result; 895 896 if (h == NULL || e == NULL) 897 rl_initialize(); 898 899 if (history_expansion_char == 0) { 900 *output = strdup(str); 901 return 0; 902 } 903 904 *output = NULL; 905 if (str[0] == history_subst_char) { 906 /* ^foo^foo2^ is equivalent to !!:s^foo^foo2^ */ 907 *output = el_malloc((strlen(str) + 4 + 1) * sizeof(**output)); 908 if (*output == NULL) 909 return 0; 910 (*output)[0] = (*output)[1] = history_expansion_char; 911 (*output)[2] = ':'; 912 (*output)[3] = 's'; 913 (void)strcpy((*output) + 4, str); 914 str = *output; 915 } else { 916 *output = strdup(str); 917 if (*output == NULL) 918 return 0; 919 } 920 921 #define ADD_STRING(what, len, fr) \ 922 { \ 923 if (idx + len + 1 > size) { \ 924 char *nresult = el_realloc(result, \ 925 (size += len + 1) * sizeof(*nresult)); \ 926 if (nresult == NULL) { \ 927 el_free(*output); \ 928 if (/*CONSTCOND*/fr) \ 929 el_free(tmp); \ 930 return 0; \ 931 } \ 932 result = nresult; \ 933 } \ 934 (void)strncpy(&result[idx], what, len); \ 935 idx += len; \ 936 result[idx] = '\0'; \ 937 } 938 939 result = NULL; 940 size = idx = 0; 941 tmp = NULL; 942 for (i = 0; str[i];) { 943 int qchar, loop_again; 944 size_t len, start, j; 945 946 qchar = 0; 947 loop_again = 1; 948 start = j = i; 949 loop: 950 for (; str[j]; j++) { 951 if (str[j] == '\\' && 952 str[j + 1] == history_expansion_char) { 953 (void)strcpy(&str[j], &str[j + 1]); 954 continue; 955 } 956 if (!loop_again) { 957 if (isspace((unsigned char) str[j]) 958 || str[j] == qchar) 959 break; 960 } 961 if (str[j] == history_expansion_char 962 && !strchr(history_no_expand_chars, str[j + 1]) 963 && (!history_inhibit_expansion_function || 964 (*history_inhibit_expansion_function)(str, 965 (int)j) == 0)) 966 break; 967 } 968 969 if (str[j] && loop_again) { 970 i = j; 971 qchar = (j > 0 && str[j - 1] == '"' )? '"':0; 972 j++; 973 if (str[j] == history_expansion_char) 974 j++; 975 loop_again = 0; 976 goto loop; 977 } 978 len = i - start; 979 ADD_STRING(&str[start], len, 0); 980 981 if (str[i] == '\0' || str[i] != history_expansion_char) { 982 len = j - i; 983 ADD_STRING(&str[i], len, 0); 984 if (start == 0) 985 ret = 0; 986 else 987 ret = 1; 988 break; 989 } 990 ret = _history_expand_command (str, i, (j - i), &tmp); 991 if (ret > 0 && tmp) { 992 len = strlen(tmp); 993 ADD_STRING(tmp, len, 1); 994 } 995 if (tmp) { 996 el_free(tmp); 997 tmp = NULL; 998 } 999 i = j; 1000 } 1001 1002 /* ret is 2 for "print only" option */ 1003 if (ret == 2) { 1004 add_history(result); 1005 #ifdef GDB_411_HACK 1006 /* gdb 4.11 has been shipped with readline, where */ 1007 /* history_expand() returned -1 when the line */ 1008 /* should not be executed; in readline 2.1+ */ 1009 /* it should return 2 in such a case */ 1010 ret = -1; 1011 #endif 1012 } 1013 el_free(*output); 1014 *output = result; 1015 1016 return ret; 1017 } 1018 1019 /* 1020 * Return a string consisting of arguments of "str" from "start" to "end". 1021 */ 1022 char * 1023 history_arg_extract(int start, int end, const char *str) 1024 { 1025 size_t i, len, max; 1026 char **arr, *result = NULL; 1027 1028 arr = history_tokenize(str); 1029 if (!arr) 1030 return NULL; 1031 if (arr && *arr == NULL) 1032 goto out; 1033 1034 for (max = 0; arr[max]; max++) 1035 continue; 1036 max--; 1037 1038 if (start == '$') 1039 start = (int)max; 1040 if (end == '$') 1041 end = (int)max; 1042 if (end < 0) 1043 end = (int)max + end + 1; 1044 if (start < 0) 1045 start = end; 1046 1047 if (start < 0 || end < 0 || (size_t)start > max || 1048 (size_t)end > max || start > end) 1049 goto out; 1050 1051 for (i = (size_t)start, len = 0; i <= (size_t)end; i++) 1052 len += strlen(arr[i]) + 1; 1053 len++; 1054 result = el_malloc(len * sizeof(*result)); 1055 if (result == NULL) 1056 goto out; 1057 1058 for (i = (size_t)start, len = 0; i <= (size_t)end; i++) { 1059 (void)strcpy(result + len, arr[i]); 1060 len += strlen(arr[i]); 1061 if (i < (size_t)end) 1062 result[len++] = ' '; 1063 } 1064 result[len] = '\0'; 1065 1066 out: 1067 for (i = 0; arr[i]; i++) 1068 el_free(arr[i]); 1069 el_free(arr); 1070 1071 return result; 1072 } 1073 1074 /* 1075 * Parse the string into individual tokens, 1076 * similar to how shell would do it. 1077 */ 1078 char ** 1079 history_tokenize(const char *str) 1080 { 1081 int size = 1, idx = 0, i, start; 1082 size_t len; 1083 char **result = NULL, *temp, delim = '\0'; 1084 1085 for (i = 0; str[i];) { 1086 while (isspace((unsigned char) str[i])) 1087 i++; 1088 start = i; 1089 for (; str[i];) { 1090 if (str[i] == '\\') { 1091 if (str[i+1] != '\0') 1092 i++; 1093 } else if (str[i] == delim) 1094 delim = '\0'; 1095 else if (!delim && 1096 (isspace((unsigned char) str[i]) || 1097 strchr("()<>;&|$", str[i]))) 1098 break; 1099 else if (!delim && strchr("'`\"", str[i])) 1100 delim = str[i]; 1101 if (str[i]) 1102 i++; 1103 } 1104 1105 if (idx + 2 >= size) { 1106 char **nresult; 1107 size <<= 1; 1108 nresult = el_realloc(result, (size_t)size * sizeof(*nresult)); 1109 if (nresult == NULL) { 1110 el_free(result); 1111 return NULL; 1112 } 1113 result = nresult; 1114 } 1115 len = (size_t)i - (size_t)start; 1116 temp = el_malloc((size_t)(len + 1) * sizeof(*temp)); 1117 if (temp == NULL) { 1118 for (i = 0; i < idx; i++) 1119 el_free(result[i]); 1120 el_free(result); 1121 return NULL; 1122 } 1123 (void)strncpy(temp, &str[start], len); 1124 temp[len] = '\0'; 1125 result[idx++] = temp; 1126 result[idx] = NULL; 1127 if (str[i]) 1128 i++; 1129 } 1130 return result; 1131 } 1132 1133 1134 /* 1135 * limit size of history record to ``max'' events 1136 */ 1137 void 1138 stifle_history(int max) 1139 { 1140 HistEvent ev; 1141 1142 if (h == NULL || e == NULL) 1143 rl_initialize(); 1144 1145 if (history(h, &ev, H_SETSIZE, max) == 0) 1146 max_input_history = max; 1147 } 1148 1149 1150 /* 1151 * "unlimit" size of history - set the limit to maximum allowed int value 1152 */ 1153 int 1154 unstifle_history(void) 1155 { 1156 HistEvent ev; 1157 int omax; 1158 1159 history(h, &ev, H_SETSIZE, INT_MAX); 1160 omax = max_input_history; 1161 max_input_history = INT_MAX; 1162 return omax; /* some value _must_ be returned */ 1163 } 1164 1165 1166 int 1167 history_is_stifled(void) 1168 { 1169 1170 /* cannot return true answer */ 1171 return max_input_history != INT_MAX; 1172 } 1173 1174 static const char _history_tmp_template[] = "/tmp/.historyXXXXXX"; 1175 1176 int 1177 history_truncate_file (const char *filename, int nlines) 1178 { 1179 int ret = 0; 1180 FILE *fp, *tp; 1181 char template[sizeof(_history_tmp_template)]; 1182 char buf[4096]; 1183 int fd; 1184 char *cp; 1185 off_t off; 1186 int count = 0; 1187 ssize_t left = 0; 1188 1189 if (filename == NULL && (filename = _default_history_file()) == NULL) 1190 return errno; 1191 if ((fp = fopen(filename, "r+")) == NULL) 1192 return errno; 1193 strcpy(template, _history_tmp_template); 1194 if ((fd = mkstemp(template)) == -1) { 1195 ret = errno; 1196 goto out1; 1197 } 1198 1199 if ((tp = fdopen(fd, "r+")) == NULL) { 1200 close(fd); 1201 ret = errno; 1202 goto out2; 1203 } 1204 1205 for(;;) { 1206 if (fread(buf, sizeof(buf), (size_t)1, fp) != 1) { 1207 if (ferror(fp)) { 1208 ret = errno; 1209 break; 1210 } 1211 if (fseeko(fp, (off_t)sizeof(buf) * count, SEEK_SET) == 1212 (off_t)-1) { 1213 ret = errno; 1214 break; 1215 } 1216 left = (ssize_t)fread(buf, (size_t)1, sizeof(buf), fp); 1217 if (ferror(fp)) { 1218 ret = errno; 1219 break; 1220 } 1221 if (left == 0) { 1222 count--; 1223 left = sizeof(buf); 1224 } else if (fwrite(buf, (size_t)left, (size_t)1, tp) 1225 != 1) { 1226 ret = errno; 1227 break; 1228 } 1229 fflush(tp); 1230 break; 1231 } 1232 if (fwrite(buf, sizeof(buf), (size_t)1, tp) != 1) { 1233 ret = errno; 1234 break; 1235 } 1236 count++; 1237 } 1238 if (ret) 1239 goto out3; 1240 cp = buf + left - 1; 1241 if(*cp != '\n') 1242 cp++; 1243 for(;;) { 1244 while (--cp >= buf) { 1245 if (*cp == '\n') { 1246 if (--nlines == 0) { 1247 if (++cp >= buf + sizeof(buf)) { 1248 count++; 1249 cp = buf; 1250 } 1251 break; 1252 } 1253 } 1254 } 1255 if (nlines <= 0 || count == 0) 1256 break; 1257 count--; 1258 if (fseeko(tp, (off_t)sizeof(buf) * count, SEEK_SET) < 0) { 1259 ret = errno; 1260 break; 1261 } 1262 if (fread(buf, sizeof(buf), (size_t)1, tp) != 1) { 1263 if (ferror(tp)) { 1264 ret = errno; 1265 break; 1266 } 1267 ret = EAGAIN; 1268 break; 1269 } 1270 cp = buf + sizeof(buf); 1271 } 1272 1273 if (ret || nlines > 0) 1274 goto out3; 1275 1276 if (fseeko(fp, (off_t)0, SEEK_SET) == (off_t)-1) { 1277 ret = errno; 1278 goto out3; 1279 } 1280 1281 if (fseeko(tp, (off_t)sizeof(buf) * count + (cp - buf), SEEK_SET) == 1282 (off_t)-1) { 1283 ret = errno; 1284 goto out3; 1285 } 1286 1287 for(;;) { 1288 if ((left = (ssize_t)fread(buf, (size_t)1, sizeof(buf), tp)) == 0) { 1289 if (ferror(fp)) 1290 ret = errno; 1291 break; 1292 } 1293 if (fwrite(buf, (size_t)left, (size_t)1, fp) != 1) { 1294 ret = errno; 1295 break; 1296 } 1297 } 1298 fflush(fp); 1299 if((off = ftello(fp)) > 0) 1300 (void)ftruncate(fileno(fp), off); 1301 out3: 1302 fclose(tp); 1303 out2: 1304 unlink(template); 1305 out1: 1306 fclose(fp); 1307 1308 return ret; 1309 } 1310 1311 1312 /* 1313 * read history from a file given 1314 */ 1315 int 1316 read_history(const char *filename) 1317 { 1318 HistEvent ev; 1319 1320 if (h == NULL || e == NULL) 1321 rl_initialize(); 1322 if (filename == NULL && (filename = _default_history_file()) == NULL) 1323 return errno; 1324 return history(h, &ev, H_LOAD, filename) == -1 ? 1325 (errno ? errno : EINVAL) : 0; 1326 } 1327 1328 1329 /* 1330 * write history to a file given 1331 */ 1332 int 1333 write_history(const char *filename) 1334 { 1335 HistEvent ev; 1336 1337 if (h == NULL || e == NULL) 1338 rl_initialize(); 1339 if (filename == NULL && (filename = _default_history_file()) == NULL) 1340 return errno; 1341 return history(h, &ev, H_SAVE, filename) == -1 ? 1342 (errno ? errno : EINVAL) : 0; 1343 } 1344 1345 1346 /* 1347 * returns history ``num''th event 1348 * 1349 * returned pointer points to static variable 1350 */ 1351 HIST_ENTRY * 1352 history_get(int num) 1353 { 1354 static HIST_ENTRY she; 1355 HistEvent ev; 1356 int curr_num; 1357 1358 if (h == NULL || e == NULL) 1359 rl_initialize(); 1360 1361 /* save current position */ 1362 if (history(h, &ev, H_CURR) != 0) 1363 return NULL; 1364 curr_num = ev.num; 1365 1366 /* start from the oldest */ 1367 if (history(h, &ev, H_LAST) != 0) 1368 return NULL; /* error */ 1369 1370 /* look forwards for event matching specified offset */ 1371 if (history(h, &ev, H_NEXT_EVDATA, num, &she.data)) 1372 return NULL; 1373 1374 she.line = ev.str; 1375 1376 /* restore pointer to where it was */ 1377 (void)history(h, &ev, H_SET, curr_num); 1378 1379 return &she; 1380 } 1381 1382 1383 /* 1384 * add the line to history table 1385 */ 1386 int 1387 add_history(const char *line) 1388 { 1389 HistEvent ev; 1390 1391 if (line == NULL) 1392 return 0; 1393 1394 if (h == NULL || e == NULL) 1395 rl_initialize(); 1396 1397 (void)history(h, &ev, H_ENTER, line); 1398 if (history(h, &ev, H_GETSIZE) == 0) 1399 history_length = ev.num; 1400 1401 return !(history_length > 0); /* return 0 if all is okay */ 1402 } 1403 1404 1405 /* 1406 * remove the specified entry from the history list and return it. 1407 */ 1408 HIST_ENTRY * 1409 remove_history(int num) 1410 { 1411 HIST_ENTRY *he; 1412 HistEvent ev; 1413 1414 if (h == NULL || e == NULL) 1415 rl_initialize(); 1416 1417 if ((he = el_malloc(sizeof(*he))) == NULL) 1418 return NULL; 1419 1420 if (history(h, &ev, H_DELDATA, num, &he->data) != 0) { 1421 el_free(he); 1422 return NULL; 1423 } 1424 1425 he->line = ev.str; 1426 if (history(h, &ev, H_GETSIZE) == 0) 1427 history_length = ev.num; 1428 1429 return he; 1430 } 1431 1432 1433 /* 1434 * replace the line and data of the num-th entry 1435 */ 1436 HIST_ENTRY * 1437 replace_history_entry(int num, const char *line, histdata_t data) 1438 { 1439 HIST_ENTRY *he; 1440 HistEvent ev; 1441 int curr_num; 1442 1443 if (h == NULL || e == NULL) 1444 rl_initialize(); 1445 1446 /* save current position */ 1447 if (history(h, &ev, H_CURR) != 0) 1448 return NULL; 1449 curr_num = ev.num; 1450 1451 /* start from the oldest */ 1452 if (history(h, &ev, H_LAST) != 0) 1453 return NULL; /* error */ 1454 1455 if ((he = el_malloc(sizeof(*he))) == NULL) 1456 return NULL; 1457 1458 /* look forwards for event matching specified offset */ 1459 if (history(h, &ev, H_NEXT_EVDATA, num, &he->data)) 1460 goto out; 1461 1462 he->line = strdup(ev.str); 1463 if (he->line == NULL) 1464 goto out; 1465 1466 if (history(h, &ev, H_REPLACE, line, data)) 1467 goto out; 1468 1469 /* restore pointer to where it was */ 1470 if (history(h, &ev, H_SET, curr_num)) 1471 goto out; 1472 1473 return he; 1474 out: 1475 el_free(he); 1476 return NULL; 1477 } 1478 1479 /* 1480 * clear the history list - delete all entries 1481 */ 1482 void 1483 clear_history(void) 1484 { 1485 HistEvent ev; 1486 1487 if (h == NULL || e == NULL) 1488 rl_initialize(); 1489 1490 (void)history(h, &ev, H_CLEAR); 1491 history_length = 0; 1492 } 1493 1494 1495 /* 1496 * returns offset of the current history event 1497 */ 1498 int 1499 where_history(void) 1500 { 1501 HistEvent ev; 1502 int curr_num, off; 1503 1504 if (history(h, &ev, H_CURR) != 0) 1505 return 0; 1506 curr_num = ev.num; 1507 1508 (void)history(h, &ev, H_FIRST); 1509 off = 1; 1510 while (ev.num != curr_num && history(h, &ev, H_NEXT) == 0) 1511 off++; 1512 1513 return off; 1514 } 1515 1516 1517 /* 1518 * returns current history event or NULL if there is no such event 1519 */ 1520 HIST_ENTRY * 1521 current_history(void) 1522 { 1523 1524 return _move_history(H_CURR); 1525 } 1526 1527 1528 /* 1529 * returns total number of bytes history events' data are using 1530 */ 1531 int 1532 history_total_bytes(void) 1533 { 1534 HistEvent ev; 1535 int curr_num; 1536 size_t size; 1537 1538 if (history(h, &ev, H_CURR) != 0) 1539 return -1; 1540 curr_num = ev.num; 1541 1542 (void)history(h, &ev, H_FIRST); 1543 size = 0; 1544 do 1545 size += strlen(ev.str) * sizeof(*ev.str); 1546 while (history(h, &ev, H_NEXT) == 0); 1547 1548 /* get to the same position as before */ 1549 history(h, &ev, H_PREV_EVENT, curr_num); 1550 1551 return (int)size; 1552 } 1553 1554 1555 /* 1556 * sets the position in the history list to ``pos'' 1557 */ 1558 int 1559 history_set_pos(int pos) 1560 { 1561 HistEvent ev; 1562 int curr_num; 1563 1564 if (pos >= history_length || pos < 0) 1565 return -1; 1566 1567 (void)history(h, &ev, H_CURR); 1568 curr_num = ev.num; 1569 1570 /* 1571 * use H_DELDATA to set to nth history (without delete) by passing 1572 * (void **)-1 1573 */ 1574 if (history(h, &ev, H_DELDATA, pos, (void **)-1)) { 1575 (void)history(h, &ev, H_SET, curr_num); 1576 return -1; 1577 } 1578 return 0; 1579 } 1580 1581 1582 /* 1583 * returns previous event in history and shifts pointer accordingly 1584 */ 1585 HIST_ENTRY * 1586 previous_history(void) 1587 { 1588 1589 return _move_history(H_PREV); 1590 } 1591 1592 1593 /* 1594 * returns next event in history and shifts pointer accordingly 1595 */ 1596 HIST_ENTRY * 1597 next_history(void) 1598 { 1599 1600 return _move_history(H_NEXT); 1601 } 1602 1603 1604 /* 1605 * searches for first history event containing the str 1606 */ 1607 int 1608 history_search(const char *str, int direction) 1609 { 1610 HistEvent ev; 1611 const char *strp; 1612 int curr_num; 1613 1614 if (history(h, &ev, H_CURR) != 0) 1615 return -1; 1616 curr_num = ev.num; 1617 1618 for (;;) { 1619 if ((strp = strstr(ev.str, str)) != NULL) 1620 return (int)(strp - ev.str); 1621 if (history(h, &ev, direction < 0 ? H_NEXT:H_PREV) != 0) 1622 break; 1623 } 1624 (void)history(h, &ev, H_SET, curr_num); 1625 return -1; 1626 } 1627 1628 1629 /* 1630 * searches for first history event beginning with str 1631 */ 1632 int 1633 history_search_prefix(const char *str, int direction) 1634 { 1635 HistEvent ev; 1636 1637 return (history(h, &ev, direction < 0 ? 1638 H_PREV_STR : H_NEXT_STR, str)); 1639 } 1640 1641 1642 /* 1643 * search for event in history containing str, starting at offset 1644 * abs(pos); continue backward, if pos<0, forward otherwise 1645 */ 1646 /* ARGSUSED */ 1647 int 1648 history_search_pos(const char *str, 1649 int direction __attribute__((__unused__)), int pos) 1650 { 1651 HistEvent ev; 1652 int curr_num, off; 1653 1654 off = (pos > 0) ? pos : -pos; 1655 pos = (pos > 0) ? 1 : -1; 1656 1657 if (history(h, &ev, H_CURR) != 0) 1658 return -1; 1659 curr_num = ev.num; 1660 1661 if (history_set_pos(off) != 0 || history(h, &ev, H_CURR) != 0) 1662 return -1; 1663 1664 for (;;) { 1665 if (strstr(ev.str, str)) 1666 return off; 1667 if (history(h, &ev, (pos < 0) ? H_PREV : H_NEXT) != 0) 1668 break; 1669 } 1670 1671 /* set "current" pointer back to previous state */ 1672 (void)history(h, &ev, 1673 pos < 0 ? H_NEXT_EVENT : H_PREV_EVENT, curr_num); 1674 1675 return -1; 1676 } 1677 1678 1679 /********************************/ 1680 /* completion functions */ 1681 1682 char * 1683 tilde_expand(char *name) 1684 { 1685 return fn_tilde_expand(name); 1686 } 1687 1688 char * 1689 filename_completion_function(const char *name, int state) 1690 { 1691 return fn_filename_completion_function(name, state); 1692 } 1693 1694 /* 1695 * a completion generator for usernames; returns _first_ username 1696 * which starts with supplied text 1697 * text contains a partial username preceded by random character 1698 * (usually '~'); state resets search from start (??? should we do that anyway) 1699 * it's the caller's responsibility to free the returned value 1700 */ 1701 char * 1702 username_completion_function(const char *text, int state) 1703 { 1704 #if defined(HAVE_GETPW_R_POSIX) || defined(HAVE_GETPW_R_DRAFT) 1705 struct passwd pwres; 1706 char pwbuf[1024]; 1707 #endif 1708 struct passwd *pass = NULL; 1709 1710 if (text[0] == '\0') 1711 return NULL; 1712 1713 if (*text == '~') 1714 text++; 1715 1716 if (state == 0) 1717 setpwent(); 1718 1719 while ( 1720 #if defined(HAVE_GETPW_R_POSIX) || defined(HAVE_GETPW_R_DRAFT) 1721 getpwent_r(&pwres, pwbuf, sizeof(pwbuf), &pass) == 0 && pass != NULL 1722 #else 1723 (pass = getpwent()) != NULL 1724 #endif 1725 && text[0] == pass->pw_name[0] 1726 && strcmp(text, pass->pw_name) == 0) 1727 continue; 1728 1729 if (pass == NULL) { 1730 endpwent(); 1731 return NULL; 1732 } 1733 return strdup(pass->pw_name); 1734 } 1735 1736 1737 /* 1738 * el-compatible wrapper to send TSTP on ^Z 1739 */ 1740 /* ARGSUSED */ 1741 static unsigned char 1742 _el_rl_tstp(EditLine *el __attribute__((__unused__)), int ch __attribute__((__unused__))) 1743 { 1744 (void)kill(0, SIGTSTP); 1745 return CC_NORM; 1746 } 1747 1748 /* 1749 * Display list of strings in columnar format on readline's output stream. 1750 * 'matches' is list of strings, 'len' is number of strings in 'matches', 1751 * 'max' is maximum length of string in 'matches'. 1752 */ 1753 void 1754 rl_display_match_list(char **matches, int len, int max) 1755 { 1756 1757 fn_display_match_list(e, matches, (size_t)len, (size_t)max); 1758 } 1759 1760 static const char * 1761 /*ARGSUSED*/ 1762 _rl_completion_append_character_function(const char *dummy 1763 __attribute__((__unused__))) 1764 { 1765 static char buf[2]; 1766 buf[0] = (char)rl_completion_append_character; 1767 buf[1] = '\0'; 1768 return buf; 1769 } 1770 1771 1772 /* 1773 * complete word at current point 1774 */ 1775 /* ARGSUSED */ 1776 int 1777 rl_complete(int ignore __attribute__((__unused__)), int invoking_key) 1778 { 1779 #ifdef WIDECHAR 1780 static ct_buffer_t wbreak_conv, sprefix_conv; 1781 #endif 1782 char *breakchars; 1783 1784 if (h == NULL || e == NULL) 1785 rl_initialize(); 1786 1787 if (rl_inhibit_completion) { 1788 char arr[2]; 1789 arr[0] = (char)invoking_key; 1790 arr[1] = '\0'; 1791 el_insertstr(e, arr); 1792 return CC_REFRESH; 1793 } 1794 1795 if (rl_completion_word_break_hook != NULL) 1796 breakchars = (*rl_completion_word_break_hook)(); 1797 else 1798 breakchars = rl_basic_word_break_characters; 1799 1800 /* Just look at how many global variables modify this operation! */ 1801 return fn_complete(e, 1802 (CPFunction *)rl_completion_entry_function, 1803 rl_attempted_completion_function, 1804 ct_decode_string(rl_basic_word_break_characters, &wbreak_conv), 1805 ct_decode_string(breakchars, &sprefix_conv), 1806 _rl_completion_append_character_function, 1807 (size_t)rl_completion_query_items, 1808 &rl_completion_type, &rl_attempted_completion_over, 1809 &rl_point, &rl_end, NULL, NULL, NULL); 1810 1811 1812 } 1813 1814 1815 /* ARGSUSED */ 1816 static unsigned char 1817 _el_rl_complete(EditLine *el __attribute__((__unused__)), int ch) 1818 { 1819 return (unsigned char)rl_complete(0, ch); 1820 } 1821 1822 /* 1823 * misc other functions 1824 */ 1825 1826 /* 1827 * bind key c to readline-type function func 1828 */ 1829 int 1830 rl_bind_key(int c, rl_command_func_t *func) 1831 { 1832 int retval = -1; 1833 1834 if (h == NULL || e == NULL) 1835 rl_initialize(); 1836 1837 if (func == rl_insert) { 1838 /* XXX notice there is no range checking of ``c'' */ 1839 e->el_map.key[c] = ED_INSERT; 1840 retval = 0; 1841 } 1842 return retval; 1843 } 1844 1845 1846 /* 1847 * read one key from input - handles chars pushed back 1848 * to input stream also 1849 */ 1850 int 1851 rl_read_key(void) 1852 { 1853 char fooarr[2 * sizeof(int)]; 1854 1855 if (e == NULL || h == NULL) 1856 rl_initialize(); 1857 1858 return el_getc(e, fooarr); 1859 } 1860 1861 1862 /* 1863 * reset the terminal 1864 */ 1865 /* ARGSUSED */ 1866 void 1867 rl_reset_terminal(const char *p __attribute__((__unused__))) 1868 { 1869 1870 if (h == NULL || e == NULL) 1871 rl_initialize(); 1872 el_reset(e); 1873 } 1874 1875 1876 /* 1877 * insert character ``c'' back into input stream, ``count'' times 1878 */ 1879 int 1880 rl_insert(int count, int c) 1881 { 1882 char arr[2]; 1883 1884 if (h == NULL || e == NULL) 1885 rl_initialize(); 1886 1887 /* XXX - int -> char conversion can lose on multichars */ 1888 arr[0] = (char)c; 1889 arr[1] = '\0'; 1890 1891 for (; count > 0; count--) 1892 el_push(e, arr); 1893 1894 return 0; 1895 } 1896 1897 int 1898 rl_insert_text(const char *text) 1899 { 1900 if (!text || *text == 0) 1901 return 0; 1902 1903 if (h == NULL || e == NULL) 1904 rl_initialize(); 1905 1906 if (el_insertstr(e, text) < 0) 1907 return 0; 1908 return (int)strlen(text); 1909 } 1910 1911 /*ARGSUSED*/ 1912 int 1913 rl_newline(int count __attribute__((__unused__)), 1914 int c __attribute__((__unused__))) 1915 { 1916 /* 1917 * Readline-4.0 appears to ignore the args. 1918 */ 1919 return rl_insert(1, '\n'); 1920 } 1921 1922 /*ARGSUSED*/ 1923 static unsigned char 1924 rl_bind_wrapper(EditLine *el __attribute__((__unused__)), unsigned char c) 1925 { 1926 if (map[c] == NULL) 1927 return CC_ERROR; 1928 1929 _rl_update_pos(); 1930 1931 (*map[c])(NULL, c); 1932 1933 /* If rl_done was set by the above call, deal with it here */ 1934 if (rl_done) 1935 return CC_EOF; 1936 1937 return CC_NORM; 1938 } 1939 1940 int 1941 rl_add_defun(const char *name, Function *fun, int c) 1942 { 1943 char dest[8]; 1944 if ((size_t)c >= sizeof(map) / sizeof(map[0]) || c < 0) 1945 return -1; 1946 map[(unsigned char)c] = fun; 1947 el_set(e, EL_ADDFN, name, name, rl_bind_wrapper); 1948 vis(dest, c, VIS_WHITE|VIS_NOSLASH, 0); 1949 el_set(e, EL_BIND, dest, name, NULL); 1950 return 0; 1951 } 1952 1953 void 1954 rl_callback_read_char(void) 1955 { 1956 int count = 0, done = 0; 1957 const char *buf = el_gets(e, &count); 1958 char *wbuf; 1959 1960 if (buf == NULL || count-- <= 0) 1961 return; 1962 if (count == 0 && buf[0] == e->el_tty.t_c[TS_IO][C_EOF]) 1963 done = 1; 1964 if (buf[count] == '\n' || buf[count] == '\r') 1965 done = 2; 1966 1967 if (done && rl_linefunc != NULL) { 1968 el_set(e, EL_UNBUFFERED, 0); 1969 if (done == 2) { 1970 if ((wbuf = strdup(buf)) != NULL) 1971 wbuf[count] = '\0'; 1972 } else 1973 wbuf = NULL; 1974 (*(void (*)(const char *))rl_linefunc)(wbuf); 1975 el_set(e, EL_UNBUFFERED, 1); 1976 } 1977 } 1978 1979 void 1980 rl_callback_handler_install(const char *prompt, VCPFunction *linefunc) 1981 { 1982 if (e == NULL) { 1983 rl_initialize(); 1984 } 1985 (void)rl_set_prompt(prompt); 1986 rl_linefunc = linefunc; 1987 el_set(e, EL_UNBUFFERED, 1); 1988 } 1989 1990 void 1991 rl_callback_handler_remove(void) 1992 { 1993 el_set(e, EL_UNBUFFERED, 0); 1994 rl_linefunc = NULL; 1995 } 1996 1997 void 1998 rl_redisplay(void) 1999 { 2000 char a[2]; 2001 a[0] = (char)e->el_tty.t_c[TS_IO][C_REPRINT]; 2002 a[1] = '\0'; 2003 el_push(e, a); 2004 } 2005 2006 int 2007 rl_get_previous_history(int count, int key) 2008 { 2009 char a[2]; 2010 a[0] = (char)key; 2011 a[1] = '\0'; 2012 while (count--) 2013 el_push(e, a); 2014 return 0; 2015 } 2016 2017 void 2018 /*ARGSUSED*/ 2019 rl_prep_terminal(int meta_flag __attribute__((__unused__))) 2020 { 2021 el_set(e, EL_PREP_TERM, 1); 2022 } 2023 2024 void 2025 rl_deprep_terminal(void) 2026 { 2027 el_set(e, EL_PREP_TERM, 0); 2028 } 2029 2030 int 2031 rl_read_init_file(const char *s) 2032 { 2033 return el_source(e, s); 2034 } 2035 2036 int 2037 rl_parse_and_bind(const char *line) 2038 { 2039 const char **argv; 2040 int argc; 2041 Tokenizer *tok; 2042 2043 tok = tok_init(NULL); 2044 tok_str(tok, line, &argc, &argv); 2045 argc = el_parse(e, argc, argv); 2046 tok_end(tok); 2047 return argc ? 1 : 0; 2048 } 2049 2050 int 2051 rl_variable_bind(const char *var, const char *value) 2052 { 2053 /* 2054 * The proper return value is undocument, but this is what the 2055 * readline source seems to do. 2056 */ 2057 return el_set(e, EL_BIND, "", var, value, NULL) == -1 ? 1 : 0; 2058 } 2059 2060 void 2061 rl_stuff_char(int c) 2062 { 2063 char buf[2]; 2064 2065 buf[0] = (char)c; 2066 buf[1] = '\0'; 2067 el_insertstr(e, buf); 2068 } 2069 2070 static int 2071 _rl_event_read_char(EditLine *el, char *cp) 2072 { 2073 int n; 2074 ssize_t num_read = 0; 2075 2076 *cp = '\0'; 2077 while (rl_event_hook) { 2078 2079 (*rl_event_hook)(); 2080 2081 #if defined(FIONREAD) 2082 if (ioctl(el->el_infd, FIONREAD, &n) < 0) 2083 return -1; 2084 if (n) 2085 num_read = read(el->el_infd, cp, (size_t)1); 2086 else 2087 num_read = 0; 2088 #elif defined(F_SETFL) && defined(O_NDELAY) 2089 if ((n = fcntl(el->el_infd, F_GETFL, 0)) < 0) 2090 return -1; 2091 if (fcntl(el->el_infd, F_SETFL, n|O_NDELAY) < 0) 2092 return -1; 2093 num_read = read(el->el_infd, cp, 1); 2094 if (fcntl(el->el_infd, F_SETFL, n)) 2095 return -1; 2096 #else 2097 /* not non-blocking, but what you gonna do? */ 2098 num_read = read(el->el_infd, cp, 1); 2099 return -1; 2100 #endif 2101 2102 if (num_read < 0 && errno == EAGAIN) 2103 continue; 2104 if (num_read == 0) 2105 continue; 2106 break; 2107 } 2108 if (!rl_event_hook) 2109 el_set(el, EL_GETCFN, EL_BUILTIN_GETCFN); 2110 return (int)num_read; 2111 } 2112 2113 static void 2114 _rl_update_pos(void) 2115 { 2116 const LineInfo *li = el_line(e); 2117 2118 rl_point = (int)(li->cursor - li->buffer); 2119 rl_end = (int)(li->lastchar - li->buffer); 2120 } 2121 2122 void 2123 rl_get_screen_size(int *rows, int *cols) 2124 { 2125 if (rows) 2126 el_get(e, EL_GETTC, "li", rows, (void *)0); 2127 if (cols) 2128 el_get(e, EL_GETTC, "co", cols, (void *)0); 2129 } 2130 2131 void 2132 rl_set_screen_size(int rows, int cols) 2133 { 2134 char buf[64]; 2135 (void)snprintf(buf, sizeof(buf), "%d", rows); 2136 el_set(e, EL_SETTC, "li", buf, NULL); 2137 (void)snprintf(buf, sizeof(buf), "%d", cols); 2138 el_set(e, EL_SETTC, "co", buf, NULL); 2139 } 2140 2141 char ** 2142 rl_completion_matches(const char *str, rl_compentry_func_t *fun) 2143 { 2144 size_t len, max, i, j, min; 2145 char **list, *match, *a, *b; 2146 2147 len = 1; 2148 max = 10; 2149 if ((list = el_malloc(max * sizeof(*list))) == NULL) 2150 return NULL; 2151 2152 while ((match = (*fun)(str, (int)(len - 1))) != NULL) { 2153 list[len++] = match; 2154 if (len == max) { 2155 char **nl; 2156 max += 10; 2157 if ((nl = el_realloc(list, max * sizeof(*nl))) == NULL) 2158 goto out; 2159 list = nl; 2160 } 2161 } 2162 if (len == 1) 2163 goto out; 2164 list[len] = NULL; 2165 if (len == 2) { 2166 if ((list[0] = strdup(list[1])) == NULL) 2167 goto out; 2168 return list; 2169 } 2170 qsort(&list[1], len - 1, sizeof(*list), 2171 (int (*)(const void *, const void *)) strcmp); 2172 min = SIZE_T_MAX; 2173 for (i = 1, a = list[i]; i < len - 1; i++, a = b) { 2174 b = list[i + 1]; 2175 for (j = 0; a[j] && a[j] == b[j]; j++) 2176 continue; 2177 if (min > j) 2178 min = j; 2179 } 2180 if (min == 0 && *str) { 2181 if ((list[0] = strdup(str)) == NULL) 2182 goto out; 2183 } else { 2184 if ((list[0] = el_malloc((min + 1) * sizeof(*list[0]))) == NULL) 2185 goto out; 2186 (void)memcpy(list[0], list[1], min); 2187 list[0][min] = '\0'; 2188 } 2189 return list; 2190 2191 out: 2192 el_free(list); 2193 return NULL; 2194 } 2195 2196 char * 2197 rl_filename_completion_function (const char *text, int state) 2198 { 2199 return fn_filename_completion_function(text, state); 2200 } 2201 2202 void 2203 rl_forced_update_display(void) 2204 { 2205 el_set(e, EL_REFRESH); 2206 } 2207 2208 int 2209 _rl_abort_internal(void) 2210 { 2211 el_beep(e); 2212 longjmp(topbuf, 1); 2213 /*NOTREACHED*/ 2214 } 2215 2216 int 2217 _rl_qsort_string_compare(char **s1, char **s2) 2218 { 2219 return strcoll(*s1, *s2); 2220 } 2221 2222 HISTORY_STATE * 2223 history_get_history_state(void) 2224 { 2225 HISTORY_STATE *hs; 2226 2227 if ((hs = el_malloc(sizeof(*hs))) == NULL) 2228 return NULL; 2229 hs->length = history_length; 2230 return hs; 2231 } 2232 2233 int 2234 /*ARGSUSED*/ 2235 rl_kill_text(int from __attribute__((__unused__)), 2236 int to __attribute__((__unused__))) 2237 { 2238 return 0; 2239 } 2240 2241 Keymap 2242 rl_make_bare_keymap(void) 2243 { 2244 return NULL; 2245 } 2246 2247 Keymap 2248 rl_get_keymap(void) 2249 { 2250 return NULL; 2251 } 2252 2253 void 2254 /*ARGSUSED*/ 2255 rl_set_keymap(Keymap k __attribute__((__unused__))) 2256 { 2257 } 2258 2259 int 2260 /*ARGSUSED*/ 2261 rl_generic_bind(int type __attribute__((__unused__)), 2262 const char * keyseq __attribute__((__unused__)), 2263 const char * data __attribute__((__unused__)), 2264 Keymap k __attribute__((__unused__))) 2265 { 2266 return 0; 2267 } 2268 2269 int 2270 /*ARGSUSED*/ 2271 rl_bind_key_in_map(int key __attribute__((__unused__)), 2272 rl_command_func_t *fun __attribute__((__unused__)), 2273 Keymap k __attribute__((__unused__))) 2274 { 2275 return 0; 2276 } 2277 2278 /* unsupported, but needed by python */ 2279 void 2280 rl_cleanup_after_signal(void) 2281 { 2282 } 2283 2284 int 2285 rl_on_new_line(void) 2286 { 2287 return 0; 2288 } 2289 2290 void 2291 rl_free_line_state(void) 2292 { 2293 } 2294