From 038bd5c28d84b385e8a32147f99265f0c2b098ee Mon Sep 17 00:00:00 2001 From: Ingo Molnar Date: Tue, 23 Jan 2007 10:45:50 +0100 Subject: [PATCH] --- yaml --- r: 45745 b: refs/heads/master c: 1b5180b65122666a36a1a232b7b9b38b21a9dcdd h: refs/heads/master i: 45743: 072457a2a20be2365a7909c16e8766d3de683589 v: v3 --- [refs] | 2 +- trunk/kernel/sys.c | 15 +++++++++++---- 2 files changed, 12 insertions(+), 5 deletions(-) diff --git a/[refs] b/[refs] index 5dbb425429b6..4f72fe33922a 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: b53d0b919ebe227e2b8e49b6e0ddee506be83aa8 +refs/heads/master: 1b5180b65122666a36a1a232b7b9b38b21a9dcdd diff --git a/trunk/kernel/sys.c b/trunk/kernel/sys.c index c7675c1bfdf2..6e2101dec0fc 100644 --- a/trunk/kernel/sys.c +++ b/trunk/kernel/sys.c @@ -323,11 +323,18 @@ EXPORT_SYMBOL_GPL(blocking_notifier_chain_unregister); int blocking_notifier_call_chain(struct blocking_notifier_head *nh, unsigned long val, void *v) { - int ret; + int ret = NOTIFY_DONE; - down_read(&nh->rwsem); - ret = notifier_call_chain(&nh->head, val, v); - up_read(&nh->rwsem); + /* + * We check the head outside the lock, but if this access is + * racy then it does not matter what the result of the test + * is, we re-check the list after having taken the lock anyway: + */ + if (rcu_dereference(nh->head)) { + down_read(&nh->rwsem); + ret = notifier_call_chain(&nh->head, val, v); + up_read(&nh->rwsem); + } return ret; }