]> git.proxmox.com Git - mirror_lxc.git/blobdiff - src/lxc/conf.c
confile:add lxc.init.cwd
[mirror_lxc.git] / src / lxc / conf.c
index 6871b83a0523cd9c913055c0bdf3f8b3aaed88bf..8234279f995687a35ed83cebb546f788fa353879 100644 (file)
 #include <../include/openpty.h>
 #endif
 
-#ifdef HAVE_LINUX_MEMFD_H
-#include <linux/memfd.h>
-#endif
-
 #include "af_unix.h"
 #include "caps.h"       /* for lxc_caps_last_cap() */
 #include "cgroup.h"
@@ -84,6 +80,7 @@
 #include "namespace.h"
 #include "network.h"
 #include "parse.h"
+#include "ringbuf.h"
 #include "storage.h"
 #include "storage/aufs.h"
 #include "storage/overlay.h"
 
 #if IS_BIONIC
 #include <../include/lxcmntent.h>
-#ifndef HAVE_PRLIMIT
-#include <../include/prlimit.h>
-#endif
 #else
 #include <mntent.h>
 #endif
 
-lxc_log_define(lxc_conf, lxc);
-
-#if HAVE_LIBCAP
-#ifndef CAP_SETFCAP
-#define CAP_SETFCAP 31
-#endif
-
-#ifndef CAP_MAC_OVERRIDE
-#define CAP_MAC_OVERRIDE 32
-#endif
-
-#ifndef CAP_MAC_ADMIN
-#define CAP_MAC_ADMIN 33
-#endif
-#endif
-
-#ifndef PR_CAPBSET_DROP
-#define PR_CAPBSET_DROP 24
-#endif
-
-#ifndef LO_FLAGS_AUTOCLEAR
-#define LO_FLAGS_AUTOCLEAR 4
-#endif
-
-#ifndef CAP_SETUID
-#define CAP_SETUID 7
-#endif
-
-#ifndef CAP_SETGID
-#define CAP_SETGID 6
+#if !defined(HAVE_PRLIMIT) && defined(HAVE_PRLIMIT64)
+#include <../include/prlimit.h>
 #endif
 
-/* needed for cgroup automount checks, regardless of whether we
- * have included linux/capability.h or not */
-#ifndef CAP_SYS_ADMIN
-#define CAP_SYS_ADMIN 21
-#endif
+lxc_log_define(lxc_conf, lxc);
 
 /* Define pivot_root() if missing from the C library */
 #ifndef HAVE_PIVOT_ROOT
@@ -160,19 +122,6 @@ static int pivot_root(const char * new_root, const char * put_old)
 extern int pivot_root(const char * new_root, const char * put_old);
 #endif
 
-/* Define sethostname() if missing from the C library */
-#ifndef HAVE_SETHOSTNAME
-static int sethostname(const char * name, size_t len)
-{
-#ifdef __NR_sethostname
-       return syscall(__NR_sethostname, name, len);
-#else
-       errno = ENOSYS;
-       return -1;
-#endif
-}
-#endif
-
 #ifndef MS_PRIVATE
 #define MS_PRIVATE (1<<18)
 #endif
@@ -181,59 +130,6 @@ static int sethostname(const char * name, size_t len)
 #define MS_LAZYTIME (1<<25)
 #endif
 
