diff options
| author | Eric Andersen <andersen@codepoet.org> | 2001-03-13 22:57:56 +0000 |
|---|---|---|
| committer | Eric Andersen <andersen@codepoet.org> | 2001-03-13 22:57:56 +0000 |
| commit | b3d6e2df95a21034e41d46a18c71dd1c4e07e987 (patch) | |
| tree | 2d549a0d8748a9673be658e193a8104149cf2c15 /shell/cmdedit.c | |
| parent | 798ab301c772cc18ab64f94386da3c7ec10daf42 (diff) | |
| download | busybox-w32-b3d6e2df95a21034e41d46a18c71dd1c4e07e987.tar.gz busybox-w32-b3d6e2df95a21034e41d46a18c71dd1c4e07e987.tar.bz2 busybox-w32-b3d6e2df95a21034e41d46a18c71dd1c4e07e987.zip | |
Update the lash shell (hopefully the last time...) so things like
echo "foo bar" and echo -n "foo\t\\\\\tbar" work as expected.
Merge prompt printing work from Vladimir.
-Erik
Diffstat (limited to 'shell/cmdedit.c')
| -rw-r--r-- | shell/cmdedit.c | 173 |
1 files changed, 97 insertions, 76 deletions
diff --git a/shell/cmdedit.c b/shell/cmdedit.c index 272d22fc0..1b5cbbfab 100644 --- a/shell/cmdedit.c +++ b/shell/cmdedit.c | |||
| @@ -27,6 +27,7 @@ | |||
| 27 | Small bugs (simple effect): | 27 | Small bugs (simple effect): |
| 28 | - not true viewing if terminal size (x*y symbols) less | 28 | - not true viewing if terminal size (x*y symbols) less |
| 29 | size (prompt + editor`s line + 2 symbols) | 29 | size (prompt + editor`s line + 2 symbols) |
| 30 | - not true viewing if length prompt less terminal width | ||
| 30 | */ | 31 | */ |
| 31 | 32 | ||
| 32 | 33 | ||
| @@ -50,29 +51,36 @@ | |||
| 50 | 51 | ||
| 51 | #else | 52 | #else |
| 52 | 53 | ||
| 53 | #define BB_FEATURE_SH_COMMAND_EDITING | 54 | #define BB_FEATURE_COMMAND_EDITING |
| 54 | #define BB_FEATURE_SH_TAB_COMPLETION | 55 | #define BB_FEATURE_COMMAND_TAB_COMPLETION |
| 55 | #define BB_FEATURE_SH_USERNAME_COMPLETION | 56 | #define BB_FEATURE_COMMAND_USERNAME_COMPLETION |
| 56 | #define BB_FEATURE_NONPRINTABLE_INVERSE_PUT | 57 | #define BB_FEATURE_NONPRINTABLE_INVERSE_PUT |
| 57 | #define BB_FEATURE_BASH_STYLE_PROMT | 58 | #undef BB_FEATURE_SIMPLE_PROMPT |
| 58 | #define BB_FEATURE_CLEAN_UP | 59 | #define BB_FEATURE_CLEAN_UP |
| 59 | 60 | ||
| 60 | #define D(x) x | 61 | #define D(x) x |
| 61 | 62 | ||
| 63 | #ifndef TRUE | ||
| 64 | #define TRUE 1 | ||
| 65 | #endif | ||
| 66 | #ifndef FALSE | ||
| 67 | #define FALSE 0 | ||
| 68 | #endif | ||
| 69 | |||
| 62 | #endif /* TEST */ | 70 | #endif /* TEST */ |
| 63 | 71 | ||
| 64 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 72 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 65 | #include <dirent.h> | 73 | #include <dirent.h> |
| 66 | #include <sys/stat.h> | 74 | #include <sys/stat.h> |
| 67 | #endif | 75 | #endif |
| 68 | 76 | ||
| 69 | #ifdef BB_FEATURE_SH_COMMAND_EDITING | 77 | #ifdef BB_FEATURE_COMMAND_EDITING |
| 70 | 78 | ||
| 71 | #ifndef BB_FEATURE_SH_TAB_COMPLETION | 79 | #ifndef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 72 | #undef BB_FEATURE_SH_USERNAME_COMPLETION | 80 | #undef BB_FEATURE_COMMAND_USERNAME_COMPLETION |
| 73 | #endif | 81 | #endif |
| 74 | 82 | ||
| 75 | #if defined(BB_FEATURE_SH_USERNAME_COMPLETION) || defined(BB_FEATURE_BASH_STYLE_PROMT) | 83 | #if defined(BB_FEATURE_COMMAND_USERNAME_COMPLETION) || !defined(BB_FEATURE_SIMPLE_PROMPT) |
| 76 | #define BB_FEATURE_GETUSERNAME_AND_HOMEDIR | 84 | #define BB_FEATURE_GETUSERNAME_AND_HOMEDIR |
| 77 | #endif | 85 | #endif |
| 78 | 86 | ||
| @@ -154,26 +162,26 @@ static | |||
| 154 | volatile int handlers_sets = 0; /* Set next bites: */ | 162 | volatile int handlers_sets = 0; /* Set next bites: */ |
| 155 | 163 | ||
| 156 | enum { | 164 | enum { |
| 157 | SET_ATEXIT = 1, /* when atexit() has been called and | 165 | SET_ATEXIT = 1, /* when atexit() has been called |
| 158 | get euid,uid,gid to fast compare */ | 166 | and get euid,uid,gid to fast compare */ |
| 159 | SET_TERM_HANDLERS = 2, /* set many terminates signal handlers */ | 167 | SET_TERM_HANDLERS = 2, /* set many terminates signal handlers */ |
| 160 | SET_WCHG_HANDLERS = 4, /* winchg signal handler */ | 168 | SET_WCHG_HANDLERS = 4, /* winchg signal handler */ |
| 161 | SET_RESET_TERM = 8, /* if the terminal needs to be reset upon exit */ | 169 | SET_RESET_TERM = 8, /* if the terminal needs to be reset upon exit */ |
| 162 | }; | 170 | }; |
| 163 | 171 | ||
| 164 | 172 | ||
| 165 | static int cmdedit_x; /* real x terminal position */ | 173 | static int cmdedit_x; /* real x terminal position */ |
| 166 | static int cmdedit_y; /* pseudoreal y terminal position */ | 174 | static int cmdedit_y; /* pseudoreal y terminal position */ |
| 167 | static int cmdedit_prmt_len; /* lenght prompt without colores string */ | 175 | static int cmdedit_prmt_len; /* lenght prompt without colores string */ |
| 168 | 176 | ||
| 169 | static int cursor; /* required global for signal handler */ | 177 | static int cursor; /* required global for signal handler */ |
| 170 | static int len; /* --- "" - - "" - -"- --""-- --""--- */ | 178 | static int len; /* --- "" - - "" - -"- --""-- --""--- */ |
| 171 | static char *command_ps; /* --- "" - - "" - -"- --""-- --""--- */ | 179 | static char *command_ps; /* --- "" - - "" - -"- --""-- --""--- */ |
| 172 | static | 180 | static |
| 173 | #ifndef BB_FEATURE_BASH_STYLE_PROMT | 181 | #ifdef BB_FEATURE_SIMPLE_PROMPT |
| 174 | const | 182 | const |
| 175 | #endif | 183 | #endif |
| 176 | char *cmdedit_prompt; /* --- "" - - "" - -"- --""-- --""--- */ | 184 | char *cmdedit_prompt; /* --- "" - - "" - -"- --""-- --""--- */ |
| 177 | 185 | ||
| 178 | /* Link into lash to reset context to 0 on ^C and such */ | 186 | /* Link into lash to reset context to 0 on ^C and such */ |
| 179 | extern unsigned int shell_context; | 187 | extern unsigned int shell_context; |
| @@ -185,13 +193,13 @@ static char *home_pwd_buf = ""; | |||
| 185 | static int my_euid; | 193 | static int my_euid; |
| 186 | #endif | 194 | #endif |
| 187 | 195 | ||
| 188 | #ifdef BB_FEATURE_BASH_STYLE_PROMT | 196 | #ifndef BB_FEATURE_SIMPLE_PROMPT |
| 189 | static char *hostname_buf = ""; | 197 | static char *hostname_buf = ""; |
| 190 | static int num_ok_lines = 1; | 198 | static int num_ok_lines = 1; |
| 191 | #endif | 199 | #endif |
| 192 | 200 | ||
| 193 | 201 | ||
| 194 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 202 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 195 | 203 | ||
| 196 | #ifndef BB_FEATURE_GETUSERNAME_AND_HOMEDIR | 204 | #ifndef BB_FEATURE_GETUSERNAME_AND_HOMEDIR |
| 197 | static int my_euid; | 205 | static int my_euid; |
| @@ -200,7 +208,7 @@ static int my_euid; | |||
| 200 | static int my_uid; | 208 | static int my_uid; |
| 201 | static int my_gid; | 209 | static int my_gid; |
| 202 | 210 | ||
| 203 | #endif /* BB_FEATURE_SH_TAB_COMPLETION */ | 211 | #endif /* BB_FEATURE_COMMAND_TAB_COMPLETION */ |
| 204 | 212 | ||
| 205 | 213 | ||
| 206 | static void cmdedit_setwidth(int w, int redraw_flg); | 214 | static void cmdedit_setwidth(int w, int redraw_flg); |
| @@ -245,7 +253,6 @@ static void cmdedit_reset_term(void) | |||
| 245 | if (his_front) { | 253 | if (his_front) { |
| 246 | struct history *n; | 254 | struct history *n; |
| 247 | 255 | ||
| 248 | //while(his_front!=his_end) { | ||
| 249 | while (his_front != his_end) { | 256 | while (his_front != his_end) { |
| 250 | n = his_front->n; | 257 | n = his_front->n; |
| 251 | free(his_front->s); | 258 | free(his_front->s); |
| @@ -355,25 +362,27 @@ static void put_prompt(void) | |||
| 355 | cursor = 0; | 362 | cursor = 0; |
| 356 | } | 363 | } |
| 357 | 364 | ||
| 358 | #ifdef BB_FEATURE_BASH_STYLE_PROMT | 365 | #ifdef BB_FEATURE_SIMPLE_PROMPT |
| 359 | static void | 366 | static void parse_prompt(const char *prmt_ptr) |
| 360 | add_to_prompt(char **prmt_mem_ptr, int *alm, int *prmt_len, | ||
| 361 | const char *addb) | ||
| 362 | { | 367 | { |
| 363 | int l = strlen(addb); | 368 | cmdedit_prompt = prmt_ptr; |
| 364 | 369 | cmdedit_prmt_len = strlen(prmt_ptr); | |
| 365 | *prmt_len += l; | 370 | put_prompt(); |
| 371 | } | ||
| 372 | #else | ||
| 373 | static void add_to_prompt(char **prmt_mem_ptr, int *alm, | ||
| 374 | int *prmt_len, const char *addb) | ||
| 375 | { | ||
| 376 | *prmt_len += strlen(addb); | ||
| 366 | if (*alm < (*prmt_len) + 1) { | 377 | if (*alm < (*prmt_len) + 1) { |
| 367 | *alm = (*prmt_len) + 1; | 378 | *alm = (*prmt_len) + 1; |
| 368 | *prmt_mem_ptr = xrealloc(*prmt_mem_ptr, *alm); | 379 | *prmt_mem_ptr = xrealloc(*prmt_mem_ptr, *alm); |
| 369 | } | 380 | } |
| 370 | strcat(*prmt_mem_ptr, addb); | 381 | strcat(*prmt_mem_ptr, addb); |
| 371 | } | 382 | } |
| 372 | #endif | ||
| 373 | 383 | ||
| 374 | static void parse_prompt(const char *prmt_ptr) | 384 | static void parse_prompt(const char *prmt_ptr) |
| 375 | { | 385 | { |
| 376 | #ifdef BB_FEATURE_BASH_STYLE_PROMT | ||
| 377 | int alm = strlen(prmt_ptr) + 1; /* supposedly require memory */ | 386 | int alm = strlen(prmt_ptr) + 1; /* supposedly require memory */ |
| 378 | int prmt_len = 0; | 387 | int prmt_len = 0; |
| 379 | int sub_len = 0; | 388 | int sub_len = 0; |
| @@ -394,9 +403,11 @@ static void parse_prompt(const char *prmt_ptr) | |||
| 394 | break; | 403 | break; |
| 395 | prmt_ptr++; | 404 | prmt_ptr++; |
| 396 | switch (c) { | 405 | switch (c) { |
| 406 | #ifdef BB_FEATURE_GETUSERNAME_AND_HOMEDIR | ||
| 397 | case 'u': | 407 | case 'u': |
| 398 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, user_buf); | 408 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, user_buf); |
| 399 | continue; | 409 | continue; |
| 410 | #endif | ||
| 400 | case 'h': | 411 | case 'h': |
| 401 | if (hostname_buf[0] == 0) { | 412 | if (hostname_buf[0] == 0) { |
| 402 | hostname_buf = xcalloc(256, 1); | 413 | hostname_buf = xcalloc(256, 1); |
| @@ -415,6 +426,7 @@ static void parse_prompt(const char *prmt_ptr) | |||
| 415 | case '$': | 426 | case '$': |
| 416 | c = my_euid == 0 ? '#' : '$'; | 427 | c = my_euid == 0 ? '#' : '$'; |
| 417 | break; | 428 | break; |
| 429 | #ifdef BB_FEATURE_GETUSERNAME_AND_HOMEDIR | ||
| 418 | case 'w': | 430 | case 'w': |
| 419 | if (pwd_buf[0] == 0) { | 431 | if (pwd_buf[0] == 0) { |
| 420 | int l; | 432 | int l; |
| @@ -429,6 +441,7 @@ static void parse_prompt(const char *prmt_ptr) | |||
| 429 | } | 441 | } |
| 430 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, pwd_buf); | 442 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, pwd_buf); |
| 431 | continue; | 443 | continue; |
| 444 | #endif | ||
| 432 | case '!': | 445 | case '!': |
| 433 | snprintf(buf, sizeof(buf), "%d", num_ok_lines); | 446 | snprintf(buf, sizeof(buf), "%d", num_ok_lines); |
| 434 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, buf); | 447 | add_to_prompt(&prmt_mem_ptr, &alm, &prmt_len, buf); |
| @@ -485,20 +498,21 @@ static void parse_prompt(const char *prmt_ptr) | |||
| 485 | if (flg_not_length == ']') | 498 | if (flg_not_length == ']') |
| 486 | sub_len++; | 499 | sub_len++; |
| 487 | } | 500 | } |
| 501 | #if 0 | ||
| 488 | cmdedit_prmt_len = prmt_len - sub_len; | 502 | cmdedit_prmt_len = prmt_len - sub_len; |
| 489 | cmdedit_prompt = prmt_mem_ptr; | ||
| 490 | #else | ||
| 491 | cmdedit_prompt = prmt_ptr; | 503 | cmdedit_prompt = prmt_ptr; |
| 492 | cmdedit_prmt_len = strlen(prmt_ptr); | 504 | #endif |
| 493 | #endif | 505 | cmdedit_prompt = prmt_mem_ptr; |
| 506 | cmdedit_prmt_len = strlen(cmdedit_prompt); | ||
| 494 | put_prompt(); | 507 | put_prompt(); |
| 495 | } | 508 | } |
| 509 | #endif | ||
| 496 | 510 | ||
| 497 | 511 | ||
| 498 | /* draw promt, editor line, and clear tail */ | 512 | /* draw promt, editor line, and clear tail */ |
| 499 | static void redraw(int y, int back_cursor) | 513 | static void redraw(int y, int back_cursor) |
| 500 | { | 514 | { |
| 501 | if (y > 0) /* up to start y */ | 515 | if (y > 0) /* up to start y */ |
| 502 | printf("\033[%dA", y); | 516 | printf("\033[%dA", y); |
| 503 | cmdedit_y = 0; /* new quasireal y */ | 517 | cmdedit_y = 0; /* new quasireal y */ |
| 504 | putchar('\r'); | 518 | putchar('\r'); |
| @@ -518,7 +532,7 @@ static void input_delete(void) | |||
| 518 | 532 | ||
| 519 | strcpy(command_ps + j, command_ps + j + 1); | 533 | strcpy(command_ps + j, command_ps + j + 1); |
| 520 | len--; | 534 | len--; |
| 521 | input_end(); /* rewtite new line */ | 535 | input_end(); /* rewtite new line */ |
| 522 | cmdedit_set_out_char(0); /* destroy end char */ | 536 | cmdedit_set_out_char(0); /* destroy end char */ |
| 523 | input_backward(cursor - j); /* back to old pos cursor */ | 537 | input_backward(cursor - j); /* back to old pos cursor */ |
| 524 | } | 538 | } |
| @@ -545,7 +559,7 @@ static void clean_up_and_die(int sig) | |||
| 545 | { | 559 | { |
| 546 | goto_new_line(); | 560 | goto_new_line(); |
| 547 | if (sig != SIGINT) | 561 | if (sig != SIGINT) |
| 548 | exit(EXIT_SUCCESS); /* cmdedit_reset_term() called in atexit */ | 562 | exit(EXIT_SUCCESS); /* cmdedit_reset_term() called in atexit */ |
| 549 | cmdedit_reset_term(); | 563 | cmdedit_reset_term(); |
| 550 | } | 564 | } |
| 551 | 565 | ||
| @@ -556,7 +570,6 @@ static void cmdedit_setwidth(int w, int redraw_flg) | |||
| 556 | cmdedit_termw = cmdedit_termw % w; | 570 | cmdedit_termw = cmdedit_termw % w; |
| 557 | } | 571 | } |
| 558 | if (w > cmdedit_termw) { | 572 | if (w > cmdedit_termw) { |
| 559 | |||
| 560 | cmdedit_termw = w; | 573 | cmdedit_termw = w; |
| 561 | 574 | ||
| 562 | if (redraw_flg) { | 575 | if (redraw_flg) { |
| @@ -590,14 +603,14 @@ extern void cmdedit_init(void) | |||
| 590 | } | 603 | } |
| 591 | #endif | 604 | #endif |
| 592 | 605 | ||
| 593 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 606 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 594 | 607 | ||
| 595 | #ifndef BB_FEATURE_GETUSERNAME_AND_HOMEDIR | 608 | #ifndef BB_FEATURE_GETUSERNAME_AND_HOMEDIR |
| 596 | my_euid = geteuid(); | 609 | my_euid = geteuid(); |
| 597 | #endif | 610 | #endif |
| 598 | my_uid = getuid(); | 611 | my_uid = getuid(); |
| 599 | my_gid = getgid(); | 612 | my_gid = getgid(); |
| 600 | #endif /* BB_FEATURE_SH_TAB_COMPLETION */ | 613 | #endif /* BB_FEATURE_COMMAND_TAB_COMPLETION */ |
| 601 | handlers_sets |= SET_ATEXIT; | 614 | handlers_sets |= SET_ATEXIT; |
| 602 | atexit(cmdedit_reset_term); /* be sure to do this only once */ | 615 | atexit(cmdedit_reset_term); /* be sure to do this only once */ |
| 603 | } | 616 | } |
| @@ -612,7 +625,7 @@ extern void cmdedit_init(void) | |||
| 612 | 625 | ||
| 613 | } | 626 | } |
| 614 | 627 | ||
| 615 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 628 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 616 | 629 | ||
| 617 | static int is_execute(const struct stat *st) | 630 | static int is_execute(const struct stat *st) |
| 618 | { | 631 | { |
| @@ -623,7 +636,7 @@ static int is_execute(const struct stat *st) | |||
| 623 | return FALSE; | 636 | return FALSE; |
| 624 | } | 637 | } |
| 625 | 638 | ||
| 626 | #ifdef BB_FEATURE_SH_USERNAME_COMPLETION | 639 | #ifdef BB_FEATURE_COMMAND_USERNAME_COMPLETION |
| 627 | 640 | ||
| 628 | static char **username_tab_completion(char *ud, int *num_matches) | 641 | static char **username_tab_completion(char *ud, int *num_matches) |
| 629 | { | 642 | { |
| @@ -632,19 +645,19 @@ static char **username_tab_completion(char *ud, int *num_matches) | |||
| 632 | char *temp; | 645 | char *temp; |
| 633 | 646 | ||
| 634 | 647 | ||
| 635 | ud++; /* ~user/... to user/... */ | 648 | ud++; /* ~user/... to user/... */ |
| 636 | userlen = strlen(ud); | 649 | userlen = strlen(ud); |
| 637 | 650 | ||
| 638 | if (num_matches == 0) { /* "~/..." or "~user/..." */ | 651 | if (num_matches == 0) { /* "~/..." or "~user/..." */ |
| 639 | char *sav_ud = ud - 1; | 652 | char *sav_ud = ud - 1; |
| 640 | char *home = 0; | 653 | char *home = 0; |
| 641 | 654 | ||
| 642 | if (*ud == '/') { /* "~/..." */ | 655 | if (*ud == '/') { /* "~/..." */ |
| 643 | home = home_pwd_buf; | 656 | home = home_pwd_buf; |
| 644 | } else { | 657 | } else { |
| 645 | /* "~user/..." */ | 658 | /* "~user/..." */ |
| 646 | temp = strchr(ud, '/'); | 659 | temp = strchr(ud, '/'); |
| 647 | *temp = 0; /* ~user\0 */ | 660 | *temp = 0; /* ~user\0 */ |
| 648 | entry = getpwnam(ud); | 661 | entry = getpwnam(ud); |
| 649 | *temp = '/'; /* restore ~user/... */ | 662 | *temp = '/'; /* restore ~user/... */ |
| 650 | ud = temp; | 663 | ud = temp; |
| @@ -660,7 +673,7 @@ static char **username_tab_completion(char *ud, int *num_matches) | |||
| 660 | strcpy(sav_ud, temp2); | 673 | strcpy(sav_ud, temp2); |
| 661 | } | 674 | } |
| 662 | } | 675 | } |
| 663 | return 0; /* void, result save to argument :-) */ | 676 | return 0; /* void, result save to argument :-) */ |
| 664 | } else { | 677 | } else { |
| 665 | /* "~[^/]*" */ | 678 | /* "~[^/]*" */ |
| 666 | char **matches = (char **) NULL; | 679 | char **matches = (char **) NULL; |
| @@ -685,7 +698,7 @@ static char **username_tab_completion(char *ud, int *num_matches) | |||
| 685 | return (matches); | 698 | return (matches); |
| 686 | } | 699 | } |
| 687 | } | 700 | } |
| 688 | #endif /* BB_FEATURE_SH_USERNAME_COMPLETION */ | 701 | #endif /* BB_FEATURE_COMMAND_USERNAME_COMPLETION */ |
| 689 | 702 | ||
| 690 | enum { | 703 | enum { |
| 691 | FIND_EXE_ONLY = 0, | 704 | FIND_EXE_ONLY = 0, |
| @@ -710,11 +723,11 @@ static int path_parse(char ***p, int flags) | |||
| 710 | npth = 0; | 723 | npth = 0; |
| 711 | 724 | ||
| 712 | for (;;) { | 725 | for (;;) { |
| 713 | npth++; /* count words is + 1 count ':' */ | 726 | npth++; /* count words is + 1 count ':' */ |
| 714 | tmp = strchr(tmp, ':'); | 727 | tmp = strchr(tmp, ':'); |
| 715 | if (tmp) { | 728 | if (tmp) { |
| 716 | if (*++tmp == 0) | 729 | if (*++tmp == 0) |
| 717 | break; /* :<empty> */ | 730 | break; /* :<empty> */ |
| 718 | } else | 731 | } else |
| 719 | break; | 732 | break; |
| 720 | } | 733 | } |
| @@ -723,7 +736,7 @@ static int path_parse(char ***p, int flags) | |||
| 723 | 736 | ||
| 724 | tmp = pth; | 737 | tmp = pth; |
| 725 | (*p)[0] = xstrdup(tmp); | 738 | (*p)[0] = xstrdup(tmp); |
| 726 | npth = 1; /* count words is + 1 count ':' */ | 739 | npth = 1; /* count words is + 1 count ':' */ |
| 727 | 740 | ||
| 728 | for (;;) { | 741 | for (;;) { |
| 729 | tmp = strchr(tmp, ':'); | 742 | tmp = strchr(tmp, ':'); |
| @@ -754,7 +767,7 @@ static char *add_quote_for_spec_chars(char *found) | |||
| 754 | } | 767 | } |
| 755 | 768 | ||
| 756 | static char **exe_n_cwd_tab_completion(char *command, int *num_matches, | 769 | static char **exe_n_cwd_tab_completion(char *command, int *num_matches, |
| 757 | int type) | 770 | int type) |
| 758 | { | 771 | { |
| 759 | 772 | ||
| 760 | char **matches = 0; | 773 | char **matches = 0; |
| @@ -782,7 +795,7 @@ static char **exe_n_cwd_tab_completion(char *command, int *num_matches, | |||
| 782 | strcpy(dirbuf, command); | 795 | strcpy(dirbuf, command); |
| 783 | /* set dir only */ | 796 | /* set dir only */ |
| 784 | dirbuf[(pfind - command) + 1] = 0; | 797 | dirbuf[(pfind - command) + 1] = 0; |
| 785 | #ifdef BB_FEATURE_SH_USERNAME_COMPLETION | 798 | #ifdef BB_FEATURE_COMMAND_USERNAME_COMPLETION |
| 786 | if (dirbuf[0] == '~') /* ~/... or ~user/... */ | 799 | if (dirbuf[0] == '~') /* ~/... or ~user/... */ |
| 787 | username_tab_completion(dirbuf, 0); | 800 | username_tab_completion(dirbuf, 0); |
| 788 | #endif | 801 | #endif |
| @@ -796,7 +809,7 @@ static char **exe_n_cwd_tab_completion(char *command, int *num_matches, | |||
| 796 | for (i = 0; i < npaths; i++) { | 809 | for (i = 0; i < npaths; i++) { |
| 797 | 810 | ||
| 798 | dir = opendir(paths[i]); | 811 | dir = opendir(paths[i]); |
| 799 | if (!dir) /* Don't print an error */ | 812 | if (!dir) /* Don't print an error */ |
| 800 | continue; | 813 | continue; |
| 801 | 814 | ||
| 802 | while ((next = readdir(dir)) != NULL) { | 815 | while ((next = readdir(dir)) != NULL) { |
| @@ -987,7 +1000,8 @@ static int find_match(char *matchBuf, int *len_with_quotes) | |||
| 987 | for (i = 0; int_buf[i]; i++) | 1000 | for (i = 0; int_buf[i]; i++) |
| 988 | if (int_buf[i] == ' ' || int_buf[i] == '<' || int_buf[i] == '>') { | 1001 | if (int_buf[i] == ' ' || int_buf[i] == '<' || int_buf[i] == '>') { |
| 989 | if (int_buf[i] == ' ' && command_mode == FIND_EXE_ONLY | 1002 | if (int_buf[i] == ' ' && command_mode == FIND_EXE_ONLY |
| 990 | && strncmp(&matchBuf[pos_buf[0]], "cd", 2) == 0) | 1003 | && matchBuf[pos_buf[0]]=='c' |
| 1004 | && matchBuf[pos_buf[1]]=='d' ) | ||
| 991 | command_mode = FIND_DIR_ONLY; | 1005 | command_mode = FIND_DIR_ONLY; |
| 992 | else { | 1006 | else { |
| 993 | command_mode = FIND_FILE_ONLY; | 1007 | command_mode = FIND_FILE_ONLY; |
| @@ -1065,7 +1079,7 @@ static void input_tab(int *lastWasTab) | |||
| 1065 | /* Free up any memory already allocated */ | 1079 | /* Free up any memory already allocated */ |
| 1066 | input_tab(0); | 1080 | input_tab(0); |
| 1067 | 1081 | ||
| 1068 | #ifdef BB_FEATURE_SH_USERNAME_COMPLETION | 1082 | #ifdef BB_FEATURE_COMMAND_USERNAME_COMPLETION |
| 1069 | /* If the word starts with `~' and there is no slash in the word, | 1083 | /* If the word starts with `~' and there is no slash in the word, |
| 1070 | * then try completing this word as a username. */ | 1084 | * then try completing this word as a username. */ |
| 1071 | 1085 | ||
| @@ -1085,7 +1099,7 @@ static void input_tab(int *lastWasTab) | |||
| 1085 | 1099 | ||
| 1086 | beep(); | 1100 | beep(); |
| 1087 | if (!matches) | 1101 | if (!matches) |
| 1088 | return; /* not found */ | 1102 | return; /* not found */ |
| 1089 | /* sort */ | 1103 | /* sort */ |
| 1090 | qsort(matches, num_matches, sizeof(char *), match_compare); | 1104 | qsort(matches, num_matches, sizeof(char *), match_compare); |
| 1091 | 1105 | ||
| @@ -1101,7 +1115,7 @@ static void input_tab(int *lastWasTab) | |||
| 1101 | free(tmp); | 1115 | free(tmp); |
| 1102 | return; | 1116 | return; |
| 1103 | } | 1117 | } |
| 1104 | } else { /* one match */ | 1118 | } else { /* one match */ |
| 1105 | tmp = matches[0]; | 1119 | tmp = matches[0]; |
| 1106 | /* for next completion current found */ | 1120 | /* for next completion current found */ |
| 1107 | *lastWasTab = FALSE; | 1121 | *lastWasTab = FALSE; |
| @@ -1164,7 +1178,7 @@ static void input_tab(int *lastWasTab) | |||
| 1164 | } | 1178 | } |
| 1165 | } | 1179 | } |
| 1166 | } | 1180 | } |
| 1167 | #endif /* BB_FEATURE_SH_TAB_COMPLETION */ | 1181 | #endif /* BB_FEATURE_COMMAND_TAB_COMPLETION */ |
| 1168 | 1182 | ||
| 1169 | static void get_previous_history(struct history **hp, struct history *p) | 1183 | static void get_previous_history(struct history **hp, struct history *p) |
| 1170 | { | 1184 | { |
| @@ -1201,6 +1215,7 @@ enum { | |||
| 1201 | * Furthermore, the "vi" command editing keys are not implemented. | 1215 | * Furthermore, the "vi" command editing keys are not implemented. |
| 1202 | * | 1216 | * |
| 1203 | */ | 1217 | */ |
| 1218 | |||
| 1204 | extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | 1219 | extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) |
| 1205 | { | 1220 | { |
| 1206 | 1221 | ||
| @@ -1212,7 +1227,7 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1212 | struct history *hp = his_end; | 1227 | struct history *hp = his_end; |
| 1213 | 1228 | ||
| 1214 | /* prepare before init handlers */ | 1229 | /* prepare before init handlers */ |
| 1215 | cmdedit_y = 0; /* quasireal y, not true work if line > xt*yt */ | 1230 | cmdedit_y = 0; /* quasireal y, not true work if line > xt*yt */ |
| 1216 | len = 0; | 1231 | len = 0; |
| 1217 | command_ps = command; | 1232 | command_ps = command; |
| 1218 | 1233 | ||
| @@ -1223,9 +1238,11 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1223 | 1238 | ||
| 1224 | new_settings.c_cc[VMIN] = 1; | 1239 | new_settings.c_cc[VMIN] = 1; |
| 1225 | new_settings.c_cc[VTIME] = 0; | 1240 | new_settings.c_cc[VTIME] = 0; |
| 1226 | new_settings.c_cc[VINTR] = _POSIX_VDISABLE; /* Turn off CTRL-C, so we can trap it */ | 1241 | /* Turn off CTRL-C, so we can trap it */ |
| 1242 | new_settings.c_cc[VINTR] = _POSIX_VDISABLE; | ||
| 1227 | new_settings.c_lflag &= ~ICANON; /* unbuffered input */ | 1243 | new_settings.c_lflag &= ~ICANON; /* unbuffered input */ |
| 1228 | new_settings.c_lflag &= ~(ECHO | ECHOCTL | ECHONL); /* Turn off echoing */ | 1244 | /* Turn off echoing */ |
| 1245 | new_settings.c_lflag &= ~(ECHO | ECHOCTL | ECHONL); | ||
| 1229 | } | 1246 | } |
| 1230 | 1247 | ||
| 1231 | command[0] = 0; | 1248 | command[0] = 0; |
| @@ -1295,7 +1312,7 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1295 | input_backspace(); | 1312 | input_backspace(); |
| 1296 | break; | 1313 | break; |
| 1297 | case '\t': | 1314 | case '\t': |
| 1298 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 1315 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 1299 | input_tab(&lastWasTab); | 1316 | input_tab(&lastWasTab); |
| 1300 | #endif | 1317 | #endif |
| 1301 | break; | 1318 | break; |
| @@ -1335,7 +1352,7 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1335 | return; | 1352 | return; |
| 1336 | } | 1353 | } |
| 1337 | switch (c) { | 1354 | switch (c) { |
| 1338 | #ifdef BB_FEATURE_SH_TAB_COMPLETION | 1355 | #ifdef BB_FEATURE_COMMAND_TAB_COMPLETION |
| 1339 | case '\t': /* Alt-Tab */ | 1356 | case '\t': /* Alt-Tab */ |
| 1340 | 1357 | ||
| 1341 | input_tab(&lastWasTab); | 1358 | input_tab(&lastWasTab); |
| @@ -1402,7 +1419,7 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1402 | break; | 1419 | break; |
| 1403 | } | 1420 | } |
| 1404 | 1421 | ||
| 1405 | default: /* If it's regular input, do the normal thing */ | 1422 | default: /* If it's regular input, do the normal thing */ |
| 1406 | #ifdef BB_FEATURE_NONPRINTABLE_INVERSE_PUT | 1423 | #ifdef BB_FEATURE_NONPRINTABLE_INVERSE_PUT |
| 1407 | /* Control-V -- Add non-printable symbol */ | 1424 | /* Control-V -- Add non-printable symbol */ |
| 1408 | if (c == 22) { | 1425 | if (c == 22) { |
| @@ -1493,16 +1510,16 @@ extern void cmdedit_read_input(char *prompt, char command[BUFSIZ]) | |||
| 1493 | history_counter++; | 1510 | history_counter++; |
| 1494 | } | 1511 | } |
| 1495 | } | 1512 | } |
| 1496 | #if defined(BB_FEATURE_BASH_STYLE_PROMT) | 1513 | #if !defined(BB_FEATURE_SIMPLE_PROMPT) |
| 1497 | num_ok_lines++; | 1514 | num_ok_lines++; |
| 1498 | #endif | 1515 | #endif |
| 1499 | } | 1516 | } |
| 1500 | command[len++] = '\n'; /* set '\n' */ | 1517 | command[len++] = '\n'; /* set '\n' */ |
| 1501 | command[len] = 0; | 1518 | command[len] = 0; |
| 1502 | #if defined(BB_FEATURE_CLEAN_UP) && defined(BB_FEATURE_SH_TAB_COMPLETION) | 1519 | #if defined(BB_FEATURE_CLEAN_UP) && defined(BB_FEATURE_COMMAND_TAB_COMPLETION) |
| 1503 | input_tab(0); /* strong free */ | 1520 | input_tab(0); /* strong free */ |
| 1504 | #endif | 1521 | #endif |
| 1505 | #if defined(BB_FEATURE_BASH_STYLE_PROMT) | 1522 | #if !defined(BB_FEATURE_SIMPLE_PROMPT) |
| 1506 | free(cmdedit_prompt); | 1523 | free(cmdedit_prompt); |
| 1507 | #endif | 1524 | #endif |
| 1508 | return; | 1525 | return; |
| @@ -1523,7 +1540,7 @@ extern void cmdedit_terminate(void) | |||
| 1523 | } | 1540 | } |
| 1524 | } | 1541 | } |
| 1525 | 1542 | ||
| 1526 | #endif /* BB_FEATURE_SH_COMMAND_EDITING */ | 1543 | #endif /* BB_FEATURE_COMMAND_EDITING */ |
| 1527 | 1544 | ||
| 1528 | 1545 | ||
| 1529 | #ifdef TEST | 1546 | #ifdef TEST |
| @@ -1534,21 +1551,25 @@ int main(int argc, char **argv) | |||
| 1534 | { | 1551 | { |
| 1535 | char buff[BUFSIZ]; | 1552 | char buff[BUFSIZ]; |
| 1536 | char *prompt = | 1553 | char *prompt = |
| 1537 | #if defined(BB_FEATURE_BASH_STYLE_PROMT) | 1554 | #if !defined(BB_FEATURE_SIMPLE_PROMPT) |
| 1538 | "\\[\\033[32;1m\\]\\u@\\[\\033[33;1m\\]\\h:\ | 1555 | "\\[\\033[32;1m\\]\\u@\\[\\x1b[33;1m\\]\\h:\ |
| 1539 | \\[\\033[34;1m\\]\\w\\[\\033[35;1m\\] \ | 1556 | \\[\\033[34;1m\\]\\w\\[\\033[35;1m\\] \ |
| 1540 | \\!\\[\\033[36;1m\\]\\$ \\[\\033[0m\\]"; | 1557 | \\!\\[\\e[36;1m\\]\\$ \\[\\E[0m\\]"; |
| 1541 | #else | 1558 | #else |
| 1542 | "% "; | 1559 | "% "; |
| 1543 | #endif | 1560 | #endif |
| 1544 | 1561 | ||
| 1545 | shell_context = 1; | 1562 | shell_context = 1; |
| 1546 | do { | 1563 | do { |
| 1564 | int l; | ||
| 1547 | cmdedit_read_input(prompt, buff); | 1565 | cmdedit_read_input(prompt, buff); |
| 1566 | l = strlen(buff); | ||
| 1567 | if(l > 0 && buff[l-1] == '\n') | ||
| 1568 | buff[l-1] = 0; | ||
| 1548 | printf("*** cmdedit_read_input() returned line =%s=\n", buff); | 1569 | printf("*** cmdedit_read_input() returned line =%s=\n", buff); |
| 1549 | } while (shell_context); | 1570 | } while (shell_context); |
| 1550 | printf("*** cmdedit_read_input() detect ^C\n"); | 1571 | printf("*** cmdedit_read_input() detect ^C\n"); |
| 1551 | return 0; | 1572 | return 0; |
| 1552 | } | 1573 | } |
| 1553 | 1574 | ||
| 1554 | #endif /* TEST */ | 1575 | #endif /* TEST */ |
