perf events: Fix ring_buffer_wakeup() brown paperbag bug
authorWill Deacon <will.deacon@arm.com>
Tue, 13 Dec 2011 19:40:45 +0000 (20:40 +0100)
committerIngo Molnar <mingo@elte.hu>
Wed, 14 Dec 2011 07:44:53 +0000 (08:44 +0100)
Commit 10c6db11 ("perf: Fix loss of notification with multi-event")
seems to unconditionally dereference event->rb in the wakeup handler,
this is wrong, there might not be a buffer attached.

Signed-off-by: Will Deacon <will.deacon@arm.com>
Signed-off-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
Link: http://lkml.kernel.org/r/20111213152651.GP20297@mudshark.cambridge.arm.com
[ minor edits ]
Signed-off-by: Ingo Molnar <mingo@elte.hu>
kernel/events/core.c

index d3b9df5962c25bdbd3ca324756474366ff8c6d68..58690af323e469213db42bce2c0d1a772db12519 100644 (file)
@@ -3558,9 +3558,13 @@ static void ring_buffer_wakeup(struct perf_event *event)
 
        rcu_read_lock();
        rb = rcu_dereference(event->rb);
-       list_for_each_entry_rcu(event, &rb->event_list, rb_entry) {
+       if (!rb)
+               goto unlock;
+
+       list_for_each_entry_rcu(event, &rb->event_list, rb_entry)
                wake_up_all(&event->waitq);
-       }
+
+unlock:
        rcu_read_unlock();
 }