]> git.ipfire.org Git - thirdparty/lxc.git/commitdiff
lxc-start: exit early and cleanly if we have insufficient privs
authorSerge Hallyn <serge.hallyn@canonical.com>
Thu, 2 Feb 2012 21:54:53 +0000 (15:54 -0600)
committerDaniel Lezcano <daniel.lezcano@free.fr>
Sun, 26 Feb 2012 09:44:40 +0000 (10:44 +0100)
Signed-off-by: Serge Hallyn <serge.hallyn@canonical.com>
Signed-off-by: Daniel Lezcano <dlezcano@fr.ibm.com>
src/lxc/caps.c
src/lxc/caps.h
src/lxc/start.c

index 1610002ac08d9632079f911904e227a0b88992be..10a0b4aaca1123cee1b7bbf28d97413b3aeccd2d 100644 (file)
@@ -213,3 +213,42 @@ int lxc_caps_last_cap(void)
 
        return last_cap;
 }
+
+/*
+ * check if we have the caps needed to start a container.  returns 1 on
+ * success, 0 on error.  (I'd prefer this be a bool, but am afraid that
+ * might fail to build on some distros).
+ */
+int lxc_caps_check(void)
+{
+       uid_t uid = getuid();
+       cap_t caps;
+       cap_flag_value_t value;
+       int i, ret;
+
+       cap_value_t needed_caps[] = { CAP_SYS_ADMIN, CAP_NET_ADMIN, CAP_SETUID, CAP_SETGID };
+
+#define NUMCAPS ((int) (sizeof(needed_caps) / sizeof(cap_t)))
+
+       if (!uid)
+               return 1;
+
+       caps = cap_get_proc();
+       if (!caps) {
+               ERROR("failed to cap_get_proc: %m");
+               return 0;
+       }
+
+       for (i=0; i<NUMCAPS; i++) {
+               ret = cap_get_flag(caps, needed_caps[i], CAP_EFFECTIVE, &value);
+               if (ret) {
+                       ERROR("Failed to cap_get_flag: %m");
+                       return 0;
+               }
+               if (!value) {
+                       return 0;
+               }
+       }
+
+       return 1;
+}
index e4e0d425e18bd406e30371c973b246c0d41443d2..0cf8460831698ad50e20974fc9eff7a44804ef25 100644 (file)
@@ -27,6 +27,7 @@ extern int lxc_caps_reset(void);
 extern int lxc_caps_down(void);
 extern int lxc_caps_up(void);
 extern int lxc_caps_init(void);
+extern int lxc_caps_check(void);
 
 extern int lxc_caps_last_cap(void);
 
index eb7d01f9b3306de22408ad64fb2524c2697a9970..91ce5fa821771e0a33ceee3337e34ed5306d3c3f 100644 (file)
@@ -319,10 +319,17 @@ out_sigfd:
        return -1;
 }
 
+extern int lxc_caps_check(void);
+
 struct lxc_handler *lxc_init(const char *name, struct lxc_conf *conf)
 {
        struct lxc_handler *handler;
 
+       if (!lxc_caps_check()) {
+               ERROR("Not running with sufficient privilege");
+               return NULL;
+       }
+
        handler = malloc(sizeof(*handler));
        if (!handler)
                return NULL;