Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  *  Copyright (C) 2006 IBM Corporation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  *  Author: Serge Hallyn <serue@us.ibm.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  *  Jun 2006 - namespaces support
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8)  *             OpenVZ, SWsoft Inc.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9)  *             Pavel Emelianov <xemul@openvz.org>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) #include <linux/export.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) #include <linux/nsproxy.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) #include <linux/init_task.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) #include <linux/mnt_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) #include <linux/utsname.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) #include <linux/pid_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) #include <net/net_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) #include <linux/ipc_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) #include <linux/time_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) #include <linux/fs_struct.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) #include <linux/proc_fs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) #include <linux/proc_ns.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) #include <linux/file.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) #include <linux/syscalls.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) #include <linux/cgroup.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) #include <linux/perf_event.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) static struct kmem_cache *nsproxy_cachep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) struct nsproxy init_nsproxy = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 	.count			= ATOMIC_INIT(1),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 	.uts_ns			= &init_uts_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) #if defined(CONFIG_POSIX_MQUEUE) || defined(CONFIG_SYSVIPC)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 	.ipc_ns			= &init_ipc_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) 	.mnt_ns			= NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) 	.pid_ns_for_children	= &init_pid_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) #ifdef CONFIG_NET
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 	.net_ns			= &init_net,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) #ifdef CONFIG_CGROUPS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 	.cgroup_ns		= &init_cgroup_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) #ifdef CONFIG_TIME_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 	.time_ns		= &init_time_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 	.time_ns_for_children	= &init_time_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) static inline struct nsproxy *create_nsproxy(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) 	struct nsproxy *nsproxy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 	nsproxy = kmem_cache_alloc(nsproxy_cachep, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) 	if (nsproxy)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 		atomic_set(&nsproxy->count, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 	return nsproxy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63)  * Create new nsproxy and all of its the associated namespaces.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64)  * Return the newly created nsproxy.  Do not attach this to the task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65)  * leave it to the caller to do proper locking and attach it to task.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) static struct nsproxy *create_new_namespaces(unsigned long flags,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 	struct task_struct *tsk, struct user_namespace *user_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 	struct fs_struct *new_fs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 	struct nsproxy *new_nsp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 	int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 	new_nsp = create_nsproxy();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	if (!new_nsp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 		return ERR_PTR(-ENOMEM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 	new_nsp->mnt_ns = copy_mnt_ns(flags, tsk->nsproxy->mnt_ns, user_ns, new_fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	if (IS_ERR(new_nsp->mnt_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 		err = PTR_ERR(new_nsp->mnt_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 		goto out_ns;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 	new_nsp->uts_ns = copy_utsname(flags, user_ns, tsk->nsproxy->uts_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 	if (IS_ERR(new_nsp->uts_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 		err = PTR_ERR(new_nsp->uts_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 		goto out_uts;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 	new_nsp->ipc_ns = copy_ipcs(flags, user_ns, tsk->nsproxy->ipc_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 	if (IS_ERR(new_nsp->ipc_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 		err = PTR_ERR(new_nsp->ipc_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 		goto out_ipc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 	new_nsp->pid_ns_for_children =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 		copy_pid_ns(flags, user_ns, tsk->nsproxy->pid_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	if (IS_ERR(new_nsp->pid_ns_for_children)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 		err = PTR_ERR(new_nsp->pid_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 		goto out_pid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 	new_nsp->cgroup_ns = copy_cgroup_ns(flags, user_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 					    tsk->nsproxy->cgroup_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 	if (IS_ERR(new_nsp->cgroup_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 		err = PTR_ERR(new_nsp->cgroup_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 		goto out_cgroup;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 	new_nsp->net_ns = copy_net_ns(flags, user_ns, tsk->nsproxy->net_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 	if (IS_ERR(new_nsp->net_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 		err = PTR_ERR(new_nsp->net_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 		goto out_net;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	new_nsp->time_ns_for_children = copy_time_ns(flags, user_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 					tsk->nsproxy->time_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 	if (IS_ERR(new_nsp->time_ns_for_children)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 		err = PTR_ERR(new_nsp->time_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 		goto out_time;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	new_nsp->time_ns = get_time_ns(tsk->nsproxy->time_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 	return new_nsp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) out_time:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 	put_net(new_nsp->net_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) out_net:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 	put_cgroup_ns(new_nsp->cgroup_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) out_cgroup:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 	if (new_nsp->pid_ns_for_children)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 		put_pid_ns(new_nsp->pid_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) out_pid:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 	if (new_nsp->ipc_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 		put_ipc_ns(new_nsp->ipc_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) out_ipc:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 	if (new_nsp->uts_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 		put_uts_ns(new_nsp->uts_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) out_uts:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 	if (new_nsp->mnt_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 		put_mnt_ns(new_nsp->mnt_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) out_ns:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	kmem_cache_free(nsproxy_cachep, new_nsp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	return ERR_PTR(err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148)  * called from clone.  This now handles copy for nsproxy and all
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149)  * namespaces therein.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) int copy_namespaces(unsigned long flags, struct task_struct *tsk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) 	struct nsproxy *old_ns = tsk->nsproxy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 	struct user_namespace *user_ns = task_cred_xxx(tsk, user_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 	struct nsproxy *new_ns;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 	if (likely(!(flags & (CLONE_NEWNS | CLONE_NEWUTS | CLONE_NEWIPC |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 			      CLONE_NEWPID | CLONE_NEWNET |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 			      CLONE_NEWCGROUP | CLONE_NEWTIME)))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 		if (likely(old_ns->time_ns_for_children == old_ns->time_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 			get_nsproxy(old_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 			return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 	} else if (!ns_capable(user_ns, CAP_SYS_ADMIN))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 	 * CLONE_NEWIPC must detach from the undolist: after switching
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 	 * to a new ipc namespace, the semaphore arrays from the old
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	 * namespace are unreachable.  In clone parlance, CLONE_SYSVSEM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	 * means share undolist with parent, so we must forbid using
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	 * it along with CLONE_NEWIPC.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 	if ((flags & (CLONE_NEWIPC | CLONE_SYSVSEM)) ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 		(CLONE_NEWIPC | CLONE_SYSVSEM)) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 	new_ns = create_new_namespaces(flags, tsk, user_ns, tsk->fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 	if (IS_ERR(new_ns))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 		return  PTR_ERR(new_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 	ret = timens_on_fork(new_ns, tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 	if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 		free_nsproxy(new_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 	tsk->nsproxy = new_ns;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) void free_nsproxy(struct nsproxy *ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 	if (ns->mnt_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 		put_mnt_ns(ns->mnt_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 	if (ns->uts_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 		put_uts_ns(ns->uts_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	if (ns->ipc_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 		put_ipc_ns(ns->ipc_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 	if (ns->pid_ns_for_children)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 		put_pid_ns(ns->pid_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	if (ns->time_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 		put_time_ns(ns->time_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	if (ns->time_ns_for_children)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 		put_time_ns(ns->time_ns_for_children);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 	put_cgroup_ns(ns->cgroup_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 	put_net(ns->net_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	kmem_cache_free(nsproxy_cachep, ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213)  * Called from unshare. Unshare all the namespaces part of nsproxy.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214)  * On success, returns the new nsproxy.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) int unshare_nsproxy_namespaces(unsigned long unshare_flags,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 	struct nsproxy **new_nsp, struct cred *new_cred, struct fs_struct *new_fs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 	struct user_namespace *user_ns;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 	int err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 	if (!(unshare_flags & (CLONE_NEWNS | CLONE_NEWUTS | CLONE_NEWIPC |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 			       CLONE_NEWNET | CLONE_NEWPID | CLONE_NEWCGROUP |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 			       CLONE_NEWTIME)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 	user_ns = new_cred ? new_cred->user_ns : current_user_ns();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 	if (!ns_capable(user_ns, CAP_SYS_ADMIN))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 	*new_nsp = create_new_namespaces(unshare_flags, current, user_ns,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 					 new_fs ? new_fs : current->fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 	if (IS_ERR(*new_nsp)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 		err = PTR_ERR(*new_nsp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) void switch_task_namespaces(struct task_struct *p, struct nsproxy *new)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 	struct nsproxy *ns;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 	might_sleep();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	task_lock(p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 	ns = p->nsproxy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 	p->nsproxy = new;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 	task_unlock(p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 	if (ns && atomic_dec_and_test(&ns->count))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 		free_nsproxy(ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) void exit_task_namespaces(struct task_struct *p)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 	switch_task_namespaces(p, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) static int check_setns_flags(unsigned long flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) 	if (!flags || (flags & ~(CLONE_NEWNS | CLONE_NEWUTS | CLONE_NEWIPC |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 				 CLONE_NEWNET | CLONE_NEWTIME | CLONE_NEWUSER |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) 				 CLONE_NEWPID | CLONE_NEWCGROUP)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) #ifndef CONFIG_USER_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 	if (flags & CLONE_NEWUSER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) #ifndef CONFIG_PID_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 	if (flags & CLONE_NEWPID)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) #ifndef CONFIG_UTS_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 	if (flags & CLONE_NEWUTS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) #ifndef CONFIG_IPC_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) 	if (flags & CLONE_NEWIPC)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) #ifndef CONFIG_CGROUPS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 	if (flags & CLONE_NEWCGROUP)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) #ifndef CONFIG_NET_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 	if (flags & CLONE_NEWNET)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) #ifndef CONFIG_TIME_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 	if (flags & CLONE_NEWTIME)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) static void put_nsset(struct nsset *nsset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 	unsigned flags = nsset->flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 	if (flags & CLONE_NEWUSER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 		put_cred(nsset_cred(nsset));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 	 * We only created a temporary copy if we attached to more than just
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 	 * the mount namespace.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	if (nsset->fs && (flags & CLONE_NEWNS) && (flags & ~CLONE_NEWNS))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 		free_fs_struct(nsset->fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 	if (nsset->nsproxy)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 		free_nsproxy(nsset->nsproxy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) static int prepare_nsset(unsigned flags, struct nsset *nsset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) 	struct task_struct *me = current;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	nsset->nsproxy = create_new_namespaces(0, me, current_user_ns(), me->fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 	if (IS_ERR(nsset->nsproxy))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 		return PTR_ERR(nsset->nsproxy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 	if (flags & CLONE_NEWUSER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 		nsset->cred = prepare_creds();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 		nsset->cred = current_cred();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 	if (!nsset->cred)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 	/* Only create a temporary copy of fs_struct if we really need to. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 	if (flags == CLONE_NEWNS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 		nsset->fs = me->fs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 	} else if (flags & CLONE_NEWNS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 		nsset->fs = copy_fs_struct(me->fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 		if (!nsset->fs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 	nsset->flags = flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 	put_nsset(nsset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 	return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) static inline int validate_ns(struct nsset *nsset, struct ns_common *ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 	return ns->ops->install(nsset, ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355)  * This is the inverse operation to unshare().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356)  * Ordering is equivalent to the standard ordering used everywhere else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357)  * during unshare and process creation. The switch to the new set of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)  * namespaces occurs at the point of no return after installation of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359)  * all requested namespaces was successful in commit_nsset().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) static int validate_nsset(struct nsset *nsset, struct pid *pid)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 	int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) 	unsigned flags = nsset->flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 	struct user_namespace *user_ns = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 	struct pid_namespace *pid_ns = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 	struct nsproxy *nsp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 	struct task_struct *tsk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 	/* Take a "snapshot" of the target task's namespaces. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 	rcu_read_lock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	tsk = pid_task(pid, PIDTYPE_PID);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 	if (!tsk) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 		rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 		return -ESRCH;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 	if (!ptrace_may_access(tsk, PTRACE_MODE_READ_REALCREDS)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 		rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 	task_lock(tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 	nsp = tsk->nsproxy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 	if (nsp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) 		get_nsproxy(nsp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) 	task_unlock(tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) 	if (!nsp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 		rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 		return -ESRCH;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) #ifdef CONFIG_PID_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 	if (flags & CLONE_NEWPID) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 		pid_ns = task_active_pid_ns(tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 		if (unlikely(!pid_ns)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 			rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 			ret = -ESRCH;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 		get_pid_ns(pid_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) #ifdef CONFIG_USER_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 	if (flags & CLONE_NEWUSER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 		user_ns = get_user_ns(__task_cred(tsk)->user_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 	rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 	 * Install requested namespaces. The caller will have
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 	 * verified earlier that the requested namespaces are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 	 * supported on this kernel. We don't report errors here
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) 	 * if a namespace is requested that isn't supported.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) #ifdef CONFIG_USER_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) 	if (flags & CLONE_NEWUSER) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) 		ret = validate_ns(nsset, &user_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 	if (flags & CLONE_NEWNS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 		ret = validate_ns(nsset, from_mnt_ns(nsp->mnt_ns));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) #ifdef CONFIG_UTS_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 	if (flags & CLONE_NEWUTS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 		ret = validate_ns(nsset, &nsp->uts_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) #ifdef CONFIG_IPC_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) 	if (flags & CLONE_NEWIPC) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) 		ret = validate_ns(nsset, &nsp->ipc_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) #ifdef CONFIG_PID_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) 	if (flags & CLONE_NEWPID) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) 		ret = validate_ns(nsset, &pid_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) #ifdef CONFIG_CGROUPS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 	if (flags & CLONE_NEWCGROUP) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 		ret = validate_ns(nsset, &nsp->cgroup_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) #ifdef CONFIG_NET_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) 	if (flags & CLONE_NEWNET) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 		ret = validate_ns(nsset, &nsp->net_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) #ifdef CONFIG_TIME_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) 	if (flags & CLONE_NEWTIME) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) 		ret = validate_ns(nsset, &nsp->time_ns->ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) 	if (pid_ns)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) 		put_pid_ns(pid_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) 	if (nsp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) 		put_nsproxy(nsp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) 	put_user_ns(user_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490)  * This is the point of no return. There are just a few namespaces
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491)  * that do some actual work here and it's sufficiently minimal that
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492)  * a separate ns_common operation seems unnecessary for now.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493)  * Unshare is doing the same thing. If we'll end up needing to do
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494)  * more in a given namespace or a helper here is ultimately not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495)  * exported anymore a simple commit handler for each namespace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496)  * should be added to ns_common.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) static void commit_nsset(struct nsset *nsset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) 	unsigned flags = nsset->flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) 	struct task_struct *me = current;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) #ifdef CONFIG_USER_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) 	if (flags & CLONE_NEWUSER) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) 		/* transfer ownership */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) 		commit_creds(nsset_cred(nsset));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) 		nsset->cred = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) 	/* We only need to commit if we have used a temporary fs_struct. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) 	if ((flags & CLONE_NEWNS) && (flags & ~CLONE_NEWNS)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) 		set_fs_root(me->fs, &nsset->fs->root);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) 		set_fs_pwd(me->fs, &nsset->fs->pwd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) #ifdef CONFIG_IPC_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) 	if (flags & CLONE_NEWIPC)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) 		exit_sem(me);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) #ifdef CONFIG_TIME_NS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) 	if (flags & CLONE_NEWTIME)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) 		timens_commit(me, nsset->nsproxy->time_ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) 	/* transfer ownership */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) 	switch_task_namespaces(me, nsset->nsproxy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) 	nsset->nsproxy = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) SYSCALL_DEFINE2(setns, int, fd, int, flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) 	struct file *file;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) 	struct ns_common *ns = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) 	struct nsset nsset = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) 	int err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) 	file = fget(fd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) 	if (!file)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) 		return -EBADF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) 	if (proc_ns_file(file)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) 		ns = get_proc_ns(file_inode(file));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) 		if (flags && (ns->ops->type != flags))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) 			err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) 		flags = ns->ops->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) 	} else if (!IS_ERR(pidfd_pid(file))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) 		err = check_setns_flags(flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) 		err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) 	if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) 	err = prepare_nsset(flags, &nsset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) 	if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) 	if (proc_ns_file(file))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) 		err = validate_ns(&nsset, ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) 		err = validate_nsset(&nsset, file->private_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) 	if (!err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) 		commit_nsset(&nsset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) 		perf_event_namespaces(current);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) 	put_nsset(&nsset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) 	fput(file);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) 	return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) int __init nsproxy_cache_init(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) 	nsproxy_cachep = KMEM_CACHE(nsproxy, SLAB_PANIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) }