[sheepdog] [PATCH v2 1/2] sheep: shutdown gracefully when we receive SIGTERM

Liu Yuan namei.unix at gmail.com
Tue Jul 24 03:33:36 CEST 2012


From: Liu Yuan <tailai.ly at taobao.com>

Signed-off-by: Liu Yuan <tailai.ly at taobao.com>
---
 sheep/sheep.c |   56 +++++++++++++++++++++++++++++++++++++++++++++++++++-----
 1 file changed, 51 insertions(+), 5 deletions(-)

diff --git a/sheep/sheep.c b/sheep/sheep.c
index 3ae1ec9..df28a94 100644
--- a/sheep/sheep.c
+++ b/sheep/sheep.c
@@ -21,6 +21,7 @@
 #include <sys/syslog.h>
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <sys/signalfd.h>
 #include <fcntl.h>
 #include <errno.h>
 
@@ -122,9 +123,54 @@ static int create_pidfile(const char *filename)
 	return 0;
 }
 
+static int sigfd;
+
+static void signal_handler(int listen_fd, int events, void *data)
+{
+	struct signalfd_siginfo siginfo;
+	int ret;
+
+	ret = read(sigfd, &siginfo, sizeof(siginfo));
+	assert(ret == sizeof(siginfo));
+	dprintf("signal %d\n", siginfo.ssi_signo);
+	switch (siginfo.ssi_signo) {
+	case SIGTERM:
+		sys->status= SD_STATUS_KILLED;
+		break;
+	default:
+		eprintf("signal %d unhandled \n", siginfo.ssi_signo);
+		break;
+	}
+}
+
 static int init_signal(void)
 {
-	return trace_init_signal();
+	sigset_t mask;
+	int ret;
+
+	ret = trace_init_signal();
+	if (ret)
+		return ret;
+
+	sigemptyset(&mask);
+	sigaddset(&mask, SIGTERM);
+	sigprocmask(SIG_BLOCK, &mask, NULL);
+
+	sigfd = signalfd(-1, &mask, SFD_NONBLOCK);
+	if (sigfd < 0) {
+		eprintf("failed to create a signal fd: %m\n");
+		return -1;
+	}
+
+	ret = register_event(sigfd, signal_handler, NULL);
+	if (ret) {
+		eprintf("failed to register signal handler (%d)\n", ret);
+		return -1;
+	}
+
+	dprintf("register signal_handler for %d\n", sigfd);
+
+	return 0;
 }
 
 static struct cluster_info __sys;
@@ -289,6 +335,10 @@ int main(int argc, char **argv)
 
 	local_req_init();
 
+	ret = init_signal();
+	if (ret)
+		exit(1);
+
 	sys->gateway_wqueue = init_work_queue("gateway", false);
 	sys->io_wqueue = init_work_queue("io", false);
 	sys->recovery_wqueue = init_work_queue("recovery", true);
@@ -298,10 +348,6 @@ int main(int argc, char **argv)
 	    !sys->deletion_wqueue || !sys->block_wqueue)
 		exit(1);
 
-	ret = init_signal();
-	if (ret)
-		exit(1);
-
 	ret = trace_init();
 	if (ret)
 		exit(1);
-- 
1.7.10.2




More information about the sheepdog mailing list