summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuke Shumaker <lukeshu@lukeshu.com>2017-06-16 16:53:00 -0400
committerLuke Shumaker <lukeshu@lukeshu.com>2017-06-16 17:06:57 -0400
commit76b7be5e7e8bd15b549aa12eabbe3a36fdc4e924 (patch)
tree098e1bdc51eb8954d6f4035d8d0e4a7192e9a602
parentc4f1e6445be169b5f4d0016de11016bd0c17a39c (diff)
nspawn: Don't expect the outer child die until after the inner is cgroupified
-rw-r--r--src/nspawn/nspawn.c55
1 files changed, 24 insertions, 31 deletions
diff --git a/src/nspawn/nspawn.c b/src/nspawn/nspawn.c
index 2c3fc4659a..5c4341e0ee 100644
--- a/src/nspawn/nspawn.c
+++ b/src/nspawn/nspawn.c
@@ -2674,15 +2674,15 @@ static int inner_child(
assert(directory);
assert(kmsg_socket >= 0);
- if (arg_userns_mode != USER_NAMESPACE_NO) {
- /* Tell the parent, that it now can write the UID map. */
- (void) barrier_place(barrier); /* #1 */
+ /* Tell the parent that it can now configure our process; write
+ * the UID map (if use_userns), place us in the correct cgroup (if
+ * use_cgns), et c. */
+ (void) barrier_place(barrier); /* #1 */
- /* Wait until the parent wrote the UID map */
- if (!barrier_place_and_sync(barrier)) { /* #2 */
- log_error("Parent died too early");
- return -ESRCH;
- }
+ /* Wait until the parent says that we are fully configured. */
+ if (!barrier_place_and_sync(barrier)) { /* #2 */
+ log_error("Parent died too early");
+ return -ESRCH;
}
r = reset_uid_gid();
@@ -2702,13 +2702,6 @@ static int inner_child(
if (r < 0)
return r;
- /* Wait until we are cgroup-ified, so that we
- * can mount the right cgroup path writable */
- if (!barrier_place_and_sync(barrier)) { /* #3 */
- log_error("Parent died too early");
- return -ESRCH;
- }
-
if (arg_use_cgns) {
r = unshare(CLONE_NEWCGROUP);
if (r < 0)
@@ -2814,7 +2807,7 @@ static int inner_child(
/* Let the parent know that we are ready and
* wait until the parent is ready with the
* setup, too... */
- if (!barrier_place_and_sync(barrier)) { /* #4 */
+ if (!barrier_place_and_sync(barrier)) { /* #3 */
log_error("Parent died too early");
return -ESRCH;
}
@@ -3765,12 +3758,6 @@ static int run(int master,
}
}
- /* Wait for the outer child. */
- r = wait_for_terminate_and_warn("namespace helper", *helper_pid, NULL);
- *helper_pid = 0;
- if (r != 0)
- return r < 0 ? r : -EIO;
-
/* And now retrieve the PID of the inner child. */
l = recv(pid_socket_pair[0], main_pid, sizeof *main_pid, 0);
if (l < 0)
@@ -3797,17 +3784,16 @@ static int run(int master,
log_debug("Init process invoked as PID "PID_FMT, *main_pid);
- if (arg_userns_mode != USER_NAMESPACE_NO) {
- if (!barrier_place_and_sync(&barrier)) { /* #1 */
- log_error("Child died too early.");
- return -ESRCH;
- }
+ /* Wait until the child gives us the OK to configure it. */
+ if (!barrier_place_and_sync(&barrier)) { /* #1 */
+ log_error("Child died too early.");
+ return -ESRCH;
+ }
+ if (arg_userns_mode != USER_NAMESPACE_NO) {
r = setup_uid_map(*main_pid);
if (r < 0)
return r;
-
- (void) barrier_place(&barrier); /* #2 */
}
if (arg_private_network) {
@@ -3881,11 +3867,18 @@ static int run(int master,
if (r < 0)
return r;
+
+ /* Wait for the outer child. */
+ r = wait_for_terminate_and_warn("namespace helper", *helper_pid, NULL);
+ *helper_pid = 0;
+ if (r != 0)
+ return r < 0 ? r : -EIO;
+
/* Notify the child that the parent is ready with all
* its setup (including cgroup-ification), and that
* the child can now hand over control to the code to
* run inside the container. */
- (void) barrier_place(&barrier); /* #3 */
+ (void) barrier_place(&barrier); /* #2 */
/* Block SIGCHLD here, before notifying child.
* process_pty() will handle it with the other signals. */
@@ -3905,7 +3898,7 @@ static int run(int master,
return r;
/* Let the child know that we are ready and wait that the child is completely ready now. */
- if (!barrier_place_and_sync(&barrier)) { /* #4 */
+ if (!barrier_place_and_sync(&barrier)) { /* #3 */
log_error("Child died too early.");
return -ESRCH;
}