aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/fork.c
diff options
context:
space:
mode:
authorBen Blum <bblum@andrew.cmu.edu>2011-05-26 19:25:18 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2011-05-26 20:12:34 -0400
commit4714d1d32d97239fb5ae3e10521d3f133a899b66 (patch)
treefb50707cefc386bf4e87cac9661a38dcfe3192df /kernel/fork.c
parentdcb3a08e69629ea65a3e9647da730bfaf670497d (diff)
cgroups: read-write lock CLONE_THREAD forking per threadgroup
Adds functionality to read/write lock CLONE_THREAD fork()ing per-threadgroup Add an rwsem that lives in a threadgroup's signal_struct that's taken for reading in the fork path, under CONFIG_CGROUPS. If another part of the kernel later wants to use such a locking mechanism, the CONFIG_CGROUPS ifdefs should be changed to a higher-up flag that CGROUPS and the other system would both depend on. This is a pre-patch for cgroup-procs-write.patch. Signed-off-by: Ben Blum <bblum@andrew.cmu.edu> Cc: "Eric W. Biederman" <ebiederm@xmission.com> Cc: Li Zefan <lizf@cn.fujitsu.com> Cc: Matt Helsley <matthltc@us.ibm.com> Reviewed-by: Paul Menage <menage@google.com> Cc: Oleg Nesterov <oleg@redhat.com> Cc: David Rientjes <rientjes@google.com> Cc: Miao Xie <miaox@cn.fujitsu.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel/fork.c')
-rw-r--r--kernel/fork.c10
1 files changed, 10 insertions, 0 deletions
diff --git a/kernel/fork.c b/kernel/fork.c
index 8e7e135d0817..1fa9d940e301 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -957,6 +957,10 @@ static int copy_signal(unsigned long clone_flags, struct task_struct *tsk)
957 tty_audit_fork(sig); 957 tty_audit_fork(sig);
958 sched_autogroup_fork(sig); 958 sched_autogroup_fork(sig);
959 959
960#ifdef CONFIG_CGROUPS
961 init_rwsem(&sig->threadgroup_fork_lock);
962#endif
963
960 sig->oom_adj = current->signal->oom_adj; 964 sig->oom_adj = current->signal->oom_adj;
961 sig->oom_score_adj = current->signal->oom_score_adj; 965 sig->oom_score_adj = current->signal->oom_score_adj;
962 sig->oom_score_adj_min = current->signal->oom_score_adj_min; 966 sig->oom_score_adj_min = current->signal->oom_score_adj_min;
@@ -1138,6 +1142,8 @@ static struct task_struct *copy_process(unsigned long clone_flags,
1138 monotonic_to_bootbased(&p->real_start_time); 1142 monotonic_to_bootbased(&p->real_start_time);
1139 p->io_context = NULL; 1143 p->io_context = NULL;
1140 p->audit_context = NULL; 1144 p->audit_context = NULL;
1145 if (clone_flags & CLONE_THREAD)
1146 threadgroup_fork_read_lock(current);
1141 cgroup_fork(p); 1147 cgroup_fork(p);
1142#ifdef CONFIG_NUMA 1148#ifdef CONFIG_NUMA
1143 p->mempolicy = mpol_dup(p->mempolicy); 1149 p->mempolicy = mpol_dup(p->mempolicy);
@@ -1342,6 +1348,8 @@ static struct task_struct *copy_process(unsigned long clone_flags,
1342 write_unlock_irq(&tasklist_lock); 1348 write_unlock_irq(&tasklist_lock);
1343 proc_fork_connector(p); 1349 proc_fork_connector(p);
1344 cgroup_post_fork(p); 1350 cgroup_post_fork(p);
1351 if (clone_flags & CLONE_THREAD)
1352 threadgroup_fork_read_unlock(current);
1345 perf_event_fork(p); 1353 perf_event_fork(p);
1346 return p; 1354 return p;
1347 1355
@@ -1380,6 +1388,8 @@ bad_fork_cleanup_policy:
1380 mpol_put(p->mempolicy); 1388 mpol_put(p->mempolicy);
1381bad_fork_cleanup_cgroup: 1389bad_fork_cleanup_cgroup:
1382#endif 1390#endif
1391 if (clone_flags & CLONE_THREAD)
1392 threadgroup_fork_read_unlock(current);
1383 cgroup_exit(p, cgroup_callbacks_done); 1393 cgroup_exit(p, cgroup_callbacks_done);
1384 delayacct_tsk_free(p); 1394 delayacct_tsk_free(p);
1385 module_put(task_thread_info(p)->exec_domain->module); 1395 module_put(task_thread_info(p)->exec_domain->module);