]> git.ipfire.org Git - thirdparty/lxc.git/commitdiff
lxc-start: Add command to retrieve the clone flags used to start the container.
authorChristian Seiler <christian@iwakd.de>
Tue, 21 Aug 2012 22:03:11 +0000 (00:03 +0200)
committerStéphane Graber <stgraber@ubuntu.com>
Mon, 12 Nov 2012 18:13:52 +0000 (13:13 -0500)
Add the LXC_COMMAND_CLONE_FLAGS that retrieves the flags passed to clone(2)
when the container was started. This allows external programs to determine
which namespaces the container was unshared from.

Signed-off-by: Christian Seiler <christian@iwakd.de>
Cc: Daniel Lezcano <daniel.lezcano@free.fr>
Acked-by: Serge Hallyn <serge.hallyn@canonical.com>
src/lxc/commands.c
src/lxc/commands.h
src/lxc/start.c
src/lxc/start.h

index cce24db0fc74f281e0c7d4a1fb8c7c20f4f1e11c..dc93815319dc61704c5ce4c669b20f64a27160a4 100644 (file)
@@ -154,11 +154,32 @@ pid_t get_init_pid(const char *name)
        return command.answer.pid;
 }
 
+int lxc_get_clone_flags(const char *name)
+{
+       struct lxc_command command = {
+               .request = { .type = LXC_COMMAND_CLONE_FLAGS },
+       };
+
+       int ret, stopped = 0;
+
+       ret = lxc_command(name, &command, &stopped);
+       if (ret < 0 && stopped)
+               return -1;
+
+       if (ret < 0) {
+               ERROR("failed to send command");
+               return -1;
+       }
+
+       return command.answer.ret;
+}
+
 extern void lxc_console_remove_fd(int, struct lxc_tty_info *);
 extern int  lxc_console_callback(int, struct lxc_request *, struct lxc_handler *);
 extern int  lxc_stop_callback(int, struct lxc_request *, struct lxc_handler *);
 extern int  lxc_state_callback(int, struct lxc_request *, struct lxc_handler *);
 extern int  lxc_pid_callback(int, struct lxc_request *, struct lxc_handler *);
+extern int  lxc_clone_flags_callback(int, struct lxc_request *, struct lxc_handler *);
 
 static int trigger_command(int fd, struct lxc_request *request,
                           struct lxc_handler *handler)
@@ -166,10 +187,11 @@ static int trigger_command(int fd, struct lxc_request *request,
        typedef int (*callback)(int, struct lxc_request *, struct lxc_handler *);
 
        callback cb[LXC_COMMAND_MAX] = {
-               [LXC_COMMAND_TTY]   = lxc_console_callback,
-               [LXC_COMMAND_STOP]  = lxc_stop_callback,
-               [LXC_COMMAND_STATE] = lxc_state_callback,
-               [LXC_COMMAND_PID]   = lxc_pid_callback,
+               [LXC_COMMAND_TTY]         = lxc_console_callback,
+               [LXC_COMMAND_STOP]        = lxc_stop_callback,
+               [LXC_COMMAND_STATE]       = lxc_state_callback,
+               [LXC_COMMAND_PID]         = lxc_pid_callback,
+               [LXC_COMMAND_CLONE_FLAGS] = lxc_clone_flags_callback,
        };
 
        if (request->type < 0 || request->type >= LXC_COMMAND_MAX)
index d5c013fc73294eedf9c0feefbf24c51b770f3106..3b0ac9a657f230d7284101e36a0a18a114cee83b 100644 (file)
@@ -28,6 +28,7 @@ enum {
        LXC_COMMAND_STOP,
        LXC_COMMAND_STATE,
        LXC_COMMAND_PID,
+       LXC_COMMAND_CLONE_FLAGS,
        LXC_COMMAND_MAX,
 };
 
@@ -48,6 +49,7 @@ struct lxc_command {
 };
 
 extern pid_t get_init_pid(const char *name);
+extern int lxc_get_clone_flags(const char *name);
 
 extern int lxc_command(const char *name, struct lxc_command *command,
                        int *stopped);
index 77755b979e9aca789aa98b9879cdf5fbebad31e5..3e26b27bea2b07e95ef8e28b9abb14fee285ec4c 100644 (file)
@@ -279,6 +279,29 @@ int lxc_pid_callback(int fd, struct lxc_request *request,
        return 0;
 }
 
+int lxc_clone_flags_callback(int fd, struct lxc_request *request,
+                            struct lxc_handler *handler)
+{
+       struct lxc_answer answer;
+       int ret;
+
+       answer.pid = 0;
+       answer.ret = handler->clone_flags;
+
+       ret = send(fd, &answer, sizeof(answer), 0);
+       if (ret < 0) {
+               WARN("failed to send answer to the peer");
+               return -1;
+       }
+
+       if (ret != sizeof(answer)) {
+               ERROR("partial answer sent");
+               return -1;
+       }
+
+       return 0;
+}
+
 int lxc_set_state(const char *name, struct lxc_handler *handler, lxc_state_t state)
 {
        handler->state = state;
@@ -558,7 +581,6 @@ out_warn_father:
 
 int lxc_spawn(struct lxc_handler *handler)
 {
-       int clone_flags;
        int failed_before_rename = 0;
        const char *name = handler->name;
        int pinfd;
@@ -566,10 +588,10 @@ int lxc_spawn(struct lxc_handler *handler)
        if (lxc_sync_init(handler))
                return -1;
 
-       clone_flags = CLONE_NEWUTS|CLONE_NEWPID|CLONE_NEWIPC|CLONE_NEWNS;
+       handler->clone_flags = CLONE_NEWUTS|CLONE_NEWPID|CLONE_NEWIPC|CLONE_NEWNS;
        if (!lxc_list_empty(&handler->conf->network)) {
 
-               clone_flags |= CLONE_NEWNET;
+               handler->clone_flags |= CLONE_NEWNET;
 
                /* Find gateway addresses from the link device, which is
                 * no longer accessible inside the container. Do this
@@ -603,7 +625,7 @@ int lxc_spawn(struct lxc_handler *handler)
        }
 
        /* Create a process in a new set of namespaces */
-       handler->pid = lxc_clone(do_start, handler, clone_flags);
+       handler->pid = lxc_clone(do_start, handler, handler->clone_flags);
        if (handler->pid < 0) {
                SYSERROR("failed to fork into a new namespace");
                goto out_delete_net;
@@ -621,7 +643,7 @@ int lxc_spawn(struct lxc_handler *handler)
                goto out_delete_net;
 
        /* Create the network configuration */
-       if (clone_flags & CLONE_NEWNET) {
+       if (handler->clone_flags & CLONE_NEWNET) {
                if (lxc_assign_network(&handler->conf->network, handler->pid)) {
                        ERROR("failed to create the configured network");
                        goto out_delete_net;
@@ -651,7 +673,7 @@ int lxc_spawn(struct lxc_handler *handler)
        return 0;
 
 out_delete_net:
-       if (clone_flags & CLONE_NEWNET)
+       if (handler->clone_flags & CLONE_NEWNET)
                lxc_delete_network(handler);
 out_abort:
        lxc_abort(name, handler);
index 0e12abaedb995170f0352c3cf9e2f61085f1a210..4b2e2b54e16da4645373f954f510010b5d14a211 100644 (file)
@@ -39,6 +39,7 @@ struct lxc_handler {
        pid_t pid;
        char *name;
        lxc_state_t state;
+       int clone_flags;
        int sigfd;
        sigset_t oldmask;
        struct lxc_conf *conf;