diff options
Diffstat (limited to '')
-rw-r--r-- | src/nxt_fs.c | 76 | ||||
-rw-r--r-- | src/nxt_fs.h | 24 | ||||
-rw-r--r-- | src/nxt_isolation.c | 105 | ||||
-rw-r--r-- | src/nxt_runtime.c | 6 | ||||
-rw-r--r-- | src/nxt_string.h | 10 |
5 files changed, 155 insertions, 66 deletions
diff --git a/src/nxt_fs.c b/src/nxt_fs.c index fe271802..0228c25a 100644 --- a/src/nxt_fs.c +++ b/src/nxt_fs.c @@ -40,30 +40,31 @@ nxt_fs_mount(nxt_task_t *task, nxt_fs_mount_t *mnt) nxt_int_t nxt_fs_mount(nxt_task_t *task, nxt_fs_mount_t *mnt) { + u_char *data, *p, *end; + size_t iovlen; + nxt_int_t ret; const char *fstype; - uint8_t is_bind, is_proc; - struct iovec iov[8]; + struct iovec iov[128]; char errmsg[256]; - is_bind = nxt_strncmp(mnt->fstype, "bind", 4) == 0; - is_proc = nxt_strncmp(mnt->fstype, "proc", 4) == 0; + if (nxt_strncmp(mnt->fstype, "bind", 4) == 0) { + fstype = "nullfs"; - if (nxt_slow_path(!is_bind && !is_proc)) { - nxt_alert(task, "mount type \"%s\" not implemented.", mnt->fstype); - return NXT_ERROR; - } + } else if (nxt_strncmp(mnt->fstype, "proc", 4) == 0) { + fstype = "procfs"; - if (is_bind) { - fstype = "nullfs"; + } else if (nxt_strncmp(mnt->fstype, "tmpfs", 5) == 0) { + fstype = "tmpfs"; } else { - fstype = "procfs"; + nxt_alert(task, "mount type \"%s\" not implemented.", mnt->fstype); + return NXT_ERROR; } iov[0].iov_base = (void *) "fstype"; iov[0].iov_len = 7; iov[1].iov_base = (void *) fstype; - iov[1].iov_len = strlen(fstype) + 1; + iov[1].iov_len = nxt_strlen(fstype) + 1; iov[2].iov_base = (void *) "fspath"; iov[2].iov_len = 7; iov[3].iov_base = (void *) mnt->dst; @@ -77,12 +78,55 @@ nxt_fs_mount(nxt_task_t *task, nxt_fs_mount_t *mnt) iov[7].iov_base = (void *) errmsg; iov[7].iov_len = sizeof(errmsg); - if (nxt_slow_path(nmount(iov, 8, 0) < 0)) { - nxt_alert(task, "nmount(%p, 8, 0) %s", errmsg); - return NXT_ERROR; + iovlen = 8; + + data = NULL; + + if (mnt->data != NULL) { + data = (u_char *) nxt_strdup(mnt->data); + if (nxt_slow_path(data == NULL)) { + return NXT_ERROR; + } + + end = data - 1; + + do { + p = end + 1; + end = nxt_strchr(p, '='); + if (end == NULL) { + break; + } + + *end = '\0'; + + iov[iovlen++].iov_base = (void *) p; + iov[iovlen++].iov_len = (end - p) + 1; + + p = end + 1; + + end = nxt_strchr(p, ','); + if (end != NULL) { + *end = '\0'; + } + + iov[iovlen++].iov_base = (void *) p; + iov[iovlen++].iov_len = nxt_strlen(p) + 1; + + } while (end != NULL && nxt_nitems(iov) > (iovlen + 2)); } - return NXT_OK; + ret = NXT_OK; + + if (nxt_slow_path(nmount(iov, iovlen, 0) < 0)) { + nxt_alert(task, "nmount(%p, %d, 0) %s", iov, iovlen, errmsg); + ret = NXT_ERROR; + } + + if (data != NULL) { + free(data); + } + + return ret; } #endif diff --git a/src/nxt_fs.h b/src/nxt_fs.h index 85c78b27..9f3266d8 100644 --- a/src/nxt_fs.h +++ b/src/nxt_fs.h @@ -18,6 +18,30 @@ #define NXT_MS_REC 0 #endif +#ifdef MS_NOSUID +#define NXT_MS_NOSUID MS_NOSUID +#else +#define NXT_MS_NOSUID 0 +#endif + +#ifdef MS_NOEXEC +#define NXT_MS_NOEXEC MS_NOEXEC +#else +#define NXT_MS_NOEXEC 0 +#endif + +#ifdef MS_RELATIME +#define NXT_MS_RELATIME MS_RELATIME +#else +#define NXT_MS_RELATIME 0 +#endif + +#ifdef MS_NODEV +#define NXT_MS_NODEV MS_NODEV +#else +#define NXT_MS_NODEV 0 +#endif + typedef struct { u_char *src; diff --git a/src/nxt_isolation.c b/src/nxt_isolation.c index 60de4324..586c0368 100644 --- a/src/nxt_isolation.c +++ b/src/nxt_isolation.c @@ -476,15 +476,13 @@ nxt_isolation_set_mounts(nxt_task_t *task, nxt_process_t *process, return NXT_ERROR; } - if (lang->mounts != NULL && lang->mounts->nelts > 0) { - ret = nxt_isolation_set_lang_mounts(task, process, lang->mounts); - if (nxt_slow_path(ret != NXT_OK)) { - return NXT_ERROR; - } - - process->isolation.cleanup = nxt_isolation_unmount_all; + ret = nxt_isolation_set_lang_mounts(task, process, lang->mounts); + if (nxt_slow_path(ret != NXT_OK)) { + return NXT_ERROR; } + process->isolation.cleanup = nxt_isolation_unmount_all; + return NXT_OK; } @@ -500,8 +498,6 @@ nxt_isolation_set_lang_mounts(nxt_task_t *task, nxt_process_t *process, const u_char *rootfs; nxt_fs_mount_t *mnt, *lang_mnt; - rootfs = process->isolation.rootfs; - rootfs_len = nxt_strlen(rootfs); mp = process->mem_pool; /* copy to init mem pool */ @@ -514,11 +510,14 @@ nxt_isolation_set_lang_mounts(nxt_task_t *task, nxt_process_t *process, mnt = mounts->elts; lang_mnt = lang_mounts->elts; + rootfs = process->isolation.rootfs; + rootfs_len = nxt_strlen(rootfs); + for (i = 0; i < n; i++) { len = nxt_strlen(lang_mnt[i].dst); mnt[i].dst = nxt_mp_alloc(mp, rootfs_len + len + 1); - if (mnt[i].dst == NULL) { + if (nxt_slow_path(mnt[i].dst == NULL)) { return NXT_ERROR; } @@ -527,6 +526,52 @@ nxt_isolation_set_lang_mounts(nxt_task_t *task, nxt_process_t *process, *p = '\0'; } + mnt = nxt_array_add(mounts); + if (nxt_slow_path(mnt == NULL)) { + return NXT_ERROR; + } + + mnt->src = (u_char *) "tmpfs"; + mnt->fstype = (u_char *) "tmpfs"; + mnt->flags = NXT_MS_NOSUID | NXT_MS_NODEV | NXT_MS_NOEXEC | NXT_MS_RELATIME; + mnt->data = (u_char *) "size=1m,mode=777"; + + mnt->dst = nxt_mp_nget(mp, rootfs_len + nxt_length("/tmp") + 1); + if (nxt_slow_path(mnt->dst == NULL)) { + return NXT_ERROR; + } + + p = nxt_cpymem(mnt->dst, rootfs, rootfs_len); + p = nxt_cpymem(p, "/tmp", 4); + *p = '\0'; + +#if (NXT_HAVE_CLONE_NEWPID) && (NXT_HAVE_CLONE_NEWNS) + + if (nxt_is_clone_flag_set(process->isolation.clone.flags, NEWPID) + && nxt_is_clone_flag_set(process->isolation.clone.flags, NEWNS)) + { + mnt = nxt_array_add(mounts); + if (nxt_slow_path(mnt == NULL)) { + return NXT_ERROR; + } + + mnt->fstype = (u_char *) "proc"; + mnt->src = (u_char *) "proc"; + + mnt->dst = nxt_mp_nget(mp, rootfs_len + nxt_length("/proc") + 1); + if (nxt_slow_path(mnt->dst == NULL)) { + return NXT_ERROR; + } + + p = nxt_cpymem(mnt->dst, rootfs, rootfs_len); + p = nxt_cpymem(p, "/proc", 5); + *p = '\0'; + + mnt->data = (u_char *) ""; + mnt->flags = 0; + } +#endif + process->isolation.mounts = mounts; return NXT_OK; @@ -556,44 +601,12 @@ nxt_int_t nxt_isolation_prepare_rootfs(nxt_task_t *task, nxt_process_t *process) { size_t i, n; - nxt_int_t ret, hasproc; + nxt_int_t ret; struct stat st; nxt_array_t *mounts; const u_char *dst; nxt_fs_mount_t *mnt; - hasproc = 0; - -#if (NXT_HAVE_CLONE_NEWPID) && (NXT_HAVE_CLONE_NEWNS) - nxt_fs_mount_t mount; - - if (nxt_is_clone_flag_set(process->isolation.clone.flags, NEWPID) - && nxt_is_clone_flag_set(process->isolation.clone.flags, NEWNS)) - { - /* - * This mount point will automatically be gone when the namespace is - * destroyed. - */ - - mount.fstype = (u_char *) "proc"; - mount.src = (u_char *) "proc"; - mount.dst = (u_char *) "/proc"; - mount.data = (u_char *) ""; - mount.flags = 0; - - ret = nxt_fs_mkdir_all(mount.dst, S_IRWXU | S_IRWXG | S_IRWXO); - if (nxt_fast_path(ret == NXT_OK)) { - ret = nxt_fs_mount(task, &mount); - if (nxt_fast_path(ret == NXT_OK)) { - hasproc = 1; - } - - } else { - nxt_log(task, NXT_LOG_WARN, "mkdir(%s) %E", mount.dst, nxt_errno); - } - } -#endif - mounts = process->isolation.mounts; n = mounts->nelts; @@ -609,12 +622,6 @@ nxt_isolation_prepare_rootfs(nxt_task_t *task, nxt_process_t *process) continue; } - if (hasproc && nxt_memcmp(mnt[i].fstype, "proc", 4) == 0 - && nxt_memcmp(mnt[i].dst, "/proc", 5) == 0) - { - continue; - } - ret = nxt_fs_mkdir_all(dst, S_IRWXU | S_IRWXG | S_IRWXO); if (nxt_slow_path(ret != NXT_OK)) { nxt_alert(task, "mkdir(%s) %E", dst, nxt_errno); diff --git a/src/nxt_runtime.c b/src/nxt_runtime.c index 435276a0..44970b34 100644 --- a/src/nxt_runtime.c +++ b/src/nxt_runtime.c @@ -84,7 +84,11 @@ nxt_runtime_create(nxt_task_t *task) lang->version = (u_char *) ""; lang->file = NULL; lang->module = &nxt_external_module; - lang->mounts = NULL; + + lang->mounts = nxt_array_create(mp, 1, sizeof(nxt_fs_mount_t)); + if (nxt_slow_path(lang->mounts == NULL)) { + goto fail; + } listen_sockets = nxt_array_create(mp, 1, sizeof(nxt_listen_socket_t)); if (nxt_slow_path(listen_sockets == NULL)) { diff --git a/src/nxt_string.h b/src/nxt_string.h index 3f9192e2..7e02f59a 100644 --- a/src/nxt_string.h +++ b/src/nxt_string.h @@ -31,6 +31,16 @@ nxt_strlen(s) \ #define \ +nxt_strdup(s) \ + strdup((char *) s) + + +#define \ +nxt_strchr(buf, delim) \ + (u_char *) strchr((char *) buf, delim) + + +#define \ nxt_memzero(buf, length) \ (void) memset(buf, 0, length) |