[sudo-users] Improper setting / resetting of the signals mask

Ciprian Dorin, Craciun ciprian.craciun at gmail.com
Tue Sep 14 07:14:45 EDT 2010


    Hello all!

    Sorry for cross-posting, but this "bug" is relevant to both
projects (`runit` and `sudo`), so please forgive me in advance. :)

    In short `sudo` doesn't seem to reset (zero out) its inherited
signal mask, and `runit` seems to leave some signals blocked when
exec-ing children. (And the side-effect is breaking some service
management scripts.)

    Now the long story:
    * (`runit` specific) it seems that when `runit` starts the
`./contro/t` script it leaves some signals blocked (at least the mask
0x14000) (see below in the transcript from `ps s $PID`); (it seems
that this happens only for `./contro/X` and not for the `./run`
scripts;)
    * (`sudo` specific) it seems that when `sudo` starts it doesn't
reset the inherited blocked signals, on which it seems to rely for
detecting when the child process finished; (and this only happens with
the latest versions of `sudo` (`1.7.4p3`), because until now sudo
didn't forked and waited for the child but instead it `execve`-d it;
now because it uses the `pam-session` feature it waits for the child
to terminate...)

    The following snippet is part of the `./control/t` script which
only sends `TERM` followed by `KILL` signals to the service. It uses
`sudo` to elevate the rights from my normal user to that of root.
~~~~
#!/bin/bash

set -e +m -u -o pipefail || exit 1
exec 2>&1

echo "before sudo" >>/tmp/transcript.txt
ps s "${$}" >>/tmp/transcript.txt

test "${#}" -eq 0
test "${UID}" -eq 0 || exec sudo -u "#0" -g "#${UID}" -E -P -n -- "${0}" "${@}"

echo "after sudo" >>/tmp/transcript.txt
ps s "${$}" >>/tmp/transcript.txt

pid="$( cat ./supervise/pid )"
test -e "/proc/${pid}" || exit 1
kill -s TERM "${pid}" || true
sleep 0.1s
test -e "/proc/${pid}" || exit 0
sleep 1s
test -e "/proc/${pid}" || exit 0
kill -s KILL "${pid}" || true
exit 0
~~~~

    And the following is the result of running the script. See the
BLOCKED (0x14000) signal mask:
    * the first "before sudo" text and the `ps` output line is before
executing `sudo` (thus showing that `runit` doesn't clear the blocked
signals mask);
    * the second "before sudo" text and the `ps` line is after
executing `sudo` (and before the UID test) and the masks are just like
the previous output (thus showing that sudo doesn't reset the masks);
~~~~
before sudo
  UID   PID          PENDING          BLOCKED          IGNORED
  CAUGHT STAT TTY        TIME COMMAND
10101  5935 0000000000000000 0000000000014000 0000000000000004
0000000000010002 S    ?          0:00 /bin/bash control/t
before sudo
  UID   PID          PENDING          BLOCKED          IGNORED
  CAUGHT STAT TTY        TIME COMMAND
    0  5937 0000000000000000 0000000000014000 0000000000000004
0000000000010002 S    ?          0:00 /bin/bash control/t
~~~~

    And the following is the result of running the same script but
with a minor modification (see the `nosig` wrapper in front of `sudo`
which is just a simple C application that manually clears all signal
masks before `execve`-ing):
    * see that the BLOCKED mask before using `nosig` is the same as in
the previous case, but:
    * by using `nosig` followed by `sudo` the signal masks are cleared
(I think that the "0x10000" signal is blocked by BASH in any case);
~~~~
test "${UID}" -eq 0 || exec nosig sudo -u "#0" -g "#${UID}" -E -P -n
-- "${0}" "${@}"
~~~~
before sudo
  UID   PID          PENDING          BLOCKED          IGNORED
  CAUGHT STAT TTY        TIME COMMAND
10101  6067 0000000000000000 0000000000014000 0000000000000004
0000000000010002 S    ?          0:00 /bin/bash control/t
before sudo
  UID   PID          PENDING          BLOCKED          IGNORED
  CAUGHT STAT TTY        TIME COMMAND
    0  6069 0000000000000000 0000000000010000 0000000000000004
0000000000010002 S    ?          0:00 /bin/bash control/t
~~~~

    So thank you for paying attention to my report, and I hope it'll
be helpful for the developers.
    Ciprian.



More information about the sudo-users mailing list