diff options
author | Rabin Vincent <rabin.vincent@stericsson.com> | 2011-02-07 22:54:36 -0500 |
---|---|---|
committer | Linus Walleij <linus.walleij@linaro.org> | 2011-02-17 07:55:45 -0500 |
commit | 0e25a5c98067286fc727cf142fc0dadf95790921 (patch) | |
tree | 2561e8b36242fbace98a2fe80047fb32aef6d150 | |
parent | 100b33c8bd8a3235fd0b7948338d6cbb3db3c63d (diff) |
ARM: perf_event: allow platform-specific interrupt handler
Allow a platform-specific IRQ handler to be specified via platform data.
This will be used to implement the single-irq workaround for the DB8500.
Signed-off-by: Rabin Vincent <rabin.vincent@stericsson.com>
Acked-by: Lee Jones <lee.jones@linaro.org>
Acked-by: Will Deacon <will.deacon@arm.com>
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
-rw-r--r-- | arch/arm/include/asm/pmu.h | 14 | ||||
-rw-r--r-- | arch/arm/kernel/perf_event.c | 17 |
2 files changed, 30 insertions, 1 deletions
diff --git a/arch/arm/include/asm/pmu.h b/arch/arm/include/asm/pmu.h index 8ccea012722c..7544ce6b481a 100644 --- a/arch/arm/include/asm/pmu.h +++ b/arch/arm/include/asm/pmu.h | |||
@@ -12,11 +12,25 @@ | |||
12 | #ifndef __ARM_PMU_H__ | 12 | #ifndef __ARM_PMU_H__ |
13 | #define __ARM_PMU_H__ | 13 | #define __ARM_PMU_H__ |
14 | 14 | ||
15 | #include <linux/interrupt.h> | ||
16 | |||
15 | enum arm_pmu_type { | 17 | enum arm_pmu_type { |
16 | ARM_PMU_DEVICE_CPU = 0, | 18 | ARM_PMU_DEVICE_CPU = 0, |
17 | ARM_NUM_PMU_DEVICES, | 19 | ARM_NUM_PMU_DEVICES, |
18 | }; | 20 | }; |
19 | 21 | ||
22 | /* | ||
23 | * struct arm_pmu_platdata - ARM PMU platform data | ||
24 | * | ||
25 | * @handle_irq: an optional handler which will be called from the interrupt and | ||
26 | * passed the address of the low level handler, and can be used to implement | ||
27 | * any platform specific handling before or after calling it. | ||
28 | */ | ||
29 | struct arm_pmu_platdata { | ||
30 | irqreturn_t (*handle_irq)(int irq, void *dev, | ||
31 | irq_handler_t pmu_handler); | ||
32 | }; | ||
33 | |||
20 | #ifdef CONFIG_CPU_HAS_PMU | 34 | #ifdef CONFIG_CPU_HAS_PMU |
21 | 35 | ||
22 | /** | 36 | /** |
diff --git a/arch/arm/kernel/perf_event.c b/arch/arm/kernel/perf_event.c index 5efa2647a2fb..323951191283 100644 --- a/arch/arm/kernel/perf_event.c +++ b/arch/arm/kernel/perf_event.c | |||
@@ -377,9 +377,18 @@ validate_group(struct perf_event *event) | |||
377 | return 0; | 377 | return 0; |
378 | } | 378 | } |
379 | 379 | ||
380 | static irqreturn_t armpmu_platform_irq(int irq, void *dev) | ||
381 | { | ||
382 | struct arm_pmu_platdata *plat = dev_get_platdata(&pmu_device->dev); | ||
383 | |||
384 | return plat->handle_irq(irq, dev, armpmu->handle_irq); | ||
385 | } | ||
386 | |||
380 | static int | 387 | static int |
381 | armpmu_reserve_hardware(void) | 388 | armpmu_reserve_hardware(void) |
382 | { | 389 | { |
390 | struct arm_pmu_platdata *plat; | ||
391 | irq_handler_t handle_irq; | ||
383 | int i, err = -ENODEV, irq; | 392 | int i, err = -ENODEV, irq; |
384 | 393 | ||
385 | pmu_device = reserve_pmu(ARM_PMU_DEVICE_CPU); | 394 | pmu_device = reserve_pmu(ARM_PMU_DEVICE_CPU); |
@@ -390,6 +399,12 @@ armpmu_reserve_hardware(void) | |||
390 | 399 | ||
391 | init_pmu(ARM_PMU_DEVICE_CPU); | 400 | init_pmu(ARM_PMU_DEVICE_CPU); |
392 | 401 | ||
402 | plat = dev_get_platdata(&pmu_device->dev); | ||
403 | if (plat && plat->handle_irq) | ||
404 | handle_irq = armpmu_platform_irq; | ||
405 | else | ||
406 | handle_irq = armpmu->handle_irq; | ||
407 | |||
393 | if (pmu_device->num_resources < 1) { | 408 | if (pmu_device->num_resources < 1) { |
394 | pr_err("no irqs for PMUs defined\n"); | 409 | pr_err("no irqs for PMUs defined\n"); |
395 | return -ENODEV; | 410 | return -ENODEV; |
@@ -400,7 +415,7 @@ armpmu_reserve_hardware(void) | |||
400 | if (irq < 0) | 415 | if (irq < 0) |
401 | continue; | 416 | continue; |
402 | 417 | ||
403 | err = request_irq(irq, armpmu->handle_irq, | 418 | err = request_irq(irq, handle_irq, |
404 | IRQF_DISABLED | IRQF_NOBALANCING, | 419 | IRQF_DISABLED | IRQF_NOBALANCING, |
405 | "armpmu", NULL); | 420 | "armpmu", NULL); |
406 | if (err) { | 421 | if (err) { |