-/* memfd_create() */
-#ifndef MFD_CLOEXEC
-#define MFD_CLOEXEC 0x0001U
-#endif
-
-#ifndef MFD_ALLOW_SEALING
-#define MFD_ALLOW_SEALING 0x0002U
-#endif
-
-#ifndef HAVE_MEMFD_CREATE
-static int memfd_create(const char *name, unsigned int flags) {
-       #ifndef __NR_memfd_create
-               #if defined __i386__
-                       #define __NR_memfd_create 356
-               #elif defined __x86_64__
-                       #define __NR_memfd_create 319
-               #elif defined __arm__
-                       #define __NR_memfd_create 385
-               #elif defined __aarch64__
-                       #define __NR_memfd_create 279
-               #elif defined __s390__
-                       #define __NR_memfd_create 350
-               #elif defined __powerpc__
-                       #define __NR_memfd_create 360
-               #elif defined __sparc__
-                       #define __NR_memfd_create 348
-               #elif defined __blackfin__
-                       #define __NR_memfd_create 390
-               #elif defined __ia64__
-                       #define __NR_memfd_create 1340
-               #elif defined _MIPS_SIM
-                       #if _MIPS_SIM == _MIPS_SIM_ABI32
-                               #define __NR_memfd_create 4354
-                       #endif
-                       #if _MIPS_SIM == _MIPS_SIM_NABI32
-                               #define __NR_memfd_create 6318
-                       #endif
-                       #if _MIPS_SIM == _MIPS_SIM_ABI64
-                               #define __NR_memfd_create 5314
-                       #endif
-               #endif
-       #endif
-       #ifdef __NR_memfd_create
-       return syscall(__NR_memfd_create, name, flags);
-       #else
-       errno = ENOSYS;
-       return -1;
-       #endif
-}
-#else
-extern int memfd_create(const char *name, unsigned int flags);
-#endif
-
 char *lxchook_names[NUM_LXC_HOOKS] = {"pre-start", "pre-mount", "mount",
                                      "autodev",   "start",     "stop",
                                      "post-stop", "clone",     "destroy",
@@ -266,9 +162,6 @@ __thread struct lxc_conf *current_config;
 struct lxc_conf *current_config;
 #endif
 
-/* Declare this here, since we don't want to reshuffle the whole file. */
-static int in_caplist(int cap, struct lxc_list *caps);
-
 static struct mount_opt mount_opt[] = {
        { "async",         1, MS_SYNCHRONOUS },
        { "atime",         1, MS_NOATIME     },
@@ -2458,10 +2351,15 @@ int setup_resource_limits(struct lxc_list *limits, pid_t pid) {
                        return -1;
                }
 
+#if HAVE_PRLIMIT || HAVE_PRLIMIT64
                if (prlimit(pid, resid, &lim->limit, NULL) != 0) {
                        ERROR("failed to set limit %s: %s", lim->resource, strerror(errno));
                        return -1;
                }
+#else
+               ERROR("Cannot set limit %s as prlimit is missing", lim->resource);
+               return -1;
+#endif
        }
        return 0;
 }
@@ -2483,6 +2381,9 @@ struct lxc_conf *lxc_conf_init(void)
        new->loglevel = LXC_LOG_LEVEL_NOTSET;
        new->personality = -1;
        new->autodev = 1;
+       new->console.buffer_log_file = NULL;
+       new->console.buffer_log_file_fd = -1;
+       new->console.buffer_size = 0;
        new->console.log_path = NULL;
        new->console.log_fd = -1;
        new->console.path = NULL;
@@ -2493,6 +2394,7 @@ struct lxc_conf *lxc_conf_init(void)
        new->console.master = -1;
        new->console.slave = -1;
        new->console.name[0] = '\0';
+       memset(&new->console.ringbuf, 0, sizeof(struct lxc_ringbuf));
        new->maincmd_fd = -1;
        new->nbd_idx = -1;
        new->rootfs.mount = strdup(default_rootfs_mount);
@@ -2512,21 +2414,19 @@ struct lxc_conf *lxc_conf_init(void)
        lxc_list_init(&new->aliens);
        lxc_list_init(&new->environment);
        lxc_list_init(&new->limits);
-       for (i=0; i<NUM_LXC_HOOKS; i++)
+       for (i = 0; i < NUM_LXC_HOOKS; i++)
                lxc_list_init(&new->hooks[i]);
        lxc_list_init(&new->groups);
        new->lsm_aa_profile = NULL;
        new->lsm_se_context = NULL;
        new->tmp_umount_proc = 0;
 
-       for (i = 0; i < LXC_NS_MAX; i++)
-               new->inherit_ns_fd[i] = -1;
-
        /* if running in a new user namespace, init and COMMAND
         * default to running as UID/GID 0 when using lxc-execute */
        new->init_uid = 0;
        new->init_gid = 0;
        memset(&new->cgroup_meta, 0, sizeof(struct lxc_cgroup));
