All of lore.kernel.org
 help / color / mirror / Atom feed
* PATCH] debug: add notifier chain debugging
@ 2008-08-15 22:29 Arjan van de Ven
  2008-08-15 22:53 ` Ingo Molnar
                   ` (2 more replies)
  0 siblings, 3 replies; 13+ messages in thread
From: Arjan van de Ven @ 2008-08-15 22:29 UTC (permalink / raw)
  To: linux-kernel; +Cc: mingo

From: Arjan van de Ven <arjan@linux.intel.com>
Subject: [PATCH] debug: add notifier chain debugging

during some development we suspected a case where we left something
in a notifier chain that was from a module that was unloaded already...
and that sort of thing is rather hard to track down.

This patch adds a very simple sanity check (which isn't all that
expensive) to make sure the notifier we're about to call is
actually from either the kernel itself of from a still-loaded
module, avoiding a hard-to-chase-down crash.

Signed-off-by: Arjan van de Ven <arjan@linux.intel.com>
---
 kernel/notifier.c |   16 ++++++++++++++++
 lib/Kconfig.debug |   10 ++++++++++
 2 files changed, 26 insertions(+), 0 deletions(-)

diff --git a/kernel/notifier.c b/kernel/notifier.c
index 823be11..143fdd7 100644
--- a/kernel/notifier.c
+++ b/kernel/notifier.c
@@ -21,6 +21,10 @@ BLOCKING_NOTIFIER_HEAD(reboot_notifier_list);
 static int notifier_chain_register(struct notifier_block **nl,
 		struct notifier_block *n)
 {
+	if (!kernel_text_address((unsigned long)n->notifier_call)) {
+		WARN(1, "Invalid notifier registered!");
+		return 0;
+	}
 	while ((*nl) != NULL) {
 		if (n->priority > (*nl)->priority)
 			break;
@@ -34,6 +38,10 @@ static int notifier_chain_register(struct notifier_block **nl,
 static int notifier_chain_cond_register(struct notifier_block **nl,
 		struct notifier_block *n)
 {
+	if (!kernel_text_address((unsigned long)n->notifier_call)) {
+		WARN(1, "Invalid notifier registered!");
+		return 0;
+	}
 	while ((*nl) != NULL) {
 		if ((*nl) == n)
 			return 0;
@@ -82,6 +90,14 @@ static int __kprobes notifier_call_chain(struct notifier_block **nl,
 
 	while (nb && nr_to_call) {
 		next_nb = rcu_dereference(nb->next);
+
+#ifdef CONFIG_DEBUG_NOTIFIERS
+		if (!kernel_text_address((unsigned long)nb->notifier_call)) {
+			WARN(1, "Invalid notifier called!");
+			nb = next_nb;
+			continue;
+		}
+#endif
 		ret = nb->notifier_call(nb, val, v);
 
 		if (nr_calls)
diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug
index 800ac84..f4bb36e 100644
--- a/lib/Kconfig.debug
+++ b/lib/Kconfig.debug
@@ -536,6 +536,16 @@ config DEBUG_SG
 
 	  If unsure, say N.
 
+config DEBUG_NOTIFIERS
+	bool "Debug notifier call chains"
+	depends on DEBUG_KERNEL
+	help
+	  Enable this to turn on sanity checking for notifier call chains.
+	  This is most useful for kernel developers to make sure that
+	  modules properly unregister themselves from notifier chains.
+	  This is a relatively cheap check but if you care about maximum
+	  performance, say N.
+
 config FRAME_POINTER
 	bool "Compile the kernel with frame pointers"
 	depends on DEBUG_KERNEL && \
-- 
1.5.5.1


^ permalink raw reply related	[flat|nested] 13+ messages in thread

end of thread, other threads:[~2008-08-27 10:55 UTC | newest]

Thread overview: 13+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-08-15 22:29 PATCH] debug: add notifier chain debugging Arjan van de Ven
2008-08-15 22:53 ` Ingo Molnar
2008-08-20  4:09 ` Andrew Morton
2008-08-20 10:53   ` Ingo Molnar
2008-08-22 14:00   ` Arjan van de Ven
2008-08-22 14:45     ` Christoph Hellwig
2008-08-25 22:39 ` Tony Luck
2008-08-26  4:55   ` Arjan van de Ven
2008-08-26  5:08     ` Tony Luck
2008-08-26 13:46       ` Arjan van de Ven
2008-08-26 16:22       ` Arjan van de Ven
2008-08-27  6:39         ` Ingo Molnar
2008-08-27 10:55           ` Arjan van de Ven

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.