Patchwork [3.5.y.z,extended,stable] Patch "module: fix symbol waiting when module fails before init" has been added to staging queue

login
register
mail settings
Submitter Herton Ronaldo Krzesinski
Date Feb. 4, 2013, 9:46 p.m.
Message ID <1360014405-3959-1-git-send-email-herton.krzesinski@canonical.com>
Download mbox | patch
Permalink /patch/218088/
State New
Headers show

Comments

Herton Ronaldo Krzesinski - Feb. 4, 2013, 9:46 p.m.
This is a note to let you know that I have just added a patch titled

    module: fix symbol waiting when module fails before init

to the linux-3.5.y-queue branch of the 3.5.y.z extended stable tree 
which can be found at:

 http://kernel.ubuntu.com/git?p=ubuntu/linux.git;a=shortlog;h=refs/heads/linux-3.5.y-queue

If you, or anyone else, feels it should not be added to this tree, please 
reply to this email.

For more information about the 3.5.y.z tree, see
https://wiki.ubuntu.com/Kernel/Dev/ExtendedStable

Thanks.
-Herton

------

From ca8e2ca76a18083e66e48241d0d1204b72f70112 Mon Sep 17 00:00:00 2001
From: Rusty Russell <rusty@rustcorp.com.au>
Date: Fri, 28 Sep 2012 14:31:03 +0930
Subject: [PATCH] module: fix symbol waiting when module fails before init

commit 6f13909f4fe9652f189b462c6c98767309000321 upstream.

We use resolve_symbol_wait(), which blocks if the module containing
the symbol is still loading.  However:

1) The module_wq we use is only woken after calling the modules' init
   function, but there are other failure paths after the module is
   placed in the linked list where we need to do the same thing.

2) wake_up() only wakes one waiter, and our waitqueue is shared by all
   modules, so we need to wake them all.

3) wake_up_all() doesn't imply a memory barrier: I feel happier calling
   it after we've grabbed and dropped the module_mutex, not just after
   the state assignment.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
Signed-off-by: Herton Ronaldo Krzesinski <herton.krzesinski@canonical.com>
---
 kernel/module.c |    8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

--
1.7.9.5

Patch

diff --git a/kernel/module.c b/kernel/module.c
index 2a15c59..27e302a 100644
--- a/kernel/module.c
+++ b/kernel/module.c
@@ -2984,7 +2984,7 @@  static struct module *load_module(void __user *umod,
 	/* Unlink carefully: kallsyms could be walking list. */
 	list_del_rcu(&mod->list);
 	module_bug_cleanup(mod);
-
+	wake_up_all(&module_wq);
  ddebug:
 	dynamic_debug_remove(info.debug);
  unlock:
@@ -3059,7 +3059,7 @@  SYSCALL_DEFINE3(init_module, void __user *, umod,
 		blocking_notifier_call_chain(&module_notify_list,
 					     MODULE_STATE_GOING, mod);
 		free_module(mod);
-		wake_up(&module_wq);
+		wake_up_all(&module_wq);
 		return ret;
 	}
 	if (ret > 0) {
@@ -3071,9 +3071,8 @@  SYSCALL_DEFINE3(init_module, void __user *, umod,
 		dump_stack();
 	}

-	/* Now it's a first class citizen!  Wake up anyone waiting for it. */
+	/* Now it's a first class citizen! */
 	mod->state = MODULE_STATE_LIVE;
-	wake_up(&module_wq);
 	blocking_notifier_call_chain(&module_notify_list,
 				     MODULE_STATE_LIVE, mod);

@@ -3096,6 +3095,7 @@  SYSCALL_DEFINE3(init_module, void __user *, umod,
 	mod->init_ro_size = 0;
 	mod->init_text_size = 0;
 	mutex_unlock(&module_mutex);
+	wake_up_all(&module_wq);

 	return 0;
 }