Red Hat Bugzilla – Bug 17244
daemon() in init.d/functions not reliable
Last modified: 2014-03-16 22:16:09 EDT
The daemon() function in /etc/rc.d/init.d/functions is designed for init
scripts to use to invoke a program. However, under certain circumstances,
the daemon() function will silently fail to start the program it is given,
but return with a "true" exit status anyway.
What causes the failure to occur is when a master instance of a daemon
spawns off independent child processes, and those child process outlive the
parent which spawned them. Take, for example, OpenSSH:
458 ? S 0:00 /usr/sbin/sshd
3988 ? S 0:00 \_ /usr/sbin/sshd
3992 ? S 0:00 \_ /usr/X11R6/bin/xterm -ls
3996 pts/2 S 0:00 \_ -bash2
Here, pid 458 is the master sshd, and one child sshd process exists (to
serve an interactive login).
If the master process (pid 458) is shut down, the child process (pid 3988)
will live on until the person who is connected logs out. But as long as
pid 3988 exists (or any other /usr/sbin/sshd processes exist), daemon()
will refuse to start up the sshd service.
This problem occurs because daemon() uses pidofproc() to attempt to see if
the process which is about to be started is already running. The
pidofproc() function will first try to read a pid from the
/var/run/<service>.pid file. If pidofproc() fails to find a pid in this
manner (which it will in the above example, because the master sshd process
will remove its pid file when it exits), pidofproc() then uses "pidof" to
grovel through the entire process table. Because the sshd child process
exists, "pidof" will find and return it. The daemon() function checks that
pid to make sure it is active, finds that it is, and silently exits without
OpenSSH is far from the only process affected by this misfeature; any
daemon that forks off child processes which exist independently of the
master daemon will be affected by this problem (e.g., Apache, sendmail).
IMO, whether implemented as an entirely new function, or as an option to
daemon(), there needs to be some way to indicate that a service that is to
be started should be judged to be running or not based SOLELY on the
presence of a valid pid in the /var/run/<service>.pid file.
*** Bug 20696 has been marked as a duplicate of this bug. ***
This will be changed in initscripts-5.60-1.