[v6,17/46] clockevents: Use get/put_online_cpus_atomic() in clockevents_notify()

Message ID 20130218124042.26245.92242.stgit@srivatsabhat.in.ibm.com
State Not Applicable
Headers show

Commit Message

Srivatsa S. Bhat Feb. 18, 2013, 12:40 p.m.
The cpu idle code invokes clockevents_notify() during idle state transitions
and the cpu offline code invokes it during the CPU_DYING phase. There
seems to be a race-condition between the two, where the clockevents_lock
never gets released, ending in a lockup. This can be fixed by synchronizing
clockevents_notify() with CPU offline, by wrapping its contents within

Signed-off-by: Srivatsa S. Bhat <srivatsa.bhat@linux.vnet.ibm.com>

 kernel/time/clockevents.c |    3 +++
 1 file changed, 3 insertions(+)


diff --git a/kernel/time/clockevents.c b/kernel/time/clockevents.c
index 30b6de0..ca340fd 100644
--- a/kernel/time/clockevents.c
+++ b/kernel/time/clockevents.c
@@ -17,6 +17,7 @@ 
 #include <linux/module.h>
 #include <linux/notifier.h>
 #include <linux/smp.h>
+#include <linux/cpu.h>
 #include "tick-internal.h"
@@ -431,6 +432,7 @@  void clockevents_notify(unsigned long reason, void *arg)
 	unsigned long flags;
 	int cpu;
+	get_online_cpus_atomic();
 	raw_spin_lock_irqsave(&clockevents_lock, flags);
 	clockevents_do_notify(reason, arg);
@@ -459,6 +461,7 @@  void clockevents_notify(unsigned long reason, void *arg)
 	raw_spin_unlock_irqrestore(&clockevents_lock, flags);
+	put_online_cpus_atomic();