From: Todd C. Miller Date: Mon, 10 Aug 2015 21:13:37 +0000 (-0600) Subject: Linux sets si_pid in struct siginfo to 0 when the process that sent X-Git-Tag: SUDO_1_8_15^2~83 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=13869d349caa670d600883cb440832abd237b993;p=sudo Linux sets si_pid in struct siginfo to 0 when the process that sent the signal is in a different container since the PID namespaces in different conatiners are separate. Avoid looking up the process group by id when si_pid is 0 since getpgid(0) returns the process group of the current process. Since sudo ignores signals sent by processes in its own process group, this had the effect of ignoring signals sent from other containers. From Maarten de Vries --- diff --git a/doc/CONTRIBUTORS b/doc/CONTRIBUTORS index b4b1ad695..09261071b 100644 --- a/doc/CONTRIBUTORS +++ b/doc/CONTRIBUTORS @@ -157,6 +157,7 @@ you believe you should be listed, please send a note to sudo@sudo.ws. Valery, Reznic Van Dinter, Theo Venckus, Martynas + de Vries, Maarten Wagner, Klaus Walsh, Dan Warburton, John diff --git a/src/exec.c b/src/exec.c index b518bae71..4e4046a6a 100644 --- a/src/exec.c +++ b/src/exec.c @@ -887,7 +887,7 @@ handler(int s, siginfo_t *info, void *context) * kill itself. For example, this can happen with some versions of * reboot that call kill(-1, SIGTERM) to kill all other processes. */ - if (s != SIGCHLD && USER_SIGNALED(info)) { + if (s != SIGCHLD && USER_SIGNALED(info) && info->si_pid != 0) { pid_t si_pgrp = getpgid(info->si_pid); if (si_pgrp != (pid_t)-1) { if (si_pgrp == ppgrp || si_pgrp == cmnd_pid) @@ -934,7 +934,6 @@ static void handler_user_only(int s, siginfo_t *info, void *context) { unsigned char signo = (unsigned char)s; - pid_t si_pgrp; /* * Only forward user-generated signals not sent by a process in @@ -945,11 +944,14 @@ handler_user_only(int s, siginfo_t *info, void *context) */ if (!USER_SIGNALED(info)) return; - if ((si_pgrp = getpgid(info->si_pid)) != (pid_t)-1) { - if (si_pgrp == ppgrp || si_pgrp == cmnd_pid) - return; - } else if (info->si_pid == cmnd_pid) { + if (info->si_pid != 0) { + pid_t si_pgrp = getpgid(info->si_pid); + if (si_pgrp != (pid_t)-1) { + if (si_pgrp == ppgrp || si_pgrp == cmnd_pid) + return; + } else if (info->si_pid == cmnd_pid) { return; + } } /* diff --git a/src/exec_pty.c b/src/exec_pty.c index f61658d2b..fc49e17f9 100644 --- a/src/exec_pty.c +++ b/src/exec_pty.c @@ -135,7 +135,7 @@ mon_handler(int s, siginfo_t *info, void *context) * itself. This can happen with, e.g., BSD-derived versions of * reboot that call kill(-1, SIGTERM) to kill all other processes. */ - if (s != SIGCHLD && USER_SIGNALED(info)) { + if (s != SIGCHLD && USER_SIGNALED(info) && info->si_pid != 0) { pid_t si_pgrp = getpgid(info->si_pid); if (si_pgrp != (pid_t)-1) { if (si_pgrp == cmnd_pgrp)