2 * UCW Library -- Daemon Control
4 * (c) 2012 Martin Mares <mj@ucw.cz>
6 * This software may be freely distributed and used according to the terms
7 * of the GNU Lesser General Public License.
11 #include <ucw/daemon.h>
12 #include <ucw/process.h>
24 static enum daemon_control_status
25 daemon_control_err(struct daemon_control_params *dc, char *msg, ...)
29 vsnprintf(dc->error_msg, DAEMON_ERR_LEN, msg, args);
31 return DAEMON_STATUS_ERROR;
35 daemon_read_pid(struct daemon_control_params *dc, int will_wait)
37 int pid_fd = open(dc->pid_file, O_RDONLY);
42 daemon_control_err(dc, "Cannot open PID file `%s': %m", dc->pid_file);
46 if (flock(pid_fd, LOCK_EX | (will_wait ? 0 : LOCK_NB)) >= 0)
48 // The lock file is stale
53 if (errno != EINTR && errno != EWOULDBLOCK)
55 daemon_control_err(dc, "Cannot lock PID file `%s': %m", dc->pid_file);
60 int n = read(pid_fd, buf, sizeof(buf));
63 daemon_control_err(dc, "Error reading `%s': %m", dc->pid_file);
66 if (n == (int) sizeof(buf))
68 daemon_control_err(dc, "PID file `%s' is too long", dc->pid_file);
75 daemon_control_err(dc, "PID file `%s' does not contain a valid PID", dc->pid_file);
86 enum daemon_control_status
87 daemon_control(struct daemon_control_params *dc)
89 enum daemon_control_status st = DAEMON_STATUS_ERROR;
91 int guard_fd = open(dc->guard_file, O_RDWR | O_CREAT, 0666);
93 return daemon_control_err(dc, "Cannot open guard file `%s': %m", dc->guard_file);
94 if (flock(guard_fd, LOCK_EX) < 0)
95 return daemon_control_err(dc, "Cannot lock guard file `%s': %m", dc->guard_file);
98 int pid = daemon_read_pid(dc, 0);
104 case DAEMON_CONTROL_CHECK:
106 st = DAEMON_STATUS_OK;
108 st = DAEMON_STATUS_NOT_RUNNING;
110 case DAEMON_CONTROL_START:
112 st = DAEMON_STATUS_ALREADY_DONE;
118 daemon_control_err(dc, "Cannot fork: %m");
124 execvp(dc->argv[0], dc->argv);
125 fprintf(stderr, "Cannot execute `%s': %m\n", dc->argv[0]);
126 exit(DAEMON_STATUS_ERROR);
129 int ec = waitpid(pp, &stat, 0);
132 daemon_control_err(dc, "Cannot wait: %m");
135 if (WIFEXITED(stat) && WEXITSTATUS(stat) == DAEMON_STATUS_ERROR)
137 daemon_control_err(dc, "Cannot execute the daemon");
140 char ecmsg[EXIT_STATUS_MSG_SIZE];
141 if (format_exit_status(ecmsg, stat))
143 daemon_control_err(dc, "Daemon %s", ecmsg);
146 pid = daemon_read_pid(dc, 0);
148 daemon_control_err(dc, "Daemon failed to write the PID file `%s'", dc->pid_file);
150 st = DAEMON_STATUS_OK;
153 case DAEMON_CONTROL_STOP:
155 return DAEMON_STATUS_ALREADY_DONE;
156 int sig = dc->signal ? : SIGTERM;
157 if (kill(pid, sig) < 0)
159 daemon_control_err(dc, "Cannot send signal %d: %m", dc->signal);
162 pid = daemon_read_pid(dc, 1);
165 st = DAEMON_STATUS_OK;
167 case DAEMON_CONTROL_SIGNAL:
169 return DAEMON_STATUS_NOT_RUNNING;
170 if (kill(pid, dc->signal) < 0)
171 daemon_control_err(dc, "Cannot send signal %d: %m", dc->signal);
173 st = DAEMON_STATUS_OK;