1 /* SPDX-License-Identifier: GPL-2.0 */
3 /** \file daemon.c Some helpers for programs that detach from the console. */
17 #include "gcc-compat.h"
24 * Do the usual stuff to become a daemon.
26 * Fork, become session leader, dup fd 0, 1, 2 to /dev/null.
28 * \sa fork(2), setsid(2), dup(2).
35 DSS_INFO_LOG(("daemonizing\n"));
43 * The parent process exits once it has received one byte from
44 * the reading end of the pipe. If the child exits before it
45 * was able to complete its setup (acquire the lock on the
46 * semaphore), the read() below will return zero. In this case
47 * we let the parent die unsuccessfully.
52 ret = read(fd[0], &c, 1);
54 DSS_EMERG_LOG(("child terminated unexpectedly\n"));
60 /* become session leader */
64 null = open("/dev/null", O_RDWR);
67 if (dup2(null, STDIN_FILENO) < 0)
69 if (dup2(null, STDOUT_FILENO) < 0)
71 if (dup2(null, STDERR_FILENO) < 0)
76 DSS_EMERG_LOG(("fatal: %s\n", strerror(errno)));
81 * fopen() the given file in append mode.
83 * \param logfile_name The name of the file to open.
85 * \return Either calls exit() or returns a valid file handle.
87 FILE *open_log(const char *logfile_name)
92 logfile = fopen(logfile_name, "a");
94 DSS_EMERG_LOG(("can not open %s: %s\n", logfile_name,
103 * Close the log file of the daemon.
105 * \param logfile The log file handle.
107 * It's OK to call this with logfile == \p NULL.
109 void close_log(FILE* logfile)
113 DSS_INFO_LOG(("closing logfile\n"));
118 * Log the startup message.
120 void log_welcome(int loglevel)
122 DSS_INFO_LOG(("***** welcome to dss ******\n"));
123 DSS_DEBUG_LOG(("using loglevel %d\n", loglevel));