diff options
Diffstat (limited to 'package/busybox/busybox-1.15.1-hush.patch')
-rw-r--r-- | package/busybox/busybox-1.15.1-hush.patch | 61 |
1 files changed, 61 insertions, 0 deletions
diff --git a/package/busybox/busybox-1.15.1-hush.patch b/package/busybox/busybox-1.15.1-hush.patch new file mode 100644 index 000000000..9ba661477 --- /dev/null +++ b/package/busybox/busybox-1.15.1-hush.patch @@ -0,0 +1,61 @@ +diff -urpN busybox-1.15.1/shell/hush.c busybox-1.15.1-hush/shell/hush.c +--- busybox-1.15.1/shell/hush.c 2009-09-12 17:56:20.000000000 +0200 ++++ busybox-1.15.1-hush/shell/hush.c 2009-09-23 03:27:27.000000000 +0200 +@@ -5183,6 +5183,47 @@ static FILE *generate_stream_from_string + xmove_fd(channel[1], 1); + /* Prevent it from trying to handle ctrl-z etc */ + IF_HUSH_JOB(G.run_list_level = 1;) ++ /* Awful hack for `trap` or $(trap). ++ * ++ * http://www.opengroup.org/onlinepubs/009695399/utilities/trap.html ++ * contains an example where "trap" is executed in a subshell: ++ * ++ * save_traps=$(trap) ++ * ... ++ * eval "$save_traps" ++ * ++ * Standard does not say that "trap" in subshell shall print ++ * parent shell's traps. It only says that its output ++ * must have suitable form, but then, in the above example ++ * (which is not supposed to be normative), it implies that. ++ * ++ * bash (and probably other shell) does implement it ++ * (traps are reset to defaults, but "trap" still shows them), ++ * but as a result, "trap" logic is hopelessly messed up: ++ * ++ * # trap ++ * trap -- 'echo Ho' SIGWINCH <--- we have a handler ++ * # (trap) <--- trap is in subshell - no output (correct, traps are reset) ++ * # true | trap <--- trap is in subshell - no output (ditto) ++ * # echo `true | trap` <--- in subshell - output (but traps are reset!) ++ * trap -- 'echo Ho' SIGWINCH ++ * # echo `(trap)` <--- in subshell in subshell - output ++ * trap -- 'echo Ho' SIGWINCH ++ * # echo `true | (trap)` <--- in subshell in subshell in subshell - output! ++ * trap -- 'echo Ho' SIGWINCH ++ * ++ * The rules when to forget and when to not forget traps ++ * get really complex and nonsensical. ++ * ++ * Our solution: ONLY bare $(trap) or `trap` is special. ++ */ ++ s = skip_whitespace(s); ++ if (strncmp(s, "trap", 4) == 0 && (*skip_whitespace(s + 4) == '\0')) ++ { ++ static const char *const argv[] = { NULL, NULL }; ++ builtin_trap((char**)argv); ++ exit(0); /* not _exit() - we need to fflush */ ++ } + #if BB_MMU + reset_traps_to_defaults(); + parse_and_run_string(s); +@@ -7057,7 +7098,8 @@ static int FAST_FUNC builtin_trap(char * + if (G.traps[i]) { + printf("trap -- "); + print_escaped(G.traps[i]); +- printf(" %s\n", get_signame(i)); ++ /* bash compat: it says SIGxxx, not just xxx */ ++ printf(" SIG%s\n", get_signame(i)); + } + } + /*fflush(stdout); - done after each builtin anyway */ |