Perf: Restore correct CPU's PMU counters after power collpase
Since the L1CC PMU's are per CPU, the variable to detect if a CPU came out of powercollapse also needs to be a per CPU variable. This ensures that we reset and restore the correct CPU's PMU counters. Change-Id: I02273df2eff9f6d88d68f46a7752c107b290a8ef Signed-off-by: Ashwin Chaugule <ashwinc@codeaurora.org>
This commit is contained in:
committed by
Iliyan Malchev
parent
36fdfc2a9a
commit
2e62e8bde4
@@ -113,7 +113,6 @@ struct arm_pmu {
|
||||
struct mutex reserve_mutex;
|
||||
u64 max_period;
|
||||
struct platform_device *plat_device;
|
||||
u32 from_idle;
|
||||
irqreturn_t (*handle_irq)(int irq_num, void *dev);
|
||||
int (*request_pmu_irq)(int irq, irq_handler_t *irq_h);
|
||||
void (*free_pmu_irq)(int irq);
|
||||
|
||||
@@ -41,6 +41,7 @@
|
||||
*/
|
||||
#define ARMPMU_MAX_HWEVENTS 32
|
||||
|
||||
static DEFINE_PER_CPU(u32, from_idle);
|
||||
static DEFINE_PER_CPU(struct perf_event * [ARMPMU_MAX_HWEVENTS], hw_events);
|
||||
static DEFINE_PER_CPU(unsigned long [BITS_TO_LONGS(ARMPMU_MAX_HWEVENTS)], used_mask);
|
||||
static DEFINE_PER_CPU(struct pmu_hw_events, cpu_hw_events);
|
||||
@@ -602,7 +603,7 @@ static void armpmu_enable(struct pmu *pmu)
|
||||
int enabled = bitmap_weight(hw_events->used_mask, armpmu->num_events);
|
||||
int idx;
|
||||
|
||||
if (armpmu->from_idle) {
|
||||
if (__get_cpu_var(from_idle)) {
|
||||
for (idx = 0; idx <= cpu_pmu->num_events; ++idx) {
|
||||
struct perf_event *event = hw_events->events[idx];
|
||||
|
||||
@@ -613,9 +614,12 @@ static void armpmu_enable(struct pmu *pmu)
|
||||
}
|
||||
|
||||
/* Reset bit so we don't needlessly re-enable counters.*/
|
||||
armpmu->from_idle = 0;
|
||||
__get_cpu_var(from_idle) = 0;
|
||||
}
|
||||
|
||||
/* So we don't start the PMU before enabling counters after idle. */
|
||||
barrier();
|
||||
|
||||
if (enabled)
|
||||
armpmu->start();
|
||||
}
|
||||
@@ -731,7 +735,6 @@ static void __init cpu_pmu_init(struct arm_pmu *armpmu)
|
||||
* UNKNOWN at reset, the PMU must be explicitly reset to avoid reading
|
||||
* junk values out of them.
|
||||
*/
|
||||
|
||||
static int __cpuinit pmu_cpu_notify(struct notifier_block *b,
|
||||
unsigned long action, void *hcpu)
|
||||
{
|
||||
@@ -805,7 +808,7 @@ static int perf_cpu_pm_notifier(struct notifier_block *self, unsigned long cmd,
|
||||
* Flip this bit so armpmu_enable knows it needs
|
||||
* to re-enable active counters.
|
||||
*/
|
||||
cpu_pmu->from_idle = 1;
|
||||
__get_cpu_var(from_idle) = 1;
|
||||
cpu_pmu->reset(NULL);
|
||||
perf_pmu_enable(&cpu_pmu->pmu);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user