ash: do not leave SIGQUIT ignored on "exec CMD"
authorDenys Vlasenko <vda.linux@googlemail.com>
Sat, 16 Jul 2016 16:33:55 +0000 (18:33 +0200)
committerDenys Vlasenko <vda.linux@googlemail.com>
Sat, 16 Jul 2016 16:33:55 +0000 (18:33 +0200)
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
shell/ash.c
shell/ash_test/ash-signals/sigquit_exec.right [new file with mode: 0644]
shell/ash_test/ash-signals/sigquit_exec.tests [new file with mode: 0755]

index faa45a8dc600f9800d866fb0198f09c28c0ad993..4f6376f787ad2446e1b63eae2d5c726299cf4226 100644 (file)
@@ -323,7 +323,7 @@ struct globals_misc {
 #define S_DFL      1            /* default signal handling (SIG_DFL) */
 #define S_CATCH    2            /* signal is caught */
 #define S_IGN      3            /* signal is ignored (SIG_IGN) */
-#define S_HARD_IGN 4            /* signal is ignored permenantly */
+#define S_HARD_IGN 4            /* signal is ignored permanently */
 
        /* indicates specified signal received */
        uint8_t gotsig[NSIG - 1]; /* offset by 1: "signal" 0 is meaningless */
@@ -9024,7 +9024,20 @@ execcmd(int argc UNUSED_PARAM, char **argv)
                iflag = 0;              /* exit on error */
                mflag = 0;
                optschanged();
+               /* We should set up signals for "exec CMD"
+                * the same way as for "CMD" without "exec".
+                * But optschanged->setinteractive->setsignal
+                * still thought we are a root shell. Therefore, for example,
+                * SIGQUIT is still set to IGN. Fix it:
+                */
+               shlvl++;
+               setsignal(SIGQUIT);
+               /*setsignal(SIGTERM); - unnecessary because of iflag=0 */
+               /*setsignal(SIGTSTP); - unnecessary because of mflag=0 */
+               /*setsignal(SIGTTOU); - unnecessary because of mflag=0 */
+
                shellexec(argv + 1, pathval(), 0);
+               /* NOTREACHED */
        }
        return 0;
 }
diff --git a/shell/ash_test/ash-signals/sigquit_exec.right b/shell/ash_test/ash-signals/sigquit_exec.right
new file mode 100644 (file)
index 0000000..a804192
--- /dev/null
@@ -0,0 +1,2 @@
+SigIgn:        0000000000000000
+SigIgn:        0000000000000000
diff --git a/shell/ash_test/ash-signals/sigquit_exec.tests b/shell/ash_test/ash-signals/sigquit_exec.tests
new file mode 100755 (executable)
index 0000000..24bda69
--- /dev/null
@@ -0,0 +1,4 @@
+# Should show no masked signals in both cases.
+# We had a bug where SIGQUIT was masked on exec.
+grep SigIgn: /proc/self/status
+exec grep SigIgn: /proc/self/status