diff options
author | Nigel Cunningham <nigel@nigel.suspend2.net> | 2008-01-17 18:21:21 -0500 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2008-01-17 18:38:59 -0500 |
commit | 784680336b616dcc4c17cbd25add3b49c555cdeb (patch) | |
tree | e607ed69188a99590a7708c922500882702b8578 /kernel | |
parent | 34aebfd3bdc93c0c5614f1f61e43b6ddc4be52ae (diff) |
Fix unbalanced helper_lock in kernel/kmod.c
call_usermodehelper_exec() has an exit path that can leave the
helper_lock() call at the top of the routine unbalanced. The attached
patch fixes this issue.
Signed-off-by: Nigel Cunningham <nigel@tuxonice.net>
Cc: <stable@kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/kmod.c | 13 |
1 files changed, 6 insertions, 7 deletions
diff --git a/kernel/kmod.c b/kernel/kmod.c index c6a4f8aebeba..bb7df2a28bd7 100644 --- a/kernel/kmod.c +++ b/kernel/kmod.c | |||
@@ -451,13 +451,11 @@ int call_usermodehelper_exec(struct subprocess_info *sub_info, | |||
451 | enum umh_wait wait) | 451 | enum umh_wait wait) |
452 | { | 452 | { |
453 | DECLARE_COMPLETION_ONSTACK(done); | 453 | DECLARE_COMPLETION_ONSTACK(done); |
454 | int retval; | 454 | int retval = 0; |
455 | 455 | ||
456 | helper_lock(); | 456 | helper_lock(); |
457 | if (sub_info->path[0] == '\0') { | 457 | if (sub_info->path[0] == '\0') |
458 | retval = 0; | ||
459 | goto out; | 458 | goto out; |
460 | } | ||
461 | 459 | ||
462 | if (!khelper_wq || usermodehelper_disabled) { | 460 | if (!khelper_wq || usermodehelper_disabled) { |
463 | retval = -EBUSY; | 461 | retval = -EBUSY; |
@@ -468,13 +466,14 @@ int call_usermodehelper_exec(struct subprocess_info *sub_info, | |||
468 | sub_info->wait = wait; | 466 | sub_info->wait = wait; |
469 | 467 | ||
470 | queue_work(khelper_wq, &sub_info->work); | 468 | queue_work(khelper_wq, &sub_info->work); |
471 | if (wait == UMH_NO_WAIT) /* task has freed sub_info */ | 469 | if (wait == UMH_NO_WAIT) /* task has freed sub_info */ |
472 | return 0; | 470 | goto unlock; |
473 | wait_for_completion(&done); | 471 | wait_for_completion(&done); |
474 | retval = sub_info->retval; | 472 | retval = sub_info->retval; |
475 | 473 | ||
476 | out: | 474 | out: |
477 | call_usermodehelper_freeinfo(sub_info); | 475 | call_usermodehelper_freeinfo(sub_info); |
476 | unlock: | ||
478 | helper_unlock(); | 477 | helper_unlock(); |
479 | return retval; | 478 | return retval; |
480 | } | 479 | } |