aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorRobert Richter <rric@kernel.org>2013-02-06 12:26:25 -0500
committerIngo Molnar <mingo@kernel.org>2013-02-06 13:45:23 -0500
commit4dd4c2ae555d8a91e8c5bf1cd56807a35764436a (patch)
treeb375aa65d3cbde5a628dea94e8d170892ed70a83 /arch
parent2c53c3dd0b6497484b29fd49d34ef98acbc14577 (diff)
perf/x86/amd: Generalize northbridge constraints code for family 15h
Generalize northbridge constraints code for family 10h so that later we can reuse the same code path with other AMD processor families that have the same northbridge event constraints. Signed-off-by: Robert Richter <rric@kernel.org> Signed-off-by: Jacob Shin <jacob.shin@amd.com> Cc: Paul Mackerras <paulus@samba.org> Cc: Arnaldo Carvalho de Melo <acme@ghostprotocols.net> Cc: Stephane Eranian <eranian@google.com> Cc: Jiri Olsa <jolsa@redhat.com> Cc: Peter Zijlstra <a.p.zijlstra@chello.nl> Link: http://lkml.kernel.org/r/1360171589-6381-3-git-send-email-jacob.shin@amd.com Signed-off-by: Ingo Molnar <mingo@kernel.org>
Diffstat (limited to 'arch')
-rw-r--r--arch/x86/kernel/cpu/perf_event_amd.c43
1 files changed, 25 insertions, 18 deletions
diff --git a/arch/x86/kernel/cpu/perf_event_amd.c b/arch/x86/kernel/cpu/perf_event_amd.c
index e7963c7af683..f8c9dfbd6613 100644
--- a/arch/x86/kernel/cpu/perf_event_amd.c
+++ b/arch/x86/kernel/cpu/perf_event_amd.c
@@ -188,20 +188,13 @@ static inline int amd_has_nb(struct cpu_hw_events *cpuc)
188 return nb && nb->nb_id != -1; 188 return nb && nb->nb_id != -1;
189} 189}
190 190
191static void amd_put_event_constraints(struct cpu_hw_events *cpuc, 191static void __amd_put_nb_event_constraints(struct cpu_hw_events *cpuc,
192 struct perf_event *event) 192 struct perf_event *event)
193{ 193{
194 struct hw_perf_event *hwc = &event->hw;
195 struct amd_nb *nb = cpuc->amd_nb; 194 struct amd_nb *nb = cpuc->amd_nb;
196 int i; 195 int i;
197 196
198 /* 197 /*
199 * only care about NB events
200 */
201 if (!(amd_has_nb(cpuc) && amd_is_nb_event(hwc)))
202 return;
203
204 /*
205 * need to scan whole list because event may not have 198 * need to scan whole list because event may not have
206 * been assigned during scheduling 199 * been assigned during scheduling
207 * 200 *
@@ -247,12 +240,13 @@ static void amd_put_event_constraints(struct cpu_hw_events *cpuc,
247 * 240 *
248 * Given that resources are allocated (cmpxchg), they must be 241 * Given that resources are allocated (cmpxchg), they must be
249 * eventually freed for others to use. This is accomplished by 242 * eventually freed for others to use. This is accomplished by
250 * calling amd_put_event_constraints(). 243 * calling __amd_put_nb_event_constraints()
251 * 244 *
252 * Non NB events are not impacted by this restriction. 245 * Non NB events are not impacted by this restriction.
253 */ 246 */
254static struct event_constraint * 247static struct event_constraint *
255amd_get_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event) 248__amd_get_nb_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event,
249 struct event_constraint *c)
256{ 250{
257 struct hw_perf_event *hwc = &event->hw; 251 struct hw_perf_event *hwc = &event->hw;
258 struct amd_nb *nb = cpuc->amd_nb; 252 struct amd_nb *nb = cpuc->amd_nb;
@@ -260,12 +254,6 @@ amd_get_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event)
260 int idx, new = -1; 254 int idx, new = -1;
261 255
262 /* 256 /*
263 * if not NB event or no NB, then no constraints
264 */
265 if (!(amd_has_nb(cpuc) && amd_is_nb_event(hwc)))
266 return &unconstrained;
267
268 /*
269 * detect if already present, if so reuse 257 * detect if already present, if so reuse
270 * 258 *
271 * cannot merge with actual allocation 259 * cannot merge with actual allocation
@@ -275,7 +263,7 @@ amd_get_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event)
275 * because of successive calls to x86_schedule_events() from 263 * because of successive calls to x86_schedule_events() from
276 * hw_perf_group_sched_in() without hw_perf_enable() 264 * hw_perf_group_sched_in() without hw_perf_enable()
277 */ 265 */
278 for (idx = 0; idx < x86_pmu.num_counters; idx++) { 266 for_each_set_bit(idx, c->idxmsk, x86_pmu.num_counters) {
279 if (new == -1 || hwc->idx == idx) 267 if (new == -1 || hwc->idx == idx)
280 /* assign free slot, prefer hwc->idx */ 268 /* assign free slot, prefer hwc->idx */
281 old = cmpxchg(nb->owners + idx, NULL, event); 269 old = cmpxchg(nb->owners + idx, NULL, event);
@@ -391,6 +379,25 @@ static void amd_pmu_cpu_dead(int cpu)
391 } 379 }
392} 380}
393 381
382static struct event_constraint *
383amd_get_event_constraints(struct cpu_hw_events *cpuc, struct perf_event *event)
384{
385 /*
386 * if not NB event or no NB, then no constraints
387 */
388 if (!(amd_has_nb(cpuc) && amd_is_nb_event(&event->hw)))
389 return &unconstrained;
390
391 return __amd_get_nb_event_constraints(cpuc, event, &unconstrained);
392}
393
394static void amd_put_event_constraints(struct cpu_hw_events *cpuc,
395 struct perf_event *event)
396{
397 if (amd_has_nb(cpuc) && amd_is_nb_event(&event->hw))
398 __amd_put_nb_event_constraints(cpuc, event);
399}
400
394PMU_FORMAT_ATTR(event, "config:0-7,32-35"); 401PMU_FORMAT_ATTR(event, "config:0-7,32-35");
395PMU_FORMAT_ATTR(umask, "config:8-15" ); 402PMU_FORMAT_ATTR(umask, "config:8-15" );
396PMU_FORMAT_ATTR(edge, "config:18" ); 403PMU_FORMAT_ATTR(edge, "config:18" );