Skip to content

Commit

Permalink
Handle interrupted kthread_create() and ENOMEM failures.
Browse files Browse the repository at this point in the history
Kernels >= 3.13 can return ENOMEM from kthread_create() in both a true
out of memory situation and also if the call is interrupted.  Re-try
the kthread_create() in these cases.
  • Loading branch information
dweeezil committed Apr 7, 2014
1 parent 4c99541 commit 5ac44ed
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 4 deletions.
19 changes: 15 additions & 4 deletions module/spl/spl-taskq.c
Original file line number Diff line number Diff line change
Expand Up @@ -839,16 +839,27 @@ taskq_create(const char *name, int nthreads, pri_t pri,
tqt->tqt_tq = tq;
tqt->tqt_id = 0;

restart:
tqt->tqt_thread = kthread_create(taskq_thread, tqt,
"%s/%d", name, i);
if (tqt->tqt_thread) {
if (IS_ERR(tqt->tqt_thread)) {
/* Re-try on interrupted kthread_create() */
if (signal_pending(current)) {
clear_thread_flag(TIF_SIGPENDING);
goto restart;
}
/* Re-try on a "real" ENOMEM */
if (PTR_ERR(tqt->tqt_thread) == -ENOMEM) {
goto restart;
}
/* Return NULL on any other error */
kmem_free(tqt, sizeof(*tqt));
rc = 1;
} else {
list_add(&tqt->tqt_thread_list, &tq->tq_thread_list);
set_user_nice(tqt->tqt_thread, PRIO_TO_NICE(pri));
wake_up_process(tqt->tqt_thread);
j++;
} else {
kmem_free(tqt, sizeof(taskq_thread_t));
rc = 1;
}
}

Expand Down
7 changes: 7 additions & 0 deletions module/spl/spl-thread.c
Original file line number Diff line number Diff line change
Expand Up @@ -126,9 +126,16 @@ __thread_create(caddr_t stk, size_t stksize, thread_func_t func,
tp->tp_state = state;
tp->tp_pri = pri;

retry:
tsk = kthread_create(thread_generic_wrapper, (void *)tp,
"%s", tp->tp_name);
if (IS_ERR(tsk)) {
if (signal_pending(current)) {
clear_thread_flag(TIF_SIGPENDING);
goto retry;
}
if (PTR_ERR(tsk) == -ENOMEM)
goto retry;
SERROR("Failed to create thread: %ld\n", PTR_ERR(tsk));
SRETURN(NULL);
}
Expand Down

0 comments on commit 5ac44ed

Please sign in to comment.