aboutsummaryrefslogtreecommitdiffstats
path: root/kernel
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2014-12-10 21:31:59 -0500
committerAl Viro <viro@zeniv.linux.org.uk>2014-12-10 21:31:59 -0500
commit707c5960f102f8cdafb9406047b158abc71b391f (patch)
tree31d195b1c48cefa2d04da7cc801824f87a0a9887 /kernel
parentba00410b8131b23edfb0e09f8b6dd26c8eb621fb (diff)
parent3d3d35b1e94ec918fc0ae670663235bf197d8609 (diff)
Merge branch 'nsfs' into for-next
Diffstat (limited to 'kernel')
-rw-r--r--kernel/nsproxy.c10
-rw-r--r--kernel/pid.c5
-rw-r--r--kernel/pid_namespace.c29
-rw-r--r--kernel/user.c5
-rw-r--r--kernel/user_namespace.c29
-rw-r--r--kernel/utsname.c31
6 files changed, 55 insertions, 54 deletions
diff --git a/kernel/nsproxy.c b/kernel/nsproxy.c
index ef42d0ab3115..49746c81ad8d 100644
--- a/kernel/nsproxy.c
+++ b/kernel/nsproxy.c
@@ -220,11 +220,10 @@ void exit_task_namespaces(struct task_struct *p)
220 220
221SYSCALL_DEFINE2(setns, int, fd, int, nstype) 221SYSCALL_DEFINE2(setns, int, fd, int, nstype)
222{ 222{
223 const struct proc_ns_operations *ops;
224 struct task_struct *tsk = current; 223 struct task_struct *tsk = current;
225 struct nsproxy *new_nsproxy; 224 struct nsproxy *new_nsproxy;
226 struct proc_ns *ei;
227 struct file *file; 225 struct file *file;
226 struct ns_common *ns;
228 int err; 227 int err;
229 228
230 file = proc_ns_fget(fd); 229 file = proc_ns_fget(fd);
@@ -232,9 +231,8 @@ SYSCALL_DEFINE2(setns, int, fd, int, nstype)
232 return PTR_ERR(file); 231 return PTR_ERR(file);
233 232
234 err = -EINVAL; 233 err = -EINVAL;
235 ei = get_proc_ns(file_inode(file)); 234 ns = get_proc_ns(file_inode(file));
236 ops = ei->ns_ops; 235 if (nstype && (ns->ops->type != nstype))
237 if (nstype && (ops->type != nstype))
238 goto out; 236 goto out;
239 237
240 new_nsproxy = create_new_namespaces(0, tsk, current_user_ns(), tsk->fs); 238 new_nsproxy = create_new_namespaces(0, tsk, current_user_ns(), tsk->fs);
@@ -243,7 +241,7 @@ SYSCALL_DEFINE2(setns, int, fd, int, nstype)
243 goto out; 241 goto out;
244 } 242 }
245 243
246 err = ops->install(new_nsproxy, ei->ns); 244 err = ns->ops->install(new_nsproxy, ns);
247 if (err) { 245 if (err) {
248 free_nsproxy(new_nsproxy); 246 free_nsproxy(new_nsproxy);
249 goto out; 247 goto out;
diff --git a/kernel/pid.c b/kernel/pid.c
index 9b9a26698144..c17a993a4d2a 100644
--- a/kernel/pid.c
+++ b/kernel/pid.c
@@ -79,7 +79,10 @@ struct pid_namespace init_pid_ns = {
79 .level = 0, 79 .level = 0,
80 .child_reaper = &init_task, 80 .child_reaper = &init_task,
81 .user_ns = &init_user_ns, 81 .user_ns = &init_user_ns,
82 .proc_inum = PROC_PID_INIT_INO, 82 .ns.inum = PROC_PID_INIT_INO,
83#ifdef CONFIG_PID_NS
84 .ns.ops = &pidns_operations,
85#endif
83}; 86};
84EXPORT_SYMBOL_GPL(init_pid_ns); 87EXPORT_SYMBOL_GPL(init_pid_ns);
85 88
diff --git a/kernel/pid_namespace.c b/kernel/pid_namespace.c
index db95d8eb761b..e1bafe3b47bb 100644
--- a/kernel/pid_namespace.c
+++ b/kernel/pid_namespace.c
@@ -105,9 +105,10 @@ static struct pid_namespace *create_pid_namespace(struct user_namespace *user_ns
105 if (ns->pid_cachep == NULL) 105 if (ns->pid_cachep == NULL)
106 goto out_free_map; 106 goto out_free_map;
107 107
108 err = proc_alloc_inum(&ns->proc_inum); 108 err = ns_alloc_inum(&ns->ns);
109 if (err) 109 if (err)
110 goto out_free_map; 110 goto out_free_map;
111 ns->ns.ops = &pidns_operations;
111 112
112 kref_init(&ns->kref); 113 kref_init(&ns->kref);
113 ns->level = level; 114 ns->level = level;
@@ -142,7 +143,7 @@ static void destroy_pid_namespace(struct pid_namespace *ns)
142{ 143{
143 int i; 144 int i;
144 145
145 proc_free_inum(ns->proc_inum); 146 ns_free_inum(&ns->ns);
146 for (i = 0; i < PIDMAP_ENTRIES; i++) 147 for (i = 0; i < PIDMAP_ENTRIES; i++)
147 kfree(ns->pidmap[i].page); 148 kfree(ns->pidmap[i].page);
148 put_user_ns(ns->user_ns); 149 put_user_ns(ns->user_ns);
@@ -313,7 +314,12 @@ int reboot_pid_ns(struct pid_namespace *pid_ns, int cmd)
313 return 0; 314 return 0;
314} 315}
315 316
316static void *pidns_get(struct task_struct *task) 317static inline struct pid_namespace *to_pid_ns(struct ns_common *ns)
318{
319 return container_of(ns, struct pid_namespace, ns);
320}
321
322static struct ns_common *pidns_get(struct task_struct *task)
317{ 323{
318 struct pid_namespace *ns; 324 struct pid_namespace *ns;
319 325
@@ -323,18 +329,18 @@ static void *pidns_get(struct task_struct *task)
323 get_pid_ns(ns); 329 get_pid_ns(ns);
324 rcu_read_unlock(); 330 rcu_read_unlock();
325 331
326 return ns; 332 return ns ? &ns->ns : NULL;
327} 333}
328 334
329static void pidns_put(void *ns) 335static void pidns_put(struct ns_common *ns)
330{ 336{
331 put_pid_ns(ns); 337 put_pid_ns(to_pid_ns(ns));
332} 338}
333 339
334static int pidns_install(struct nsproxy *nsproxy, void *ns) 340static int pidns_install(struct nsproxy *nsproxy, struct ns_common *ns)
335{ 341{
336 struct pid_namespace *active = task_active_pid_ns(current); 342 struct pid_namespace *active = task_active_pid_ns(current);
337 struct pid_namespace *ancestor, *new = ns; 343 struct pid_namespace *ancestor, *new = to_pid_ns(ns);
338 344
339 if (!ns_capable(new->user_ns, CAP_SYS_ADMIN) || 345 if (!ns_capable(new->user_ns, CAP_SYS_ADMIN) ||
340 !ns_capable(current_user_ns(), CAP_SYS_ADMIN)) 346 !ns_capable(current_user_ns(), CAP_SYS_ADMIN))
@@ -362,19 +368,12 @@ static int pidns_install(struct nsproxy *nsproxy, void *ns)
362 return 0; 368 return 0;
363} 369}
364 370
365static unsigned int pidns_inum(void *ns)
366{
367 struct pid_namespace *pid_ns = ns;
368 return pid_ns->proc_inum;
369}
370
371const struct proc_ns_operations pidns_operations = { 371const struct proc_ns_operations pidns_operations = {
372 .name = "pid", 372 .name = "pid",
373 .type = CLONE_NEWPID, 373 .type = CLONE_NEWPID,
374 .get = pidns_get, 374 .get = pidns_get,
375 .put = pidns_put, 375 .put = pidns_put,
376 .install = pidns_install, 376 .install = pidns_install,
377 .inum = pidns_inum,
378}; 377};
379 378
380static __init int pid_namespaces_init(void) 379static __init int pid_namespaces_init(void)
diff --git a/kernel/user.c b/kernel/user.c
index 4efa39350e44..69b800aebf13 100644
--- a/kernel/user.c
+++ b/kernel/user.c
@@ -50,7 +50,10 @@ struct user_namespace init_user_ns = {
50 .count = ATOMIC_INIT(3), 50 .count = ATOMIC_INIT(3),
51 .owner = GLOBAL_ROOT_UID, 51 .owner = GLOBAL_ROOT_UID,
52 .group = GLOBAL_ROOT_GID, 52 .group = GLOBAL_ROOT_GID,
53 .proc_inum = PROC_USER_INIT_INO, 53 .ns.inum = PROC_USER_INIT_INO,
54#ifdef CONFIG_USER_NS
55 .ns.ops = &userns_operations,
56#endif
54#ifdef CONFIG_PERSISTENT_KEYRINGS 57#ifdef CONFIG_PERSISTENT_KEYRINGS
55 .persistent_keyring_register_sem = 58 .persistent_keyring_register_sem =
56 __RWSEM_INITIALIZER(init_user_ns.persistent_keyring_register_sem), 59 __RWSEM_INITIALIZER(init_user_ns.persistent_keyring_register_sem),
diff --git a/kernel/user_namespace.c b/kernel/user_namespace.c
index aa312b0dc3ec..1491ad00388f 100644
--- a/kernel/user_namespace.c
+++ b/kernel/user_namespace.c
@@ -86,11 +86,12 @@ int create_user_ns(struct cred *new)
86 if (!ns) 86 if (!ns)
87 return -ENOMEM; 87 return -ENOMEM;
88 88
89 ret = proc_alloc_inum(&ns->proc_inum); 89 ret = ns_alloc_inum(&ns->ns);
90 if (ret) { 90 if (ret) {
91 kmem_cache_free(user_ns_cachep, ns); 91 kmem_cache_free(user_ns_cachep, ns);
92 return ret; 92 return ret;
93 } 93 }
94 ns->ns.ops = &userns_operations;
94 95
95 atomic_set(&ns->count, 1); 96 atomic_set(&ns->count, 1);
96 /* Leave the new->user_ns reference with the new user namespace. */ 97 /* Leave the new->user_ns reference with the new user namespace. */
@@ -136,7 +137,7 @@ void free_user_ns(struct user_namespace *ns)
136#ifdef CONFIG_PERSISTENT_KEYRINGS 137#ifdef CONFIG_PERSISTENT_KEYRINGS
137 key_put(ns->persistent_keyring_register); 138 key_put(ns->persistent_keyring_register);
138#endif 139#endif
139 proc_free_inum(ns->proc_inum); 140 ns_free_inum(&ns->ns);
140 kmem_cache_free(user_ns_cachep, ns); 141 kmem_cache_free(user_ns_cachep, ns);
141 ns = parent; 142 ns = parent;
142 } while (atomic_dec_and_test(&parent->count)); 143 } while (atomic_dec_and_test(&parent->count));
@@ -841,7 +842,12 @@ static bool new_idmap_permitted(const struct file *file,
841 return false; 842 return false;
842} 843}
843 844
844static void *userns_get(struct task_struct *task) 845static inline struct user_namespace *to_user_ns(struct ns_common *ns)
846{
847 return container_of(ns, struct user_namespace, ns);
848}
849
850static struct ns_common *userns_get(struct task_struct *task)
845{ 851{
846 struct user_namespace *user_ns; 852 struct user_namespace *user_ns;
847 853
@@ -849,17 +855,17 @@ static void *userns_get(struct task_struct *task)
849 user_ns = get_user_ns(__task_cred(task)->user_ns); 855 user_ns = get_user_ns(__task_cred(task)->user_ns);
850 rcu_read_unlock(); 856 rcu_read_unlock();
851 857
852 return user_ns; 858 return user_ns ? &user_ns->ns : NULL;
853} 859}
854 860
855static void userns_put(void *ns) 861static void userns_put(struct ns_common *ns)
856{ 862{
857 put_user_ns(ns); 863 put_user_ns(to_user_ns(ns));
858} 864}
859 865
860static int userns_install(struct nsproxy *nsproxy, void *ns) 866static int userns_install(struct nsproxy *nsproxy, struct ns_common *ns)
861{ 867{
862 struct user_namespace *user_ns = ns; 868 struct user_namespace *user_ns = to_user_ns(ns);
863 struct cred *cred; 869 struct cred *cred;
864 870
865 /* Don't allow gaining capabilities by reentering 871 /* Don't allow gaining capabilities by reentering
@@ -888,19 +894,12 @@ static int userns_install(struct nsproxy *nsproxy, void *ns)
888 return commit_creds(cred); 894 return commit_creds(cred);
889} 895}
890 896
891static unsigned int userns_inum(void *ns)
892{
893 struct user_namespace *user_ns = ns;
894 return user_ns->proc_inum;
895}
896
897const struct proc_ns_operations userns_operations = { 897const struct proc_ns_operations userns_operations = {
898 .name = "user", 898 .name = "user",
899 .type = CLONE_NEWUSER, 899 .type = CLONE_NEWUSER,
900 .get = userns_get, 900 .get = userns_get,
901 .put = userns_put, 901 .put = userns_put,
902 .install = userns_install, 902 .install = userns_install,
903 .inum = userns_inum,
904}; 903};
905 904
906static __init int user_namespaces_init(void) 905static __init int user_namespaces_init(void)
diff --git a/kernel/utsname.c b/kernel/utsname.c
index 883aaaa7de8a..831ea7108232 100644
--- a/kernel/utsname.c
+++ b/kernel/utsname.c
@@ -42,12 +42,14 @@ static struct uts_namespace *clone_uts_ns(struct user_namespace *user_ns,
42 if (!ns) 42 if (!ns)
43 return ERR_PTR(-ENOMEM); 43 return ERR_PTR(-ENOMEM);
44 44
45 err = proc_alloc_inum(&ns->proc_inum); 45 err = ns_alloc_inum(&ns->ns);
46 if (err) { 46 if (err) {
47 kfree(ns); 47 kfree(ns);
48 return ERR_PTR(err); 48 return ERR_PTR(err);
49 } 49 }
50 50
51 ns->ns.ops = &utsns_operations;
52
51 down_read(&uts_sem); 53 down_read(&uts_sem);
52 memcpy(&ns->name, &old_ns->name, sizeof(ns->name)); 54 memcpy(&ns->name, &old_ns->name, sizeof(ns->name));
53 ns->user_ns = get_user_ns(user_ns); 55 ns->user_ns = get_user_ns(user_ns);
@@ -84,11 +86,16 @@ void free_uts_ns(struct kref *kref)
84 86
85 ns = container_of(kref, struct uts_namespace, kref); 87 ns = container_of(kref, struct uts_namespace, kref);
86 put_user_ns(ns->user_ns); 88 put_user_ns(ns->user_ns);
87 proc_free_inum(ns->proc_inum); 89 ns_free_inum(&ns->ns);
88 kfree(ns); 90 kfree(ns);
89} 91}
90 92
91static void *utsns_get(struct task_struct *task) 93static inline struct uts_namespace *to_uts_ns(struct ns_common *ns)
94{
95 return container_of(ns, struct uts_namespace, ns);
96}
97
98static struct ns_common *utsns_get(struct task_struct *task)
92{ 99{
93 struct uts_namespace *ns = NULL; 100 struct uts_namespace *ns = NULL;
94 struct nsproxy *nsproxy; 101 struct nsproxy *nsproxy;
@@ -101,17 +108,17 @@ static void *utsns_get(struct task_struct *task)
101 } 108 }
102 task_unlock(task); 109 task_unlock(task);
103 110
104 return ns; 111 return ns ? &ns->ns : NULL;
105} 112}
106 113
107static void utsns_put(void *ns) 114static void utsns_put(struct ns_common *ns)
108{ 115{
109 put_uts_ns(ns); 116 put_uts_ns(to_uts_ns(ns));
110} 117}
111 118
112static int utsns_install(struct nsproxy *nsproxy, void *new) 119static int utsns_install(struct nsproxy *nsproxy, struct ns_common *new)
113{ 120{
114 struct uts_namespace *ns = new; 121 struct uts_namespace *ns = to_uts_ns(new);
115 122
116 if (!ns_capable(ns->user_ns, CAP_SYS_ADMIN) || 123 if (!ns_capable(ns->user_ns, CAP_SYS_ADMIN) ||
117 !ns_capable(current_user_ns(), CAP_SYS_ADMIN)) 124 !ns_capable(current_user_ns(), CAP_SYS_ADMIN))
@@ -123,18 +130,10 @@ static int utsns_install(struct nsproxy *nsproxy, void *new)
123 return 0; 130 return 0;
124} 131}
125 132
126static unsigned int utsns_inum(void *vp)
127{
128 struct uts_namespace *ns = vp;
129
130 return ns->proc_inum;
131}
132
133const struct proc_ns_operations utsns_operations = { 133const struct proc_ns_operations utsns_operations = {
134 .name = "uts", 134 .name = "uts",
135 .type = CLONE_NEWUTS, 135 .type = CLONE_NEWUTS,
136 .get = utsns_get, 136 .get = utsns_get,
137 .put = utsns_put, 137 .put = utsns_put,
138 .install = utsns_install, 138 .install = utsns_install,
139 .inum = utsns_inum,
140}; 139};