* Use an explicit handler for SIGCHLD, since SIG_IGN doesn't do the

right thing on FreeBSD 4 (it leaves zombies).
This commit is contained in:
Eelco Dolstra 2006-12-05 17:21:42 +00:00
parent 62b0497c0f
commit 99655245ae

View file

@ -10,10 +10,12 @@
#include <unistd.h> #include <unistd.h>
#include <signal.h> #include <signal.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/wait.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/socket.h> #include <sys/socket.h>
#include <sys/un.h> #include <sys/un.h>
#include <fcntl.h> #include <fcntl.h>
#include <errno.h>
using namespace nix; using namespace nix;
@ -403,10 +405,17 @@ static void processConnection()
} }
static void setSigChldAction(bool ignore) static void sigChldHandler(int sigNo)
{
/* Reap all dead children. */
while (waitpid(-1, 0, WNOHANG) == 0) ;
}
static void setSigChldAction(bool autoReap)
{ {
struct sigaction act, oact; struct sigaction act, oact;
act.sa_handler = ignore ? SIG_IGN : SIG_DFL; act.sa_handler = autoReap ? sigChldHandler : SIG_DFL;
sigfillset(&act.sa_mask); sigfillset(&act.sa_mask);
act.sa_flags = 0; act.sa_flags = 0;
if (sigaction(SIGCHLD, &act, &oact)) if (sigaction(SIGCHLD, &act, &oact))
@ -463,6 +472,9 @@ static void daemonLoop()
(struct sockaddr *) &remoteAddr, &remoteAddrLen); (struct sockaddr *) &remoteAddr, &remoteAddrLen);
checkInterrupt(); checkInterrupt();
if (remote == -1) if (remote == -1)
if (errno == EINTR)
continue;
else
throw SysError("accepting connection"); throw SysError("accepting connection");
printMsg(lvlInfo, format("accepted connection %1%") % remote); printMsg(lvlInfo, format("accepted connection %1%") % remote);