aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/oprofile/op_model_v7.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/oprofile/op_model_v7.c')
-rw-r--r--arch/arm/oprofile/op_model_v7.c38
1 files changed, 21 insertions, 17 deletions
diff --git a/arch/arm/oprofile/op_model_v7.c b/arch/arm/oprofile/op_model_v7.c
index f20295f14adb..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"
@@ -191,12 +194,8 @@ int armv7_setup_pmnc(void)
191 return -EBUSY; 194 return -EBUSY;
192 } 195 }
193 196
194 /* 197 /* Initialize & Reset PMNC: C bit and P bit */
195 * Initialize & Reset PMNC: C bit, D bit and P bit. 198 armv7_pmnc_write(PMNC_P | PMNC_C);
196 * Note: Using a slower count for CCNT (D bit: divide by 64) results
197 * in a more stable system
198 */
199 armv7_pmnc_write(PMNC_P | PMNC_C | PMNC_D);
200 199
201 200
202 for (cnt = CCNT; cnt < CNTMAX; cnt++) { 201 for (cnt = CCNT; cnt < CNTMAX; cnt++) {
@@ -299,7 +298,7 @@ static irqreturn_t armv7_pmnc_interrupt(int irq, void *arg)
299 return IRQ_HANDLED; 298 return IRQ_HANDLED;
300} 299}
301 300
302int armv7_request_interrupts(int *irqs, int nr) 301int armv7_request_interrupts(const int *irqs, int nr)
303{ 302{
304 unsigned int i; 303 unsigned int i;
305 int ret = 0; 304 int ret = 0;
@@ -322,7 +321,7 @@ int armv7_request_interrupts(int *irqs, int nr)
322 return ret; 321 return ret;
323} 322}
324 323
325void armv7_release_interrupts(int *irqs, int nr) 324void armv7_release_interrupts(const int *irqs, int nr)
326{ 325{
327 unsigned int i; 326 unsigned int i;
328 327
@@ -366,12 +365,7 @@ static void armv7_pmnc_dump_regs(void)
366} 365}
367#endif 366#endif
368 367
369 368static const struct pmu_irqs *pmu_irqs;
370static int irqs[] = {
371#ifdef CONFIG_ARCH_OMAP3
372 INT_34XX_BENCH_MPU_EMUL,
373#endif
374};
375 369
376static void armv7_pmnc_stop(void) 370static void armv7_pmnc_stop(void)
377{ 371{
@@ -379,19 +373,29 @@ static void armv7_pmnc_stop(void)
379 armv7_pmnc_dump_regs(); 373 armv7_pmnc_dump_regs();
380#endif 374#endif
381 armv7_stop_pmnc(); 375 armv7_stop_pmnc();
382 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;
383} 379}
384 380
385static int armv7_pmnc_start(void) 381static int armv7_pmnc_start(void)
386{ 382{
387 int ret; 383 int ret;
388 384
385 pmu_irqs = reserve_pmu();
386 if (IS_ERR(pmu_irqs))
387 return PTR_ERR(pmu_irqs);
388
389#ifdef DEBUG 389#ifdef DEBUG
390 armv7_pmnc_dump_regs(); 390 armv7_pmnc_dump_regs();
391#endif 391#endif
392 ret = armv7_request_interrupts(irqs, ARRAY_SIZE(irqs)); 392 ret = armv7_request_interrupts(pmu_irqs->irqs, pmu_irqs->num_irqs);
393 if (ret >= 0) 393 if (ret >= 0) {
394 armv7_start_pmnc(); 394 armv7_start_pmnc();
395 } else {
396 release_pmu(pmu_irqs);
397 pmu_irqs = NULL;
398 }
395 399
396 return ret; 400 return ret;
397} 401}