[lxc-devel] [lxc/master] conf: always send response to parent waiting for devptfs_fd

brauner on Github lxc-bot at linuxcontainers.org
Tue Oct 20 11:34:43 UTC 2020


A non-text attachment was scrubbed...
Name: not available
Type: text/x-mailbox
Size: 591 bytes
Desc: not available
URL: <http://lists.linuxcontainers.org/pipermail/lxc-devel/attachments/20201020/c96e03e6/attachment.bin>
-------------- next part --------------
From 68f3899e4aad1695fd31e5da47dcf3897d2ae2d9 Mon Sep 17 00:00:00 2001
From: Christian Brauner <christian.brauner at ubuntu.com>
Date: Tue, 20 Oct 2020 13:02:00 +0200
Subject: [PATCH] conf: always send response to parent waiting for devptfs_fd

When no devpts devices are requested we used to return early but did not send a
response to the parent. This is a problem because the parent will be waiting
for a devpts fd to be sent. Make sure to always send a response.

Signed-off-by: Christian Brauner <christian.brauner at ubuntu.com>
---
 src/lxc/conf.c  | 34 ++++++++++++++++++++++++++--------
 src/lxc/conf.h  |  2 ++
 src/lxc/start.c |  5 +----
 3 files changed, 29 insertions(+), 12 deletions(-)

diff --git a/src/lxc/conf.c b/src/lxc/conf.c
index b8058ffdce..e006ea4391 100644
--- a/src/lxc/conf.c
+++ b/src/lxc/conf.c
@@ -1477,7 +1477,23 @@ static const struct id_map *find_mapped_nsid_entry(const struct lxc_conf *conf,
 	return retmap;
 }
 
-static int lxc_setup_devpts(struct lxc_handler *handler)
+int lxc_setup_devpts_parent(struct lxc_handler *handler)
+{
+	int ret;
+
+	if (handler->conf->pty_max <= 0)
+		return 0;
+
+	ret = lxc_abstract_unix_recv_fds(handler->data_sock[1], &handler->conf->devpts_fd, 1,
+					 &handler->conf->devpts_fd, sizeof(handler->conf->devpts_fd));
+	if (ret < 0)
+		return log_error_errno(-1, errno, "Failed to receive devpts fd from child");
+
+	TRACE("Received devpts file descriptor %d from child", handler->conf->devpts_fd);
+	return 0;
+}
+
+static int lxc_setup_devpts_child(struct lxc_handler *handler)
 {
 	__do_close int devpts_fd = -EBADF;
 	int ret;
@@ -1533,13 +1549,7 @@ static int lxc_setup_devpts(struct lxc_handler *handler)
 	if (devpts_fd < 0) {
 		devpts_fd = -EBADF;
 		TRACE("Failed to create detached devpts mount");
-		ret = lxc_abstract_unix_send_fds(sock, NULL, 0, &devpts_fd, sizeof(int));
-	} else {
-		ret = lxc_abstract_unix_send_fds(sock, &devpts_fd, 1, NULL, 0);
 	}
-	if (ret < 0)
-		return log_error_errno(-1, errno, "Failed to send devpts fd to parent");
-	TRACE("Sent devpts file descriptor %d to parent", devpts_fd);
 
 	/* Remove any pre-existing /dev/ptmx file. */
 	ret = remove("/dev/ptmx");
@@ -1575,6 +1585,14 @@ static int lxc_setup_devpts(struct lxc_handler *handler)
 		return log_error_errno(-1, errno, "Failed to create symlink from \"/dev/ptmx\" to \"/dev/pts/ptmx\"");
 	DEBUG("Created symlink from \"/dev/ptmx\" to \"/dev/pts/ptmx\"");
 
+	if (devpts_fd < 0)
+		ret = lxc_abstract_unix_send_fds(sock, NULL, 0, &devpts_fd, sizeof(int));
+	else
+		ret = lxc_abstract_unix_send_fds(sock, &devpts_fd, 1, NULL, 0);
+	if (ret < 0)
+		return log_error_errno(-1, errno, "Failed to send devpts fd to parent");
+
+	TRACE("Sent devpts file descriptor %d to parent", devpts_fd);
 	return 0;
 }
 
@@ -3392,7 +3410,7 @@ int lxc_setup(struct lxc_handler *handler)
 	if (lxc_conf->autodev > 0)
 		(void)lxc_setup_boot_id();
 
-	ret = lxc_setup_devpts(handler);
+	ret = lxc_setup_devpts_child(handler);
 	if (ret < 0)
 		return log_error(-1, "Failed to setup new devpts instance");
 
diff --git a/src/lxc/conf.h b/src/lxc/conf.h
index cd54b3fe0f..ba06d42dc0 100644
--- a/src/lxc/conf.h
+++ b/src/lxc/conf.h
@@ -490,4 +490,6 @@ static inline int chown_mapped_root(const char *path, const struct lxc_conf *con
 	return userns_exec_mapped_root(path, -EBADF, conf);
 }
 
+__hidden int lxc_setup_devpts_parent(struct lxc_handler *handler);
+
 #endif /* __LXC_CONF_H */
diff --git a/src/lxc/start.c b/src/lxc/start.c
index 7b29d40834..7bf7f8a2fb 100644
--- a/src/lxc/start.c
+++ b/src/lxc/start.c
@@ -1953,14 +1953,11 @@ static int lxc_spawn(struct lxc_handler *handler)
 		}
 	}
 
-	ret = lxc_abstract_unix_recv_fds(data_sock1, &handler->conf->devpts_fd, 1,
-					 &handler->conf->devpts_fd,
-					 sizeof(handler->conf->devpts_fd));
+	ret = lxc_setup_devpts_parent(handler);
 	if (ret < 0) {
 		SYSERROR("Failed to receive devpts fd from child");
 		goto out_delete_net;
 	}
-	TRACE("Received devpts file descriptor %d from child", handler->conf->devpts_fd);
 
 	/* Now all networks are created, network devices are moved into place,
 	 * and the correct names and ifindices in the respective namespaces have


More information about the lxc-devel mailing list