Date: Mon, 06 Feb 2012 23:46:24 +0200 From: Mikolaj Golub <trociny@freebsd.org> To: Pawel Jakub Dawidek <pjd@FreeBSD.org> Cc: svn-src-head@FreeBSD.org, Guy Helmer <ghelmer@palisadesystems.com>, svn-src-all@FreeBSD.org, Andrey Zonov <andrey@zonov.org>, src-committers@FreeBSD.org Subject: Re: svn commit: r230869 - head/usr.sbin/daemon Message-ID: <86wr7zmy8f.fsf@kopusha.home.net> In-Reply-To: <20120206082706.GA1324@garage.freebsd.pl> (Pawel Jakub Dawidek's message of "Mon, 6 Feb 2012 09:27:06 %2B0100") References: <201202011641.q11Gf0j6095461@svn.freebsd.org> <20120204074201.GA1694@garage.freebsd.pl> <4F2CEB1D.10607@zonov.org> <27A0A960-F767-4D2C-BF3E-31F73FBF4E28@palisadesystems.com> <86zkcy5ur9.fsf@kopusha.home.net> <20120205093938.GC30033@garage.freebsd.pl> <86lioh7yz5.fsf@kopusha.home.net> <20120205214647.GI30033@garage.freebsd.pl> <86sjiov29o.fsf@in138.ua3> <20120206082706.GA1324@garage.freebsd.pl>
next in thread | previous in thread | raw e-mail | index | archive | help
[-- Attachment #1 --]
PJD> For the patch itself.
PJD> You don't have to have two separate cases depending on request for
PJD> pidfile. You can specify NULL pfh to the pidfile functions.
PJD> Even in example from the manual page when pfh is NULL there is a case
PJD> where we warn, but continue execution and call pidfile functions.
PJD> This should simplify the code.
PJD> If you do that (actually even if you don't), remember to either use
PJD> warn(3) before pidfile_remove(3) and exit(3) after or preserve errno
PJD> before calling pidfile_remove(3), as pidfile_remove(3) can modify it if
PJD> unlink(2) is unsuccessful or pfh is NULL.
Thanks. The updated version is attached.
--
Mikolaj Golub
[-- Attachment #2 --]
Index: usr.sbin/daemon/daemon.c
===================================================================
--- usr.sbin/daemon/daemon.c (revision 231014)
+++ usr.sbin/daemon/daemon.c (working copy)
@@ -32,6 +32,7 @@
__FBSDID("$FreeBSD$");
#include <sys/param.h>
+#include <sys/wait.h>
#include <err.h>
#include <errno.h>
@@ -43,15 +44,16 @@ __FBSDID("$FreeBSD$");
#include <unistd.h>
static void restrict_process(const char *);
+static void wait_child(pid_t pid);
static void usage(void);
int
main(int argc, char *argv[])
{
struct pidfh *pfh = NULL;
- int ch, nochdir, noclose, errcode;
+ int ch, nochdir, noclose;
const char *pidfile, *user;
- pid_t otherpid;
+ pid_t otherpid, pid;
nochdir = noclose = 1;
pidfile = user = NULL;
@@ -79,9 +81,7 @@ main(int argc, char *argv[])
if (argc == 0)
usage();
- if (user != NULL)
- restrict_process(user);
-
+ pfh = NULL;
/*
* Try to open the pidfile before calling daemon(3),
* to be able to report the error intelligently
@@ -100,22 +100,36 @@ main(int argc, char *argv[])
if (daemon(nochdir, noclose) == -1)
err(1, NULL);
- /* Now that we are the child, write out the pid */
- if (pidfile)
+ pid = 0;
+ if (pidfile) {
+ /*
+ * Spawn a child to exec the command, so in the parent
+ * we could wait for it to exit and remove pidfile.
+ */
+ pid = fork();
+ if (pid == -1) {
+ pidfile_remove(pfh);
+ err(1, "fork");
+ }
+ }
+ if (pid == 0) {
+ /* Now that we are the child, write out the pid. */
pidfile_write(pfh);
- execvp(argv[0], argv);
+ if (user != NULL)
+ restrict_process(user);
- /*
- * execvp() failed -- unlink pidfile if any, and
- * report the error
- */
- errcode = errno; /* Preserve errcode -- unlink may reset it */
- if (pidfile)
- pidfile_remove(pfh);
+ execvp(argv[0], argv);
- /* The child is now running, so the exit status doesn't matter. */
- errc(1, errcode, "%s", argv[0]);
+ /*
+ * execvp() failed -- report the error. The child is
+ * now running, so the exit status doesn't matter.
+ */
+ err(1, "%s", argv[0]);
+ }
+ wait_child(pid);
+ pidfile_remove(pfh);
+ exit(0); /* Exit status does not metter. */
}
static void
@@ -132,6 +146,19 @@ restrict_process(const char *user)
}
static void
+wait_child(pid_t pid)
+{
+ int status;
+
+ while (waitpid(pid, &status, 0) == -1) {
+ if (errno != EINTR) {
+ warn("waitpid");
+ break;
+ }
+ }
+}
+
+static void
usage(void)
{
(void)fprintf(stderr,
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?86wr7zmy8f.fsf>
