diff options
author | Peter Zijlstra <a.p.zijlstra@chello.nl> | 2009-12-16 11:55:54 -0500 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2009-12-16 12:30:11 -0500 |
commit | f4c4176f21533e22bcc292030da72bcfa105f5b8 (patch) | |
tree | 9e4376f5ff4dc3fb0f333faca94f219570df9af8 /kernel | |
parent | 9b33827de63539c7c3314ddf890fb216e4acf3d8 (diff) |
perf events: Allow per-task-per-cpu counters
In order to allow for per-task-per-cpu counters, useful for
scalability when profiling task hierarchies, we allow installing
events with event->cpu != -1 in task contexts.
__perf_event_sched_in() already skips events where ->cpu
mis-matches the current cpu, fix up __perf_install_in_context()
and __perf_event_enable() to also respect this filter.
This does lead to vary hard to interpret enabled/running times
for such counters, but I don't see a simple solution for that.
Signed-off-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: fweisbec@gmail.com
Cc: Paul Mackerras <paulus@samba.org>
LKML-Reference: <20091216165904.831451147@chello.nl>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/perf_event.c | 11 |
1 files changed, 7 insertions, 4 deletions
diff --git a/kernel/perf_event.c b/kernel/perf_event.c index 0dd8e5d02c66..2e0aaa34fc7e 100644 --- a/kernel/perf_event.c +++ b/kernel/perf_event.c | |||
@@ -782,6 +782,9 @@ static void __perf_install_in_context(void *info) | |||
782 | 782 | ||
783 | add_event_to_ctx(event, ctx); | 783 | add_event_to_ctx(event, ctx); |
784 | 784 | ||
785 | if (event->cpu != -1 && event->cpu != smp_processor_id()) | ||
786 | goto unlock; | ||
787 | |||
785 | /* | 788 | /* |
786 | * Don't put the event on if it is disabled or if | 789 | * Don't put the event on if it is disabled or if |
787 | * it is in a group and the group isn't on. | 790 | * it is in a group and the group isn't on. |
@@ -925,6 +928,9 @@ static void __perf_event_enable(void *info) | |||
925 | goto unlock; | 928 | goto unlock; |
926 | __perf_event_mark_enabled(event, ctx); | 929 | __perf_event_mark_enabled(event, ctx); |
927 | 930 | ||
931 | if (event->cpu != -1 && event->cpu != smp_processor_id()) | ||
932 | goto unlock; | ||
933 | |||
928 | /* | 934 | /* |
929 | * If the event is in a group and isn't the group leader, | 935 | * If the event is in a group and isn't the group leader, |
930 | * then don't put it on unless the group is on. | 936 | * then don't put it on unless the group is on. |
@@ -1595,10 +1601,7 @@ static struct perf_event_context *find_get_context(pid_t pid, int cpu) | |||
1595 | unsigned long flags; | 1601 | unsigned long flags; |
1596 | int err; | 1602 | int err; |
1597 | 1603 | ||
1598 | /* | 1604 | if (pid == -1 && cpu != -1) { |
1599 | * If cpu is not a wildcard then this is a percpu event: | ||
1600 | */ | ||
1601 | if (cpu != -1) { | ||
1602 | /* Must be root to operate on a CPU event: */ | 1605 | /* Must be root to operate on a CPU event: */ |
1603 | if (perf_paranoid_cpu() && !capable(CAP_SYS_ADMIN)) | 1606 | if (perf_paranoid_cpu() && !capable(CAP_SYS_ADMIN)) |
1604 | return ERR_PTR(-EACCES); | 1607 | return ERR_PTR(-EACCES); |