diff options
author | Zefan Li <lizefan@huawei.com> | 2017-04-18 22:15:59 -0400 |
---|---|---|
committer | Tejun Heo <tj@kernel.org> | 2017-04-28 18:04:54 -0400 |
commit | 9732adc5d6520238223df16630f1f8cad2269317 (patch) | |
tree | b10b3242df285c38a45e4b8039b2e860a9e20def /kernel/cgroup/cgroup.c | |
parent | a590b90d472f2c176c140576ee3ab44df7f67839 (diff) |
cgroup: avoid attaching a cgroup root to two different superblocks, take 2
Commit bfb0b80db5f9 ("cgroup: avoid attaching a cgroup root to two
different superblocks") is broken. Now we try to fix the race by
delaying the initialization of cgroup root refcnt until a superblock
has been allocated.
Reported-by: Dmitry Vyukov <dvyukov@google.com>
Reported-by: Andrei Vagin <avagin@virtuozzo.com>
Tested-by: Andrei Vagin <avagin@virtuozzo.com>
Signed-off-by: Zefan Li <lizefan@huawei.com>
Signed-off-by: Tejun Heo <tj@kernel.org>
Diffstat (limited to 'kernel/cgroup/cgroup.c')
-rw-r--r-- | kernel/cgroup/cgroup.c | 8 |
1 files changed, 4 insertions, 4 deletions
diff --git a/kernel/cgroup/cgroup.c b/kernel/cgroup/cgroup.c index 10951d5e35d2..38d9386f46e7 100644 --- a/kernel/cgroup/cgroup.c +++ b/kernel/cgroup/cgroup.c | |||
@@ -1645,7 +1645,7 @@ void init_cgroup_root(struct cgroup_root *root, struct cgroup_sb_opts *opts) | |||
1645 | set_bit(CGRP_CPUSET_CLONE_CHILDREN, &root->cgrp.flags); | 1645 | set_bit(CGRP_CPUSET_CLONE_CHILDREN, &root->cgrp.flags); |
1646 | } | 1646 | } |
1647 | 1647 | ||
1648 | int cgroup_setup_root(struct cgroup_root *root, u16 ss_mask) | 1648 | int cgroup_setup_root(struct cgroup_root *root, u16 ss_mask, int ref_flags) |
1649 | { | 1649 | { |
1650 | LIST_HEAD(tmp_links); | 1650 | LIST_HEAD(tmp_links); |
1651 | struct cgroup *root_cgrp = &root->cgrp; | 1651 | struct cgroup *root_cgrp = &root->cgrp; |
@@ -1661,8 +1661,8 @@ int cgroup_setup_root(struct cgroup_root *root, u16 ss_mask) | |||
1661 | root_cgrp->id = ret; | 1661 | root_cgrp->id = ret; |
1662 | root_cgrp->ancestor_ids[0] = ret; | 1662 | root_cgrp->ancestor_ids[0] = ret; |
1663 | 1663 | ||
1664 | ret = percpu_ref_init(&root_cgrp->self.refcnt, css_release, 0, | 1664 | ret = percpu_ref_init(&root_cgrp->self.refcnt, css_release, |
1665 | GFP_KERNEL); | 1665 | ref_flags, GFP_KERNEL); |
1666 | if (ret) | 1666 | if (ret) |
1667 | goto out; | 1667 | goto out; |
1668 | 1668 | ||
@@ -4517,7 +4517,7 @@ int __init cgroup_init(void) | |||
4517 | hash_add(css_set_table, &init_css_set.hlist, | 4517 | hash_add(css_set_table, &init_css_set.hlist, |
4518 | css_set_hash(init_css_set.subsys)); | 4518 | css_set_hash(init_css_set.subsys)); |
4519 | 4519 | ||
4520 | BUG_ON(cgroup_setup_root(&cgrp_dfl_root, 0)); | 4520 | BUG_ON(cgroup_setup_root(&cgrp_dfl_root, 0, 0)); |
4521 | 4521 | ||
4522 | mutex_unlock(&cgroup_mutex); | 4522 | mutex_unlock(&cgroup_mutex); |
4523 | 4523 | ||