-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
cgroups: implement namespace tracking subsystem
When a task enters a new namespace via a clone() or unshare(), a new cgroup is created and the task moves into it. This version names cgroups which are automatically created using cgroup_clone() as "node_<pid>" where pid is the pid of the unsharing or cloned process. (Thanks Pavel for the idea) This is safe because if the process unshares again, it will create /cgroups/(...)/node_<pid>/node_<pid> The only possibilities (AFAICT) for a -EEXIST on unshare are 1. pid wraparound 2. a process fails an unshare, then tries again. Case 1 is unlikely enough that I ignore it (at least for now). In case 2, the node_<pid> will be empty and can be rmdir'ed to make the subsequent unshare() succeed. Changelog: Name cloned cgroups as "node_<pid>". [[email protected]: fix order of cgroup subsystems in init/Kconfig] Signed-off-by: Serge E. Hallyn <[email protected]> Cc: Paul Menage <[email protected]> Signed-off-by: Cedric Le Goater <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
- Loading branch information
Serge E. Hallyn
authored and
Linus Torvalds
committed
Oct 19, 2007
1 parent
846c7bb
commit 858d72e
Showing
6 changed files
with
146 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -24,3 +24,9 @@ SUBSYS(debug) | |
#endif | ||
|
||
/* */ | ||
|
||
#ifdef CONFIG_CGROUP_NS | ||
SUBSYS(ns) | ||
#endif | ||
|
||
/* */ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,100 @@ | ||
/* | ||
* ns_cgroup.c - namespace cgroup subsystem | ||
* | ||
* Copyright 2006, 2007 IBM Corp | ||
*/ | ||
|
||
#include <linux/module.h> | ||
#include <linux/cgroup.h> | ||
#include <linux/fs.h> | ||
|
||
struct ns_cgroup { | ||
struct cgroup_subsys_state css; | ||
spinlock_t lock; | ||
}; | ||
|
||
struct cgroup_subsys ns_subsys; | ||
|
||
static inline struct ns_cgroup *cgroup_to_ns( | ||
struct cgroup *cgroup) | ||
{ | ||
return container_of(cgroup_subsys_state(cgroup, ns_subsys_id), | ||
struct ns_cgroup, css); | ||
} | ||
|
||
int ns_cgroup_clone(struct task_struct *task) | ||
{ | ||
return cgroup_clone(task, &ns_subsys); | ||
} | ||
|
||
/* | ||
* Rules: | ||
* 1. you can only enter a cgroup which is a child of your current | ||
* cgroup | ||
* 2. you can only place another process into a cgroup if | ||
* a. you have CAP_SYS_ADMIN | ||
* b. your cgroup is an ancestor of task's destination cgroup | ||
* (hence either you are in the same cgroup as task, or in an | ||
* ancestor cgroup thereof) | ||
*/ | ||
static int ns_can_attach(struct cgroup_subsys *ss, | ||
struct cgroup *new_cgroup, struct task_struct *task) | ||
{ | ||
struct cgroup *orig; | ||
|
||
if (current != task) { | ||
if (!capable(CAP_SYS_ADMIN)) | ||
return -EPERM; | ||
|
||
if (!cgroup_is_descendant(new_cgroup)) | ||
return -EPERM; | ||
} | ||
|
||
if (atomic_read(&new_cgroup->count) != 0) | ||
return -EPERM; | ||
|
||
orig = task_cgroup(task, ns_subsys_id); | ||
if (orig && orig != new_cgroup->parent) | ||
return -EPERM; | ||
|
||
return 0; | ||
} | ||
|
||
/* | ||
* Rules: you can only create a cgroup if | ||
* 1. you are capable(CAP_SYS_ADMIN) | ||
* 2. the target cgroup is a descendant of your own cgroup | ||
*/ | ||
static struct cgroup_subsys_state *ns_create(struct cgroup_subsys *ss, | ||
struct cgroup *cgroup) | ||
{ | ||
struct ns_cgroup *ns_cgroup; | ||
|
||
if (!capable(CAP_SYS_ADMIN)) | ||
return ERR_PTR(-EPERM); | ||
if (!cgroup_is_descendant(cgroup)) | ||
return ERR_PTR(-EPERM); | ||
|
||
ns_cgroup = kzalloc(sizeof(*ns_cgroup), GFP_KERNEL); | ||
if (!ns_cgroup) | ||
return ERR_PTR(-ENOMEM); | ||
spin_lock_init(&ns_cgroup->lock); | ||
return &ns_cgroup->css; | ||
} | ||
|
||
static void ns_destroy(struct cgroup_subsys *ss, | ||
struct cgroup *cgroup) | ||
{ | ||
struct ns_cgroup *ns_cgroup; | ||
|
||
ns_cgroup = cgroup_to_ns(cgroup); | ||
kfree(ns_cgroup); | ||
} | ||
|
||
struct cgroup_subsys ns_subsys = { | ||
.name = "ns", | ||
.can_attach = ns_can_attach, | ||
.create = ns_create, | ||
.destroy = ns_destroy, | ||
.subsys_id = ns_subsys_id, | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters