[Ocfs2-tools-devel] [PATCH] o2hbmonitor: add semaphore

Srinivas Eeda srinivas.eeda at oracle.com
Mon Jan 3 16:35:59 PST 2011


add semaphore to limit to one o2hbmonitor per node

Signed-off-by: Srinivas Eeda <srinivas.eeda at oracle.com>
---
 o2monitor/o2hbmonitor.c |   64 +++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 64 insertions(+), 0 deletions(-)

diff --git a/o2monitor/o2hbmonitor.c b/o2monitor/o2hbmonitor.c
index 5bb5590..dc222f1 100644
--- a/o2monitor/o2hbmonitor.c
+++ b/o2monitor/o2hbmonitor.c
@@ -43,6 +43,8 @@
 #include <libgen.h>
 #include <syslog.h>
 #include <errno.h>
+#include <sys/ipc.h>
+#include <sys/sem.h>
 
 #define SYS_CONFIG_DIR			"/sys/kernel/config"
 #define O2HB_CLUSTER_DIR		SYS_CONFIG_DIR"/cluster"
@@ -61,6 +63,8 @@
 #define SLOW_POLL_IN_SECS		10
 #define FAST_POLL_IN_SECS		2
 
+#define O2HB_SEM_MAGIC_KEY		0x6F326862
+
 char *progname;
 int interactive;
 int warn_threshold_percent;
@@ -300,6 +304,53 @@ static void monitor(void)
 	}
 }
 
+static int islocked(void)
+{
+	int semid;
+	struct sembuf trylock[1] = {
+		{.sem_num = 0, .sem_op = 0, .sem_flg = SEM_UNDO|IPC_NOWAIT},
+	};
+
+	semid = semget(O2HB_SEM_MAGIC_KEY, 1, 0);
+	if (semid < 0)
+		return 0;
+	if (semop(semid, trylock, 1) < 0)
+		return 1;
+	return 0;
+}
+
+static int getlock(void)
+{
+	int ret, semid, vals[1] = { 0 };
+	struct sembuf trylock[2] = {
+		{.sem_num = 0, .sem_op = 0, .sem_flg = SEM_UNDO|IPC_NOWAIT},
+		{.sem_num = 0, .sem_op = 1, .sem_flg = SEM_UNDO|IPC_NOWAIT},
+	};
+
+	semid = semget(O2HB_SEM_MAGIC_KEY, 1, 0);
+	if (semid < 0) {
+		semid = semget(O2HB_SEM_MAGIC_KEY, 1,
+			       IPC_CREAT|IPC_EXCL|S_IRUSR);
+		if (semid < 0)
+			goto out;
+		semctl(semid, 0, SETALL, vals);
+		if (semop(semid, trylock, 2) < 0)
+			goto out;
+		else
+			return 0;
+	}
+	if (semop(semid, trylock, 2) < 0)
+		goto out;
+	return 0;
+out:
+	ret = errno;
+	if (ret == EAGAIN) {
+		syslog(LOG_WARNING, "Another instance of %s is already running."
+		       " Aborting.\n", progname);
+	}
+	return errno;
+}
+
 static void usage(void)
 {
 	fprintf(stderr, "usage: %s [-w percent] -[ivV]\n", progname);
@@ -352,6 +403,12 @@ int main(int argc, char **argv)
 	if (version)
 		show_version();
 
+	if (islocked()) {
+		fprintf(stderr, "Another instance of %s is already running. "
+		       "Aborting.\n", progname);
+		return 1;
+	}
+
 	if (!interactive) {
 		ret = daemon(0, verbose);
 		if (ret)
@@ -360,6 +417,13 @@ int main(int argc, char **argv)
 	}
 
 	openlog(progname, LOG_CONS|LOG_NDELAY, LOG_DAEMON);
+	ret = getlock();
+	if (ret == EAGAIN) {
+		closelog();
+		return ret;
+	}
+
+	syslog(LOG_INFO, "Starting\n");
 	monitor();
 	closelog();
 
-- 
1.5.6.5




More information about the Ocfs2-tools-devel mailing list