Commit fc75cdfa5b43ac4d3232b490800cd35063adafd3
Committed by
Linus Torvalds
1 parent
04a3446c90
Exists in
master
and in
7 other branches
[PATCH] cpu hotplug: fix CPU_UP_CANCEL handling
If a cpu hotplug callback fails on CPU_UP_PREPARE, all callbacks will be called with CPU_UP_CANCELED. A few of these callbacks assume that on CPU_UP_PREPARE a pointer to task has been stored in a percpu array. This assumption is not true if CPU_UP_PREPARE fails and the following calls to kthread_bind() in CPU_UP_CANCELED will cause an addressing exception because of passing a NULL pointer. Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com> Cc: Ashok Raj <ashok.raj@intel.com> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Showing 4 changed files with 8 additions and 0 deletions Side-by-side Diff
kernel/sched.c
... | ... | @@ -4756,6 +4756,8 @@ |
4756 | 4756 | break; |
4757 | 4757 | #ifdef CONFIG_HOTPLUG_CPU |
4758 | 4758 | case CPU_UP_CANCELED: |
4759 | + if (!cpu_rq(cpu)->migration_thread) | |
4760 | + break; | |
4759 | 4761 | /* Unbind it from offline cpu so it can run. Fall thru. */ |
4760 | 4762 | kthread_bind(cpu_rq(cpu)->migration_thread, |
4761 | 4763 | any_online_cpu(cpu_online_map)); |
kernel/softirq.c
kernel/softlockup.c
... | ... | @@ -127,6 +127,8 @@ |
127 | 127 | break; |
128 | 128 | #ifdef CONFIG_HOTPLUG_CPU |
129 | 129 | case CPU_UP_CANCELED: |
130 | + if (!per_cpu(watchdog_task, hotcpu)) | |
131 | + break; | |
130 | 132 | /* Unbind so it can run. Fall thru. */ |
131 | 133 | kthread_bind(per_cpu(watchdog_task, hotcpu), |
132 | 134 | any_online_cpu(cpu_online_map)); |
kernel/workqueue.c
... | ... | @@ -590,6 +590,8 @@ |
590 | 590 | |
591 | 591 | case CPU_UP_CANCELED: |
592 | 592 | list_for_each_entry(wq, &workqueues, list) { |
593 | + if (!per_cpu_ptr(wq->cpu_wq, hotcpu)->thread) | |
594 | + continue; | |
593 | 595 | /* Unbind so it can run. */ |
594 | 596 | kthread_bind(per_cpu_ptr(wq->cpu_wq, hotcpu)->thread, |
595 | 597 | any_online_cpu(cpu_online_map)); |