diff options
author | Stephane Eranian <eranian@google.com> | 2013-01-24 10:10:27 -0500 |
---|---|---|
committer | Arnaldo Carvalho de Melo <acme@redhat.com> | 2013-04-01 11:15:04 -0400 |
commit | 9fac2cf316b070ae43d2ae2525e381ff2d1d68aa (patch) | |
tree | 526d974269e48f18be3d4e6191ea853d4ef800d9 | |
parent | 3a54aaa0a3ddb2cf2ec1b94a94024e9a8a8af962 (diff) |
perf/x86: Add flags to event constraints
This patch adds a flags field to each event constraint.
It can be used to store event specific features which can
then later be used by scheduling code or low-level x86 code.
The flags are propagated into event->hw.flags during the
get_event_constraint() call. They are cleared during the
put_event_constraint() call.
This mechanism is going to be used by the PEBS-LL patches.
It avoids defining yet another table to hold event specific
information.
Signed-off-by: Stephane Eranian <eranian@google.com>
Cc: peterz@infradead.org
Cc: ak@linux.intel.com
Cc: jolsa@redhat.com
Cc: namhyung.kim@lge.com
Link: http://lkml.kernel.org/r/1359040242-8269-4-git-send-email-eranian@google.com
Signed-off-by: Ingo Molnar <mingo@kernel.org>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
-rw-r--r-- | arch/x86/kernel/cpu/perf_event.c | 2 | ||||
-rw-r--r-- | arch/x86/kernel/cpu/perf_event.h | 8 | ||||
-rw-r--r-- | arch/x86/kernel/cpu/perf_event_intel.c | 6 | ||||
-rw-r--r-- | arch/x86/kernel/cpu/perf_event_intel_ds.c | 4 | ||||
-rw-r--r-- | arch/x86/kernel/cpu/perf_event_intel_uncore.c | 2 | ||||
-rw-r--r-- | include/linux/perf_event.h | 1 |
6 files changed, 16 insertions, 7 deletions
diff --git a/arch/x86/kernel/cpu/perf_event.c b/arch/x86/kernel/cpu/perf_event.c index 6e8ab0427041..8ba51518f689 100644 --- a/arch/x86/kernel/cpu/perf_event.c +++ b/arch/x86/kernel/cpu/perf_event.c | |||
@@ -1489,7 +1489,7 @@ static int __init init_hw_perf_events(void) | |||
1489 | 1489 | ||
1490 | unconstrained = (struct event_constraint) | 1490 | unconstrained = (struct event_constraint) |
1491 | __EVENT_CONSTRAINT(0, (1ULL << x86_pmu.num_counters) - 1, | 1491 | __EVENT_CONSTRAINT(0, (1ULL << x86_pmu.num_counters) - 1, |
1492 | 0, x86_pmu.num_counters, 0); | 1492 | 0, x86_pmu.num_counters, 0, 0); |
1493 | 1493 | ||
1494 | x86_pmu.attr_rdpmc = 1; /* enable userspace RDPMC usage by default */ | 1494 | x86_pmu.attr_rdpmc = 1; /* enable userspace RDPMC usage by default */ |
1495 | x86_pmu_format_group.attrs = x86_pmu.format_attrs; | 1495 | x86_pmu_format_group.attrs = x86_pmu.format_attrs; |
diff --git a/arch/x86/kernel/cpu/perf_event.h b/arch/x86/kernel/cpu/perf_event.h index b1518eed5f99..9686d38eb458 100644 --- a/arch/x86/kernel/cpu/perf_event.h +++ b/arch/x86/kernel/cpu/perf_event.h | |||
@@ -59,6 +59,7 @@ struct event_constraint { | |||
59 | u64 cmask; | 59 | u64 cmask; |
60 | int weight; | 60 | int weight; |
61 | int overlap; | 61 | int overlap; |
62 | int flags; | ||
62 | }; | 63 | }; |
63 | 64 | ||
64 | struct amd_nb { | 65 | struct amd_nb { |
@@ -170,16 +171,17 @@ struct cpu_hw_events { | |||
170 | void *kfree_on_online; | 171 | void *kfree_on_online; |
171 | }; | 172 | }; |
172 | 173 | ||
173 | #define __EVENT_CONSTRAINT(c, n, m, w, o) {\ | 174 | #define __EVENT_CONSTRAINT(c, n, m, w, o, f) {\ |
174 | { .idxmsk64 = (n) }, \ | 175 | { .idxmsk64 = (n) }, \ |
175 | .code = (c), \ | 176 | .code = (c), \ |
176 | .cmask = (m), \ | 177 | .cmask = (m), \ |
177 | .weight = (w), \ | 178 | .weight = (w), \ |
178 | .overlap = (o), \ | 179 | .overlap = (o), \ |
180 | .flags = f, \ | ||
179 | } | 181 | } |
180 | 182 | ||
181 | #define EVENT_CONSTRAINT(c, n, m) \ | 183 | #define EVENT_CONSTRAINT(c, n, m) \ |
182 | __EVENT_CONSTRAINT(c, n, m, HWEIGHT(n), 0) | 184 | __EVENT_CONSTRAINT(c, n, m, HWEIGHT(n), 0, 0) |
183 | 185 | ||
184 | /* | 186 | /* |
185 | * The overlap flag marks event constraints with overlapping counter | 187 | * The overlap flag marks event constraints with overlapping counter |
@@ -203,7 +205,7 @@ struct cpu_hw_events { | |||
203 | * and its counter masks must be kept at a minimum. | 205 | * and its counter masks must be kept at a minimum. |
204 | */ | 206 | */ |
205 | #define EVENT_CONSTRAINT_OVERLAP(c, n, m) \ | 207 | #define EVENT_CONSTRAINT_OVERLAP(c, n, m) \ |
206 | __EVENT_CONSTRAINT(c, n, m, HWEIGHT(n), 1) | 208 | __EVENT_CONSTRAINT(c, n, m, HWEIGHT(n), 1, 0) |
207 | 209 | ||
208 | /* | 210 | /* |
209 | * Constraint on the Event code. | 211 | * Constraint on the Event code. |
diff --git a/arch/x86/kernel/cpu/perf_event_intel.c b/arch/x86/kernel/cpu/perf_event_intel.c index dab7580c47ae..df3beaac3397 100644 --- a/arch/x86/kernel/cpu/perf_event_intel.c +++ b/arch/x86/kernel/cpu/perf_event_intel.c | |||
@@ -1392,8 +1392,11 @@ x86_get_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event) | |||
1392 | 1392 | ||
1393 | if (x86_pmu.event_constraints) { | 1393 | if (x86_pmu.event_constraints) { |
1394 | for_each_event_constraint(c, x86_pmu.event_constraints) { | 1394 | for_each_event_constraint(c, x86_pmu.event_constraints) { |
1395 | if ((event->hw.config & c->cmask) == c->code) | 1395 | if ((event->hw.config & c->cmask) == c->code) { |
1396 | /* hw.flags zeroed at initialization */ | ||
1397 | event->hw.flags |= c->flags; | ||
1396 | return c; | 1398 | return c; |
1399 | } | ||
1397 | } | 1400 | } |
1398 | } | 1401 | } |
1399 | 1402 | ||
@@ -1438,6 +1441,7 @@ intel_put_shared_regs_event_constraints(struct cpu_hw_events *cpuc, | |||
1438 | static void intel_put_event_constraints(struct cpu_hw_events *cpuc, | 1441 | static void intel_put_event_constraints(struct cpu_hw_events *cpuc, |
1439 | struct perf_event *event) | 1442 | struct perf_event *event) |
1440 | { | 1443 | { |
1444 | event->hw.flags = 0; | ||
1441 | intel_put_shared_regs_event_constraints(cpuc, event); | 1445 | intel_put_shared_regs_event_constraints(cpuc, event); |
1442 | } | 1446 | } |
1443 | 1447 | ||
diff --git a/arch/x86/kernel/cpu/perf_event_intel_ds.c b/arch/x86/kernel/cpu/perf_event_intel_ds.c index 826054a4f2ee..f30d85bcbda9 100644 --- a/arch/x86/kernel/cpu/perf_event_intel_ds.c +++ b/arch/x86/kernel/cpu/perf_event_intel_ds.c | |||
@@ -430,8 +430,10 @@ struct event_constraint *intel_pebs_constraints(struct perf_event *event) | |||
430 | 430 | ||
431 | if (x86_pmu.pebs_constraints) { | 431 | if (x86_pmu.pebs_constraints) { |
432 | for_each_event_constraint(c, x86_pmu.pebs_constraints) { | 432 | for_each_event_constraint(c, x86_pmu.pebs_constraints) { |
433 | if ((event->hw.config & c->cmask) == c->code) | 433 | if ((event->hw.config & c->cmask) == c->code) { |
434 | event->hw.flags |= c->flags; | ||
434 | return c; | 435 | return c; |
436 | } | ||
435 | } | 437 | } |
436 | } | 438 | } |
437 | 439 | ||
diff --git a/arch/x86/kernel/cpu/perf_event_intel_uncore.c b/arch/x86/kernel/cpu/perf_event_intel_uncore.c index b43200dbfe7e..75da9e18b128 100644 --- a/arch/x86/kernel/cpu/perf_event_intel_uncore.c +++ b/arch/x86/kernel/cpu/perf_event_intel_uncore.c | |||
@@ -2438,7 +2438,7 @@ static int __init uncore_type_init(struct intel_uncore_type *type) | |||
2438 | 2438 | ||
2439 | type->unconstrainted = (struct event_constraint) | 2439 | type->unconstrainted = (struct event_constraint) |
2440 | __EVENT_CONSTRAINT(0, (1ULL << type->num_counters) - 1, | 2440 | __EVENT_CONSTRAINT(0, (1ULL << type->num_counters) - 1, |
2441 | 0, type->num_counters, 0); | 2441 | 0, type->num_counters, 0, 0); |
2442 | 2442 | ||
2443 | for (i = 0; i < type->num_boxes; i++) { | 2443 | for (i = 0; i < type->num_boxes; i++) { |
2444 | pmus[i].func_id = -1; | 2444 | pmus[i].func_id = -1; |
diff --git a/include/linux/perf_event.h b/include/linux/perf_event.h index 1c592114c437..cd3bb2cd9494 100644 --- a/include/linux/perf_event.h +++ b/include/linux/perf_event.h | |||
@@ -127,6 +127,7 @@ struct hw_perf_event { | |||
127 | int event_base_rdpmc; | 127 | int event_base_rdpmc; |
128 | int idx; | 128 | int idx; |
129 | int last_cpu; | 129 | int last_cpu; |
130 | int flags; | ||
130 | 131 | ||
131 | struct hw_perf_event_extra extra_reg; | 132 | struct hw_perf_event_extra extra_reg; |
132 | struct hw_perf_event_extra branch_reg; | 133 | struct hw_perf_event_extra branch_reg; |