summaryrefslogtreecommitdiffstats
path: root/kernel/cgroup.c
diff options
context:
space:
mode:
authorTejun Heo <tj@kernel.org>2015-09-25 16:24:27 -0400
committerTejun Heo <tj@kernel.org>2015-09-25 16:25:07 -0400
commita3e72739b7a7ea225dd11c4096f97123f6427d87 (patch)
tree60f7c8d79db9e09f2ac8b097928fa0e4034ba631 /kernel/cgroup.c
parentc0522908d22e0b8669e01a7706720996c773e7f4 (diff)
downloadlinux-a3e72739b7a7ea225dd11c4096f97123f6427d87.tar.bz2
cgroup: fix too early usage of static_branch_disable()
49d1dc4b8179 ("cgroup: implement static_key based cgroup_subsys_enabled() and cgroup_subsys_on_dfl()") converted cgroup enabled test to use static_key; however, cgroup_disable() is called before static_key subsystem itself is initialized and thus leads to the following warning when "cgroup_disable=" parameter is specified. WARNING: CPU: 0 PID: 0 at kernel/jump_label.c:99 static_key_slow_dec+0x44/0x60() static_key_slow_dec used before call to jump_label_init ... Call Trace: [<ffffffff813b18c2>] dump_stack+0x44/0x62 [<ffffffff8108dd52>] warn_slowpath_common+0x82/0xc0 [<ffffffff8108ddec>] warn_slowpath_fmt+0x5c/0x80 [<ffffffff8119c054>] static_key_slow_dec+0x44/0x60 [<ffffffff81d826b6>] cgroup_disable+0xaf/0xd6 [<ffffffff81d5f9de>] unknown_bootoption+0x8c/0x194 [<ffffffff810b0c03>] parse_args+0x273/0x4a0 [<ffffffff81d5fd67>] start_kernel+0x205/0x4b8 ... Fix it by making cgroup_disable() to record the subsystems to disable in cgroup_disable_mask and moving the actual application to cgroup_init() which is late enough and where the enabled state is first used. Signed-off-by: Tejun Heo <tj@kernel.org> Reported-by: Andrey Wagin <avagin@gmail.com> Link: http://lkml.kernel.org/g/CANaxB-yFuS4SA2znSvcKrO9L_CbHciHYW+o9bN8sZJ8eR9FxYA@mail.gmail.com Fixes: 49d1dc4b81797f88270832b11e9f73809e7e7209
Diffstat (limited to 'kernel/cgroup.c')
-rw-r--r--kernel/cgroup.c14
1 files changed, 8 insertions, 6 deletions
diff --git a/kernel/cgroup.c b/kernel/cgroup.c
index f924158a1b65..ae23814b0c6e 100644
--- a/kernel/cgroup.c
+++ b/kernel/cgroup.c
@@ -5124,6 +5124,8 @@ int __init cgroup_init_early(void)
return 0;
}
+static unsigned long cgroup_disable_mask __initdata;
+
/**
* cgroup_init - cgroup initialization
*
@@ -5170,8 +5172,12 @@ int __init cgroup_init(void)
* disabled flag and cftype registration needs kmalloc,
* both of which aren't available during early_init.
*/
- if (!cgroup_ssid_enabled(ssid))
+ if (cgroup_disable_mask & (1 << ssid)) {
+ static_branch_disable(cgroup_subsys_enabled_key[ssid]);
+ printk(KERN_INFO "Disabling %s control group subsystem\n",
+ ss->name);
continue;
+ }
cgrp_dfl_root.subsys_mask |= 1 << ss->id;
@@ -5595,11 +5601,7 @@ static int __init cgroup_disable(char *str)
if (strcmp(token, ss->name) &&
strcmp(token, ss->legacy_name))
continue;
-
- static_branch_disable(cgroup_subsys_enabled_key[i]);
- printk(KERN_INFO "Disabling %s control group subsystem\n",
- ss->name);
- break;
+ cgroup_disable_mask |= 1 << i;
}
}
return 1;