2007-12-10 19:25:55

by Steve Dickson

[permalink] [raw]
Subject: [PATCH] nfs-utils: sm-notify does not remove its pid file.

It turns out that the sm-notify command, used to notify clients that
they need to reclaim their locks because the server just changed
state, does not clean up its pid file. The pid file is used to ensure
only one instance of the process is running. This results in sm-notify
exiting before notifying any clients on the second reboot.

I also changed the directory in which the pid file is created from
/var/run into BASEDIR so the file can be removed after the after the
user id is changed to a non-root uid.

steved.


commit 72e24403c298b7991eb04dd68ed2e9fcbe4baf70
Author: Steve Dickson <[email protected]>
Date: Mon Dec 10 12:17:29 2007 -0500

Make sure sm-notify's pid file is removed when the process
exits. Also moved the pid file from /var/run into BASEDIR
so the file can be removed after the user id is changed
to a non-root uid.

Signed-off-by: Steve Dickson <[email protected]>

diff --git a/utils/statd/sm-notify.c b/utils/statd/sm-notify.c
index bb67c37..3f80e04 100644
--- a/utils/statd/sm-notify.c
+++ b/utils/statd/sm-notify.c
@@ -32,6 +32,10 @@
# endif
#endif

+#ifndef PIDFILE
+#define PIDFILE BASEDIR "/sm-notify.pid"
+#endif
+
#define DEFAULT_SM_STATE_PATH BASEDIR "/state"
#define DEFAULT_SM_DIR_PATH BASEDIR "/sm"
#define DEFAULT_SM_BAK_PATH DEFAULT_SM_DIR_PATH ".bak"
@@ -89,6 +93,7 @@ void nsm_log(int fac, const char *fmt, ...);
static int record_pid(void);
static void drop_privs(void);
static void set_kernel_nsm_state(int state);
+static void remove_pid(void);

static struct nsm_host * hosts = NULL;

@@ -155,6 +160,7 @@ usage: fprintf(stderr,
/* already run, don't try again */
exit(0);
}
+ atexit(remove_pid);

if (opt_srcaddr) {
strncpy(nsm_hostname, opt_srcaddr, sizeof(nsm_hostname)-1);
@@ -736,13 +742,19 @@ static int record_pid(void)
int fd;

snprintf(pid, 20, "%d\n", getpid());
- fd = open("/var/run/sm-notify.pid", O_CREAT|O_EXCL|O_WRONLY, 0600);
+ fd = open(PIDFILE, O_CREAT|O_EXCL|O_WRONLY, 0600);
if (fd < 0)
return 0;
write(fd, pid, strlen(pid));
close(fd);
return 1;
}
+static void remove_pid()
+{
+ if (unlink(PIDFILE) < 0)
+ nsm_log(LOG_WARNING,
+ "Unable to remove %s: %s", PIDFILE, strerror(errno));
+}

/* Drop privileges to match owner of state-directory
* (in case a reply triggers some unknown bug).