From 3f9b1a883c61bf15c2dd623bf331a7e84fd0d515 Mon Sep 17 00:00:00 2001 From: Peter Zijlstra Date: Mon, 16 Nov 2009 12:45:14 +0100 Subject: [PATCH] --- yaml --- r: 169625 b: refs/heads/master c: 559fdc3c1b624edb1933a875022fe7e27934d11c h: refs/heads/master i: 169623: 4081ef3a953c6011732447797daea2aac4621086 v: v3 --- [refs] | 2 +- trunk/include/linux/perf_event.h | 1 - trunk/kernel/perf_event.c | 21 +++++++++++---------- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/[refs] b/[refs] index a6e2e0d45029..7eae449faa73 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: 7255fe2a42c612f2b8fe4c347f0a5f0c97d85a46 +refs/heads/master: 559fdc3c1b624edb1933a875022fe7e27934d11c diff --git a/trunk/include/linux/perf_event.h b/trunk/include/linux/perf_event.h index df4e73e33774..7f87563c8485 100644 --- a/trunk/include/linux/perf_event.h +++ b/trunk/include/linux/perf_event.h @@ -714,7 +714,6 @@ struct perf_output_handle { int nmi; int sample; int locked; - unsigned long flags; }; #ifdef CONFIG_PERF_EVENTS diff --git a/trunk/kernel/perf_event.c b/trunk/kernel/perf_event.c index 6f4ed3b4cd73..3256e36ad251 100644 --- a/trunk/kernel/perf_event.c +++ b/trunk/kernel/perf_event.c @@ -2674,20 +2674,21 @@ static void perf_output_wakeup(struct perf_output_handle *handle) static void perf_output_lock(struct perf_output_handle *handle) { struct perf_mmap_data *data = handle->data; - int cpu; + int cur, cpu = get_cpu(); handle->locked = 0; - local_irq_save(handle->flags); - cpu = smp_processor_id(); - - if (in_nmi() && atomic_read(&data->lock) == cpu) - return; + for (;;) { + cur = atomic_cmpxchg(&data->lock, -1, cpu); + if (cur == -1) { + handle->locked = 1; + break; + } + if (cur == cpu) + break; - while (atomic_cmpxchg(&data->lock, -1, cpu) != -1) cpu_relax(); - - handle->locked = 1; + } } static void perf_output_unlock(struct perf_output_handle *handle) @@ -2733,7 +2734,7 @@ static void perf_output_unlock(struct perf_output_handle *handle) if (atomic_xchg(&data->wakeup, 0)) perf_output_wakeup(handle); out: - local_irq_restore(handle->flags); + put_cpu(); } void perf_output_copy(struct perf_output_handle *handle,