X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=src%2Fdaemon%2Fcollectd.c;h=9cba9132814cbcafa97ddf92f6289c5bd9c0991d;hb=010ac3193d5bd761146faec22c5591335cf866c7;hp=2e2d821aade194873c923ceabcf8951291d0dc69;hpb=216c6246b73645ac093de15b87aedc9abc6ebc80;p=collectd.git diff --git a/src/daemon/collectd.c b/src/daemon/collectd.c index 2e2d821a..9cba9132 100644 --- a/src/daemon/collectd.c +++ b/src/daemon/collectd.c @@ -33,6 +33,7 @@ #include #include +#include #include #include @@ -191,7 +192,7 @@ static int change_basedir (const char *orig_dir) sstrerror (errno, errbuf, sizeof (errbuf))); return (-1); } - + dirlen = strlen (dir); while ((dirlen > 0) && (dir[dirlen - 1] == '/')) dir[--dirlen] = '\0'; @@ -270,7 +271,7 @@ static void update_kstat (void) static void exit_usage (int status) { printf ("Usage: "PACKAGE" [OPTIONS]\n\n" - + "Available options:\n" " General:\n" " -C Configuration file.\n" @@ -307,7 +308,11 @@ static int do_init (void) #endif #if HAVE_LIBSTATGRAB - if (sg_init ()) + if (sg_init ( +# if HAVE_LIBSTATGRAB_INIT_ARG + 0 +# endif + )) { ERROR ("sg_init: %s", sg_str_error (sg_get_error ())); return (-1); @@ -409,6 +414,72 @@ static int pidfile_remove (void) } /* static int pidfile_remove (const char *file) */ #endif /* COLLECT_DAEMON */ +int notify_upstart (void) +{ + const char *upstart_job = getenv("UPSTART_JOB"); + + if (upstart_job == NULL) + return 0; + + if (strcmp(upstart_job, "collectd") != 0) + return 0; + + WARNING ("supervised by upstart, will stop to signal readyness"); + raise(SIGSTOP); + unsetenv("UPSTART_JOB"); + + return 1; +} + +int notify_systemd (void) +{ + int fd = -1; + const char *notifysocket = getenv("NOTIFY_SOCKET"); + struct sockaddr_un su; + struct iovec iov; + struct msghdr hdr; + + if (notifysocket == NULL) + return 0; + + if ((strchr("@/", notifysocket[0])) == NULL || + strlen(notifysocket) < 2) + return 0; + + WARNING ("supervised by systemd, will signal readyness"); + if ((fd = socket(AF_UNIX, SOCK_DGRAM, 0)) < 0) { + WARNING ("cannot contact systemd socket %s", notifysocket); + return 0; + } + + bzero(&su, sizeof(su)); + su.sun_family = AF_UNIX; + sstrncpy (su.sun_path, notifysocket, sizeof(su.sun_path)); + + if (notifysocket[0] == '@') + su.sun_path[0] = 0; + + bzero(&iov, sizeof(iov)); + iov.iov_base = "READY=1"; + iov.iov_len = strlen("READY=1"); + + bzero(&hdr, sizeof(hdr)); + hdr.msg_name = &su; + hdr.msg_namelen = offsetof(struct sockaddr_un, sun_path) + + strlen(notifysocket); + hdr.msg_iov = &iov; + hdr.msg_iovlen = 1; + + unsetenv("NOTIFY_SOCKET"); + if (sendmsg(fd, &hdr, MSG_NOSIGNAL) < 0) { + WARNING ("cannot send notification to systemd"); + close(fd); + return 0; + } + close(fd); + return 1; +} + int main (int argc, char **argv) { struct sigaction sig_int_action; @@ -525,7 +596,11 @@ int main (int argc, char **argv) sig_chld_action.sa_handler = SIG_IGN; sigaction (SIGCHLD, &sig_chld_action, NULL); - if (daemonize) + /* + * Only daemonize if we're not being supervised + * by upstart or systemd. + */ + if (daemonize && notify_upstart() == 0 && notify_systemd() == 0) { if ((pid = fork ()) == -1) {