aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/oprofile/op_model_v7.c
diff options
context:
space:
mode:
authorJamie Iles <jamie.iles@picochip.com>2010-02-02 14:24:07 -0500
committerRussell King <rmk+kernel@arm.linux.org.uk>2010-02-12 12:23:43 -0500
commit1618fdd9602c689de2f820a88cb3e283a39c3d90 (patch)
treebe2cec6548d61dc83b7fc538fa929533f9cb9112 /arch/arm/oprofile/op_model_v7.c
parent0f4f0672ac950c96cffaf84a666d35e817d7c3ca (diff)
ARM: 5901/2: arm/oprofile: reserve the PMU when starting
Make sure that we have access to the performance counters and that they aren't being used by perf events or anything else. Cc: Will Deacon <will.deacon@arm.com> Cc: Jean Pihet <jpihet@mvista.com> Signed-off-by: Jamie Iles <jamie.iles@picochip.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'arch/arm/oprofile/op_model_v7.c')
-rw-r--r--arch/arm/oprofile/op_model_v7.c30
1 files changed, 19 insertions, 11 deletions
diff --git a/arch/arm/oprofile/op_model_v7.c b/arch/arm/oprofile/op_model_v7.c
index 2088a6c0cc0e..8642d0891ae1 100644
--- a/arch/arm/oprofile/op_model_v7.c
+++ b/arch/arm/oprofile/op_model_v7.c
@@ -11,11 +11,14 @@
11 */ 11 */
12#include <linux/types.h> 12#include <linux/types.h>
13#include <linux/errno.h> 13#include <linux/errno.h>
14#include <linux/err.h>
14#include <linux/oprofile.h> 15#include <linux/oprofile.h>
15#include <linux/interrupt.h> 16#include <linux/interrupt.h>
16#include <linux/irq.h> 17#include <linux/irq.h>
17#include <linux/smp.h> 18#include <linux/smp.h>
18 19
20#include <asm/pmu.h>
21
19#include "op_counter.h" 22#include "op_counter.h"
20#include "op_arm_model.h" 23#include "op_arm_model.h"
21#include "op_model_v7.h" 24#include "op_model_v7.h"
@@ -295,7 +298,7 @@ static irqreturn_t armv7_pmnc_interrupt(int irq, void *arg)
295 return IRQ_HANDLED; 298 return IRQ_HANDLED;
296} 299}
297 300
298int armv7_request_interrupts(int *irqs, int nr) 301int armv7_request_interrupts(const int *irqs, int nr)
299{ 302{
300 unsigned int i; 303 unsigned int i;
301 int ret = 0; 304 int ret = 0;
@@ -318,7 +321,7 @@ int armv7_request_interrupts(int *irqs, int nr)
318 return ret; 321 return ret;
319} 322}
320 323
321void armv7_release_interrupts(int *irqs, int nr) 324void armv7_release_interrupts(const int *irqs, int nr)
322{ 325{
323 unsigned int i; 326 unsigned int i;
324 327
@@ -362,12 +365,7 @@ static void armv7_pmnc_dump_regs(void)
362} 365}
363#endif 366#endif
364 367
365 368static const struct pmu_irqs *pmu_irqs;
366static int irqs[] = {
367#ifdef CONFIG_ARCH_OMAP3
368 INT_34XX_BENCH_MPU_EMUL,
369#endif
370};
371 369
372static void armv7_pmnc_stop(void) 370static void armv7_pmnc_stop(void)
373{ 371{
@@ -375,19 +373,29 @@ static void armv7_pmnc_stop(void)
375 armv7_pmnc_dump_regs(); 373 armv7_pmnc_dump_regs();
376#endif 374#endif
377 armv7_stop_pmnc(); 375 armv7_stop_pmnc();
378 armv7_release_interrupts(irqs, ARRAY_SIZE(irqs)); 376 armv7_release_interrupts(pmu_irqs->irqs, pmu_irqs->num_irqs);
377 release_pmu(pmu_irqs);
378 pmu_irqs = NULL;
379} 379}
380 380
381static int armv7_pmnc_start(void) 381static int armv7_pmnc_start(void)
382{ 382{
383 int ret; 383 int ret;
384 384
385 pmu_irqs = reserve_pmu();
386 if (IS_ERR(pmu_irqs))
387 return PTR_ERR(pmu_irqs);
388
385#ifdef DEBUG 389#ifdef DEBUG
386 armv7_pmnc_dump_regs(); 390 armv7_pmnc_dump_regs();
387#endif 391#endif
388 ret = armv7_request_interrupts(irqs, ARRAY_SIZE(irqs)); 392 ret = armv7_request_interrupts(pmu_irqs->irqs, pmu_irqs->num_irqs);
389 if (ret >= 0) 393 if (ret >= 0) {
390 armv7_start_pmnc(); 394 armv7_start_pmnc();
395 } else {
396 release_pmu(pmu_irqs);
397 pmu_irqs = NULL;
398 }
391 399
392 return ret; 400 return ret;
393} 401}