Skip to content

Commit

Permalink
iscsi-target: Fix incorrect np->np_thread NULL assignment
Browse files Browse the repository at this point in the history
When shutting down a target there is a race condition between
iscsit_del_np() and __iscsi_target_login_thread().
The latter sets the thread pointer to NULL, and the former
tries to issue kthread_stop() on that pointer without any
synchronization.

This patch moves the np->np_thread NULL assignment into
iscsit_del_np(), after kthread_stop() has completed. It also
removes the signal_pending() + np_state check, and only
exits when kthread_should_stop() is true.

Reported-by: Hannes Reinecke <hare@suse.de>
Cc: <stable@vger.kernel.org> #3.12+
Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
  • Loading branch information
Nicholas Bellinger committed Dec 19, 2013
1 parent 63832aa commit db6077f
Show file tree
Hide file tree
Showing 2 changed files with 1 addition and 6 deletions.
1 change: 1 addition & 0 deletions drivers/target/iscsi/iscsi_target.c
Original file line number Diff line number Diff line change
Expand Up @@ -465,6 +465,7 @@ int iscsit_del_np(struct iscsi_np *np)
*/
send_sig(SIGINT, np->np_thread, 1);
kthread_stop(np->np_thread);
np->np_thread = NULL;
}

np->np_transport->iscsit_free_np(np);
Expand Down
6 changes: 0 additions & 6 deletions drivers/target/iscsi/iscsi_target_login.c
Original file line number Diff line number Diff line change
Expand Up @@ -1403,19 +1403,13 @@ static int __iscsi_target_login_thread(struct iscsi_np *np)

out:
stop = kthread_should_stop();
if (!stop && signal_pending(current)) {
spin_lock_bh(&np->np_thread_lock);
stop = (np->np_thread_state == ISCSI_NP_THREAD_SHUTDOWN);
spin_unlock_bh(&np->np_thread_lock);
}
/* Wait for another socket.. */
if (!stop)
return 1;
exit:
iscsi_stop_login_thread_timer(np);
spin_lock_bh(&np->np_thread_lock);
np->np_thread_state = ISCSI_NP_THREAD_EXIT;
np->np_thread = NULL;
spin_unlock_bh(&np->np_thread_lock);

return 0;
Expand Down

0 comments on commit db6077f

Please sign in to comment.