diff options
Diffstat (limited to 'kernel/kthread.c')
-rw-r--r-- | kernel/kthread.c | 8 |
1 files changed, 6 insertions, 2 deletions
diff --git a/kernel/kthread.c b/kernel/kthread.c index c52a05a8ec52..f5dc0b151d61 100644 --- a/kernel/kthread.c +++ b/kernel/kthread.c | |||
@@ -390,10 +390,10 @@ struct task_struct *kthread_create_on_cpu(int (*threadfn)(void *data), | |||
390 | cpu); | 390 | cpu); |
391 | if (IS_ERR(p)) | 391 | if (IS_ERR(p)) |
392 | return p; | 392 | return p; |
393 | kthread_bind(p, cpu); | ||
394 | /* CPU hotplug need to bind once again when unparking the thread. */ | ||
393 | set_bit(KTHREAD_IS_PER_CPU, &to_kthread(p)->flags); | 395 | set_bit(KTHREAD_IS_PER_CPU, &to_kthread(p)->flags); |
394 | to_kthread(p)->cpu = cpu; | 396 | to_kthread(p)->cpu = cpu; |
395 | /* Park the thread to get it out of TASK_UNINTERRUPTIBLE state */ | ||
396 | kthread_park(p); | ||
397 | return p; | 397 | return p; |
398 | } | 398 | } |
399 | 399 | ||
@@ -407,6 +407,10 @@ static void __kthread_unpark(struct task_struct *k, struct kthread *kthread) | |||
407 | * which might be about to be cleared. | 407 | * which might be about to be cleared. |
408 | */ | 408 | */ |
409 | if (test_and_clear_bit(KTHREAD_IS_PARKED, &kthread->flags)) { | 409 | if (test_and_clear_bit(KTHREAD_IS_PARKED, &kthread->flags)) { |
410 | /* | ||
411 | * Newly created kthread was parked when the CPU was offline. | ||
412 | * The binding was lost and we need to set it again. | ||
413 | */ | ||
410 | if (test_bit(KTHREAD_IS_PER_CPU, &kthread->flags)) | 414 | if (test_bit(KTHREAD_IS_PER_CPU, &kthread->flags)) |
411 | __kthread_bind(k, kthread->cpu, TASK_PARKED); | 415 | __kthread_bind(k, kthread->cpu, TASK_PARKED); |
412 | wake_up_state(k, TASK_PARKED); | 416 | wake_up_state(k, TASK_PARKED); |