diff options
author | Scott Wood <scottwood@freescale.com> | 2014-04-07 23:49:35 (GMT) |
---|---|---|
committer | Scott Wood <scottwood@freescale.com> | 2014-04-07 23:49:35 (GMT) |
commit | 62b8c978ee6b8d135d9e7953221de58000dba986 (patch) | |
tree | 683b04b2e627f6710c22c151b23c8cc9a165315e /kernel/kthread.c | |
parent | 78fd82238d0e5716578c326404184a27ba67fd6e (diff) | |
download | linux-fsl-qoriq-62b8c978ee6b8d135d9e7953221de58000dba986.tar.xz |
Rewind v3.13-rc3+ (78fd82238d0e5716) to v3.12
Diffstat (limited to 'kernel/kthread.c')
-rw-r--r-- | kernel/kthread.c | 73 |
1 files changed, 18 insertions, 55 deletions
diff --git a/kernel/kthread.c b/kernel/kthread.c index b5ae3ee..760e86d 100644 --- a/kernel/kthread.c +++ b/kernel/kthread.c @@ -33,7 +33,7 @@ struct kthread_create_info /* Result passed back to kthread_create() from kthreadd. */ struct task_struct *result; - struct completion *done; + struct completion done; struct list_head list; }; @@ -178,7 +178,6 @@ static int kthread(void *_create) struct kthread_create_info *create = _create; int (*threadfn)(void *data) = create->threadfn; void *data = create->data; - struct completion *done; struct kthread self; int ret; @@ -188,16 +187,10 @@ static int kthread(void *_create) init_completion(&self.parked); current->vfork_done = &self.exited; - /* If user was SIGKILLed, I release the structure. */ - done = xchg(&create->done, NULL); - if (!done) { - kfree(create); - do_exit(-EINTR); - } /* OK, tell user we're spawned, wait for stop or wakeup */ __set_current_state(TASK_UNINTERRUPTIBLE); create->result = current; - complete(done); + complete(&create->done); schedule(); ret = -EINTR; @@ -230,15 +223,8 @@ static void create_kthread(struct kthread_create_info *create) /* We want our own signal handler (we take no signals by default). */ pid = kernel_thread(kthread, create, CLONE_FS | CLONE_FILES | SIGCHLD); if (pid < 0) { - /* If user was SIGKILLed, I release the structure. */ - struct completion *done = xchg(&create->done, NULL); - - if (!done) { - kfree(create); - return; - } create->result = ERR_PTR(pid); - complete(done); + complete(&create->done); } } @@ -269,59 +255,36 @@ struct task_struct *kthread_create_on_node(int (*threadfn)(void *data), const char namefmt[], ...) { - DECLARE_COMPLETION_ONSTACK(done); - struct task_struct *task; - struct kthread_create_info *create = kmalloc(sizeof(*create), - GFP_KERNEL); - - if (!create) - return ERR_PTR(-ENOMEM); - create->threadfn = threadfn; - create->data = data; - create->node = node; - create->done = &done; + struct kthread_create_info create; + + create.threadfn = threadfn; + create.data = data; + create.node = node; + init_completion(&create.done); spin_lock(&kthread_create_lock); - list_add_tail(&create->list, &kthread_create_list); + list_add_tail(&create.list, &kthread_create_list); spin_unlock(&kthread_create_lock); wake_up_process(kthreadd_task); - /* - * Wait for completion in killable state, for I might be chosen by - * the OOM killer while kthreadd is trying to allocate memory for - * new kernel thread. - */ - if (unlikely(wait_for_completion_killable(&done))) { - /* - * If I was SIGKILLed before kthreadd (or new kernel thread) - * calls complete(), leave the cleanup of this structure to - * that thread. - */ - if (xchg(&create->done, NULL)) - return ERR_PTR(-ENOMEM); - /* - * kthreadd (or new kernel thread) will call complete() - * shortly. - */ - wait_for_completion(&done); - } - task = create->result; - if (!IS_ERR(task)) { + wait_for_completion(&create.done); + + if (!IS_ERR(create.result)) { static const struct sched_param param = { .sched_priority = 0 }; va_list args; va_start(args, namefmt); - vsnprintf(task->comm, sizeof(task->comm), namefmt, args); + vsnprintf(create.result->comm, sizeof(create.result->comm), + namefmt, args); va_end(args); /* * root may have changed our (kthreadd's) priority or CPU mask. * The kernel thread should not inherit these properties. */ - sched_setscheduler_nocheck(task, SCHED_NORMAL, ¶m); - set_cpus_allowed_ptr(task, cpu_all_mask); + sched_setscheduler_nocheck(create.result, SCHED_NORMAL, ¶m); + set_cpus_allowed_ptr(create.result, cpu_all_mask); } - kfree(create); - return task; + return create.result; } EXPORT_SYMBOL(kthread_create_on_node); |