diff options
author | Lennart Poettering <lennart@poettering.net> | 2016-12-06 18:19:23 +0100 |
---|---|---|
committer | Lennart Poettering <lennart@poettering.net> | 2016-12-14 18:29:30 +0100 |
commit | 75bf701f5c5ff4ce0679d7bcc7000aa497e1f6ad (patch) | |
tree | dd3081b57363462b6460470d62758d1b4fe353a8 /src/nspawn | |
parent | 8d6e80343a1463afbaed1beca4b18c49ce056034 (diff) |
nspawn: flush out environment block of the -a stub init process
The container detection code in virt.c we ship checks for /proc/1/environ,
looking for "container=" in it. Let's make sure our "-a" init stub exposes that
correctly.
Without this "systemd-detect-virt" run in a "-a" container won't detect that it
is being run in a container.
Diffstat (limited to 'src/nspawn')
-rw-r--r-- | src/nspawn/nspawn-stub-pid1.c | 29 | ||||
-rw-r--r-- | src/nspawn/nspawn-stub-pid1.h | 4 | ||||
-rw-r--r-- | src/nspawn/nspawn.c | 2 |
3 files changed, 32 insertions, 3 deletions
diff --git a/src/nspawn/nspawn-stub-pid1.c b/src/nspawn/nspawn-stub-pid1.c index 2de87e3c63..38ab37367e 100644 --- a/src/nspawn/nspawn-stub-pid1.c +++ b/src/nspawn/nspawn-stub-pid1.c @@ -20,6 +20,7 @@ #include <sys/reboot.h> #include <sys/unistd.h> #include <sys/wait.h> +#include <sys/prctl.h> #include "fd-util.h" #include "log.h" @@ -29,7 +30,22 @@ #include "time-util.h" #include "def.h" -int stub_pid1(void) { +static int reset_environ(const char *new_environment, size_t length) { + unsigned long start, end; + + start = (unsigned long) new_environment; + end = start + length; + + if (prctl(PR_SET_MM, PR_SET_MM_ENV_START, start, 0, 0) < 0) + return -errno; + + if (prctl(PR_SET_MM, PR_SET_MM_ENV_END, end, 0, 0) < 0) + return -errno; + + return 0; +} + +int stub_pid1(sd_id128_t uuid) { enum { STATE_RUNNING, STATE_REBOOT, @@ -41,6 +57,11 @@ int stub_pid1(void) { pid_t pid; int r; + /* The new environment we set up, on the stack. */ + char new_environment[] = + "container=systemd-nspawn\0" + "container_uuid=XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; + /* Implements a stub PID 1, that reaps all processes and processes a couple of standard signals. This is useful * for allowing arbitrary processes run in a container, and still have all zombies reaped. */ @@ -64,6 +85,12 @@ int stub_pid1(void) { close_all_fds(NULL, 0); log_open(); + /* Flush out /proc/self/environ, so that we don't leak the environment from the host into the container. Also, + * set $container= and $container_uuid= so that clients in the container that query it from /proc/1/environ + * find them set set. */ + sd_id128_to_string(uuid, new_environment + sizeof(new_environment) - SD_ID128_STRING_MAX); + reset_environ(new_environment, sizeof(new_environment)); + rename_process("STUBINIT"); assert_se(sigemptyset(&waitmask) >= 0); diff --git a/src/nspawn/nspawn-stub-pid1.h b/src/nspawn/nspawn-stub-pid1.h index 36c1aaf5dd..7ca83078c0 100644 --- a/src/nspawn/nspawn-stub-pid1.h +++ b/src/nspawn/nspawn-stub-pid1.h @@ -19,4 +19,6 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>. ***/ -int stub_pid1(void); +#include "sd-id128.h" + +int stub_pid1(sd_id128_t uuid); diff --git a/src/nspawn/nspawn.c b/src/nspawn/nspawn.c index 080bd7c31e..dcc639f15c 100644 --- a/src/nspawn/nspawn.c +++ b/src/nspawn/nspawn.c @@ -2278,7 +2278,7 @@ static int inner_child( return log_error_errno(errno, "Failed to change to specified working directory %s: %m", arg_chdir); if (arg_start_mode == START_PID2) { - r = stub_pid1(); + r = stub_pid1(arg_uuid); if (r < 0) return r; } |