diff options
| author | Linux Build Service Account <lnxbuild@localhost> | 2017-01-04 03:25:34 -0800 |
|---|---|---|
| committer | Gerrit - the friendly Code Review server <code-review@localhost> | 2017-01-04 03:25:34 -0800 |
| commit | 9a18201fc8d1698a42f42c51092c61b27acb7722 (patch) | |
| tree | 78920d18465698b26c111cf226e3e83748c27295 | |
| parent | f478111a155fb3f1ab2d9c19acbfe9139b199b90 (diff) | |
| parent | f67dcbea7f75a70601ac408416e572eac3f7d272 (diff) | |
Merge "sched: Fix deadlock between cpu hotplug and upmigrate change"
| -rw-r--r-- | kernel/sched/hmp.c | 27 |
1 files changed, 19 insertions, 8 deletions
diff --git a/kernel/sched/hmp.c b/kernel/sched/hmp.c index a8bf39c6d7d7..ab5587309760 100644 --- a/kernel/sched/hmp.c +++ b/kernel/sched/hmp.c @@ -1470,7 +1470,20 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, int ret; unsigned int old_val; unsigned int *data = (unsigned int *)table->data; - int update_min_nice = 0; + int update_task_count = 0; + + if (!sched_enable_hmp) + return 0; + + /* + * The policy mutex is acquired with cpu_hotplug.lock + * held from cpu_up()->cpufreq_governor_interactive()-> + * sched_set_window(). So enforce the same order here. + */ + if (write && (data == &sysctl_sched_upmigrate_pct)) { + update_task_count = 1; + get_online_cpus(); + } mutex_lock(&policy_mutex); @@ -1478,7 +1491,7 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, ret = proc_dointvec_minmax(table, write, buffer, lenp, ppos); - if (ret || !write || !sched_enable_hmp) + if (ret || !write) goto done; if (write && (old_val == *data)) @@ -1500,20 +1513,18 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, * includes taking runqueue lock of all online cpus and re-initiatizing * their big counter values based on changed criteria. */ - if ((data == &sysctl_sched_upmigrate_pct || update_min_nice)) { - get_online_cpus(); + if (update_task_count) pre_big_task_count_change(cpu_online_mask); - } set_hmp_defaults(); - if ((data == &sysctl_sched_upmigrate_pct || update_min_nice)) { + if (update_task_count) post_big_task_count_change(cpu_online_mask); - put_online_cpus(); - } done: mutex_unlock(&policy_mutex); + if (update_task_count) + put_online_cpus(); return ret; } |
