By switching to sigaction(2) instead of signal(2), the signal handler for child processes can be registered only once, instead of every time the signal was received.
If the signal(2) call within the signal handler fails, die() is called which in turn is not signal-safe. Therefore, the change to sigaction makes dwm() more portable among POSIX systems and fixes a signal race condition. In order to use sigaction(2), the target system must be compatible to POSIX.1-2001 or SVr4, which is basically already given due to compile flags (e.g. BSD_SOURCE). --- dwm.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/dwm.c b/dwm.c index d27cb67..f593007 100644 --- a/dwm.c +++ b/dwm.c @@ -1537,9 +1537,14 @@ setup(void) int i; XSetWindowAttributes wa; Atom utf8string; + struct sigaction sa; /* clean up any zombies immediately */ - sigchld(0); + sa.sa_handler = sigchld; + sa.sa_flags = SA_RESTART; + sigemptyset(&sa.sa_mask); + if (sigaction(SIGCHLD, &sa, NULL)) + die("can't install SIGCHLD handler:"); /* init screen */ screen = DefaultScreen(dpy); @@ -1635,8 +1640,6 @@ showhide(Client *c) void sigchld(int unused) { - if (signal(SIGCHLD, sigchld) == SIG_ERR) - die("can't install SIGCHLD handler:"); while (0 < waitpid(-1, NULL, WNOHANG)); } -- 2.11.0