[lxc-devel] [PATCH] rootfs pinning: make file hidden, don't delete it, encode pid
Christian Seiler
christian at iwakd.de
Sat Sep 28 06:36:34 UTC 2013
This makes the following changes to the rootfs pinning mechanism:
- Contrary to a recent change, the file will not be deleted
immediately after creation. This should make NFS happy.
- To reduce nuissance for administrators, make the file hidden by
default.
- Delete the file at container shutdown. (i.e. clean up after oneself)
- Because the file is now deleted, and a rootfs could be shared
between containers, the filename now encodes the pid of the
lxc-start process, so that the rw-hold on the filesystem will only
be removed once the last container exits.
Signed-off-by: Christian Seiler <christian at iwakd.de>
---
src/lxc/conf.c | 24 +++++++++++++++---------
src/lxc/conf.h | 2 +-
src/lxc/start.c | 10 +++++++++-
src/lxc/start.h | 1 +
4 files changed, 26 insertions(+), 11 deletions(-)
diff --git a/src/lxc/conf.c b/src/lxc/conf.c
index ecbcf41..4cd9462 100644
--- a/src/lxc/conf.c
+++ b/src/lxc/conf.c
@@ -695,15 +695,18 @@ static int mount_rootfs_block(const char *rootfs, const char *target)
/*
* pin_rootfs
- * if rootfs is a directory, then open ${rootfs}/lxc.hold for writing for
- * the duration of the container run, to prevent the container from marking
- * the underlying fs readonly on shutdown. unlink the file immediately so
- * no name pollution is happens
+ * if rootfs is a directory, then open ${rootfs}/.lxc-hold-$pid for writing
+ * for the duration of the container run, to prevent the container from
+ * marking the underlying fs readonly on shutdown. $pid is the pid of
+ * lxc-start. At shutdown the hold file will be removed again. The pid is
+ * encoded in the filename, so that if multiple containers use the same
+ * root filesystem, a hold will be kept open until the last container is
+ * stopped.
* return -1 on error.
* return -2 if nothing needed to be pinned.
* return an open fd (>=0) if we pinned it.
*/
-int pin_rootfs(const char *rootfs)
+int pin_rootfs(const char *rootfs, char **filename_ptr)
{
char absrootfs[MAXPATHLEN];
char absrootfspin[MAXPATHLEN];
@@ -725,16 +728,19 @@ int pin_rootfs(const char *rootfs)
if (!S_ISDIR(s.st_mode))
return -2;
- ret = snprintf(absrootfspin, MAXPATHLEN, "%s/lxc.hold", absrootfs);
+ ret = snprintf(absrootfspin, MAXPATHLEN, "%s/.lxc-hold-%lu", absrootfs, (unsigned long)getpid());
if (ret >= MAXPATHLEN)
return -1;
+ if (filename_ptr) {
+ *filename_ptr = strdup(absrootfspin);
+ if (!*filename_ptr)
+ return -1;
+ }
+
process_lock();
fd = open(absrootfspin, O_CREAT | O_RDWR, S_IWUSR|S_IRUSR);
process_unlock();
- if (fd < 0)
- return fd;
- (void)unlink(absrootfspin);
return fd;
}
diff --git a/src/lxc/conf.h b/src/lxc/conf.h
index 84acce8..e3a962a 100644
--- a/src/lxc/conf.h
+++ b/src/lxc/conf.h
@@ -331,7 +331,7 @@ extern int detect_shared_rootfs(void);
extern struct lxc_conf *lxc_conf_init(void);
extern void lxc_conf_free(struct lxc_conf *conf);
-extern int pin_rootfs(const char *rootfs);
+extern int pin_rootfs(const char *rootfs, char **filename_ptr);
extern int lxc_create_network(struct lxc_handler *handler);
extern void lxc_delete_network(struct lxc_handler *handler);
diff --git a/src/lxc/start.c b/src/lxc/start.c
index 7538403..26c71c4 100644
--- a/src/lxc/start.c
+++ b/src/lxc/start.c
@@ -386,6 +386,14 @@ static void lxc_fini(const char *name, struct lxc_handler *handler)
if (run_lxc_hooks(name, "post-stop", handler->conf, handler->lxcpath, NULL))
ERROR("failed to run post-stop hooks for container '%s'.", name);
+ /* remove rootfs pin file after we shutdown this
+ * container
+ */
+ if (handler->pin_filename) {
+ unlink(handler->pin_filename);
+ free(handler->pin_filename);
+ }
+
/* reset mask set by setup_signal_fd */
if (sigprocmask(SIG_SETMASK, &handler->oldmask, NULL))
WARN("failed to restore sigprocmask");
@@ -708,7 +716,7 @@ int lxc_spawn(struct lxc_handler *handler)
* marking it readonly.
*/
- handler->pinfd = pin_rootfs(handler->conf->rootfs.path);
+ handler->pinfd = pin_rootfs(handler->conf->rootfs.path, &handler->pin_filename);
if (handler->pinfd == -1)
INFO("failed to pin the container's rootfs");
diff --git a/src/lxc/start.h b/src/lxc/start.h
index c35c5c4..345b4e0 100644
--- a/src/lxc/start.h
+++ b/src/lxc/start.h
@@ -50,6 +50,7 @@ struct lxc_handler {
struct lxc_operations *ops;
void *data;
int sv[2];
+ char *pin_filename;
int pinfd;
const char *lxcpath;
struct cgroup_process_info *cgroup;
--
1.7.10.4
More information about the lxc-devel
mailing list