+       memset(&new->inherit_ns, 0, sizeof(char *) * LXC_NS_MAX);
 
        return new;
 }
@@ -2701,9 +2601,6 @@ int lxc_map_ids(struct lxc_list *idmap, pid_t pid)
                        pos += sprintf(mapbuf, "new%cidmap %d", u_or_g, pid);
 
                lxc_list_for_each(iterator, idmap) {
-                       /* The kernel only takes <= 4k for writes to
-                        * /proc/<nr>/[ug]id_map
-                        */
                        map = iterator->elem;
                        if (map->idtype != type)
                                continue;
@@ -2715,8 +2612,13 @@ int lxc_map_ids(struct lxc_list *idmap, pid_t pid)
                                        use_shadow ? " " : "", map->nsid,
                                        map->hostid, map->range,
                                        use_shadow ? "" : "\n");
-                       if (fill <= 0 || fill >= left)
-                               SYSERROR("Too many {g,u}id mappings defined.");
+                       if (fill <= 0 || fill >= left) {
+                               /* The kernel only takes <= 4k for writes to
+                                * /proc/<pid>/{g,u}id_map
+                                */
+                               SYSERROR("Too many %cid mappings defined", u_or_g);
+                               return -1;
+                       }
 
                        pos += fill;
                }
@@ -3146,7 +3048,7 @@ int lxc_setup(struct lxc_handler *handler)
                return -1;
        }
 
-       if (lxc_conf->inherit_ns_fd[LXC_NS_UTS] == -1) {
+       if (handler->nsfd[LXC_NS_UTS] == -1) {
                if (setup_utsname(lxc_conf->utsname)) {
                        ERROR("failed to setup the utsname for '%s'", name);
                        return -1;
@@ -3512,8 +3414,11 @@ void lxc_conf_free(struct lxc_conf *conf)
                return;
        if (current_config == conf)
                current_config = NULL;
+       free(conf->console.buffer_log_file);
        free(conf->console.log_path);
        free(conf->console.path);
+       if (conf->console.buffer_size > 0 && conf->console.ringbuf.addr)
+               lxc_ringbuf_release(&conf->console.ringbuf);
        free(conf->rootfs.mount);
        free(conf->rootfs.bdev_type);
        free(conf->rootfs.options);
@@ -3527,6 +3432,7 @@ void lxc_conf_free(struct lxc_conf *conf)
        free(conf->rcfile);
        free(conf->execute_cmd);
        free(conf->init_cmd);
+       free(conf->init_cwd);
        free(conf->unexpanded_config);
        free(conf->pty_names);
        free(conf->syslog);
@@ -3663,7 +3569,7 @@ int userns_exec_1(struct lxc_conf *conf, int (*fn)(void *), void *data,
        struct lxc_list *it;
        struct id_map *map;
        char c = '1';
-       int ret = -1;
+       int ret = -1, status = -1;
        struct lxc_list *idmap = NULL, *tmplist = NULL;
        struct id_map *container_root_uid = NULL, *container_root_gid = NULL,
                      *host_uid_map = NULL, *host_gid_map = NULL;
@@ -3833,10 +3739,11 @@ int userns_exec_1(struct lxc_conf *conf, int (*fn)(void *), void *data,
                goto on_error;
        }
 
+on_error:
        /* Wait for child to finish. */
-       ret = wait_for_pid(pid);
+       if (pid > 0)
+               status = wait_for_pid(pid);
 
-on_error:
        if (idmap)
                lxc_free_idmap(idmap);
        if (container_root_uid)
@@ -3852,6 +3759,9 @@ on_error:
                close(p[0]);
        close(p[1]);
 
+       if (status < 0)
+               ret = -1;
+
        return ret;
 }
 
@@ -4015,10 +3925,11 @@ int userns_exec_full(struct lxc_conf *conf, int (*fn)(void *), void *data,
                goto on_error;
        }
 
+on_error:
        /* Wait for child to finish. */
-       ret = wait_for_pid(pid);
+       if (pid > 0)
+               ret = wait_for_pid(pid);
 
-on_error:
        if (idmap)
                lxc_free_idmap(idmap);
        if (host_uid_map && (host_uid_map != container_root_uid))