diff options
| author | Denys Vlasenko <vda.linux@googlemail.com> | 2016-11-08 04:59:11 +0100 |
|---|---|---|
| committer | Denys Vlasenko <vda.linux@googlemail.com> | 2016-11-08 04:59:11 +0100 |
| commit | 830ea35484cecb8b4cdbe0f30cc5d573ff0e3411 (patch) | |
| tree | 9057122598e964984f9bda62a75d7cb746cd602f | |
| parent | 02affb4afd4a71b0c1ca6286f9b0f6bf3b10e0a1 (diff) | |
| download | busybox-w32-830ea35484cecb8b4cdbe0f30cc5d573ff0e3411.tar.gz busybox-w32-830ea35484cecb8b4cdbe0f30cc5d573ff0e3411.tar.bz2 busybox-w32-830ea35484cecb8b4cdbe0f30cc5d573ff0e3411.zip | |
hush: make "wait %1" less likely to play with signal mask
Was playing with "sleep 3 | exit 3 & wait %1" and noticed that often
SIGCHLD arrives even before I get to signal masking. Can avoid it in this
case.
function old new delta
wait_for_child_or_signal 228 265 +37
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
| -rw-r--r-- | shell/hush.c | 15 |
1 files changed, 7 insertions, 8 deletions
diff --git a/shell/hush.c b/shell/hush.c index ddbf2f7d8..5e51adfdc 100644 --- a/shell/hush.c +++ b/shell/hush.c | |||
| @@ -8146,11 +8146,11 @@ static void install_fatal_sighandlers(void) | |||
| 8146 | 8146 | ||
| 8147 | /* We will restore tty pgrp on these signals */ | 8147 | /* We will restore tty pgrp on these signals */ |
| 8148 | mask = 0 | 8148 | mask = 0 |
| 8149 | + (1 << SIGILL ) * HUSH_DEBUG | 8149 | /*+ (1 << SIGILL ) * HUSH_DEBUG*/ |
| 8150 | + (1 << SIGFPE ) * HUSH_DEBUG | 8150 | /*+ (1 << SIGFPE ) * HUSH_DEBUG*/ |
| 8151 | + (1 << SIGBUS ) * HUSH_DEBUG | 8151 | + (1 << SIGBUS ) * HUSH_DEBUG |
| 8152 | + (1 << SIGSEGV) * HUSH_DEBUG | 8152 | + (1 << SIGSEGV) * HUSH_DEBUG |
| 8153 | + (1 << SIGTRAP) * HUSH_DEBUG | 8153 | /*+ (1 << SIGTRAP) * HUSH_DEBUG*/ |
| 8154 | + (1 << SIGABRT) | 8154 | + (1 << SIGABRT) |
| 8155 | /* bash 3.2 seems to handle these just like 'fatal' ones */ | 8155 | /* bash 3.2 seems to handle these just like 'fatal' ones */ |
| 8156 | + (1 << SIGPIPE) | 8156 | + (1 << SIGPIPE) |
| @@ -9518,6 +9518,9 @@ static int wait_for_child_or_signal(struct pipe *waitfor_pipe, pid_t waitfor_pid | |||
| 9518 | int sig; | 9518 | int sig; |
| 9519 | sigset_t oldset; | 9519 | sigset_t oldset; |
| 9520 | 9520 | ||
| 9521 | if (!sigisemptyset(&G.pending_set)) | ||
| 9522 | goto check_sig; | ||
| 9523 | |||
| 9521 | /* waitpid is not interruptible by SA_RESTARTed | 9524 | /* waitpid is not interruptible by SA_RESTARTed |
| 9522 | * signals which we use. Thus, this ugly dance: | 9525 | * signals which we use. Thus, this ugly dance: |
| 9523 | */ | 9526 | */ |
| @@ -9532,7 +9535,6 @@ static int wait_for_child_or_signal(struct pipe *waitfor_pipe, pid_t waitfor_pid | |||
| 9532 | 9535 | ||
| 9533 | if (!sigisemptyset(&G.pending_set)) { | 9536 | if (!sigisemptyset(&G.pending_set)) { |
| 9534 | /* Crap! we raced with some signal! */ | 9537 | /* Crap! we raced with some signal! */ |
| 9535 | // sig = 0; | ||
| 9536 | goto restore; | 9538 | goto restore; |
| 9537 | } | 9539 | } |
| 9538 | 9540 | ||
| @@ -9567,13 +9569,10 @@ static int wait_for_child_or_signal(struct pipe *waitfor_pipe, pid_t waitfor_pid | |||
| 9567 | sigsuspend(&oldset); | 9569 | sigsuspend(&oldset); |
| 9568 | restore: | 9570 | restore: |
| 9569 | sigprocmask(SIG_SETMASK, &oldset, NULL); | 9571 | sigprocmask(SIG_SETMASK, &oldset, NULL); |
| 9570 | 9572 | check_sig: | |
| 9571 | /* So, did we get a signal? */ | 9573 | /* So, did we get a signal? */ |
| 9572 | //if (sig > 0) | ||
| 9573 | // raise(sig); /* run handler */ | ||
| 9574 | sig = check_and_run_traps(); | 9574 | sig = check_and_run_traps(); |
| 9575 | if (sig /*&& sig != SIGCHLD - always true */) { | 9575 | if (sig /*&& sig != SIGCHLD - always true */) { |
| 9576 | /* see note 2 */ | ||
| 9577 | ret = 128 + sig; | 9576 | ret = 128 + sig; |
| 9578 | break; | 9577 | break; |
| 9579 | } | 9578 | } |
