msm: cpufreq: Fix store_powersave_bias to account for sync' CPUs.
Current code assumes that all online CPUs runs their own timers to
collect CPU samples for demand based switching (dbs). But in case of
synchronous CPUs, ondemand governor registers only one timer at init
time because both CPUs are accounted in the same timer call. Hence
trying to restart/cancel dbs timers for all online CPUs is not legal
for these CPUs. This change fixes above function to restart/cancel
timers only once for group of synchronous CPUs.
Change-Id: I23f1697783a65f125679a07a076620e8fa5e62d5
Signed-off-by: Krishna Vanka <kvanka@codeaurora.org>
diff --git a/drivers/cpufreq/cpufreq_ondemand.c b/drivers/cpufreq/cpufreq_ondemand.c
index 6aed95c..2d33096 100644
--- a/drivers/cpufreq/cpufreq_ondemand.c
+++ b/drivers/cpufreq/cpufreq_ondemand.c
@@ -412,9 +412,12 @@
{
int input = 0;
int bypass = 0;
- int ret, cpu, reenable_timer;
+ int ret, cpu, reenable_timer, j;
struct cpu_dbs_info_s *dbs_info;
+ struct cpumask cpus_timer_done;
+ cpumask_clear(&cpus_timer_done);
+
ret = sscanf(buf, "%d", &input);
if (ret != 1)
@@ -447,10 +450,23 @@
continue;
dbs_info = &per_cpu(od_cpu_dbs_info, cpu);
+
+ for_each_cpu(j, &cpus_timer_done) {
+ if (!dbs_info->cur_policy) {
+ pr_err("Dbs policy is NULL\n");
+ goto skip_this_cpu;
+ }
+ if (cpumask_test_cpu(j, dbs_info->
+ cur_policy->cpus))
+ goto skip_this_cpu;
+ }
+
+ cpumask_set_cpu(cpu, &cpus_timer_done);
if (dbs_info->cur_policy) {
/* restart dbs timer */
dbs_timer_init(dbs_info);
}
+skip_this_cpu:
unlock_policy_rwsem_write(cpu);
}
}
@@ -463,6 +479,19 @@
continue;
dbs_info = &per_cpu(od_cpu_dbs_info, cpu);
+
+ for_each_cpu(j, &cpus_timer_done) {
+ if (!dbs_info->cur_policy) {
+ pr_err("Dbs policy is NULL\n");
+ goto skip_this_cpu_bypass;
+ }
+ if (cpumask_test_cpu(j, dbs_info->
+ cur_policy->cpus))
+ goto skip_this_cpu_bypass;
+ }
+
+ cpumask_set_cpu(cpu, &cpus_timer_done);
+
if (dbs_info->cur_policy) {
/* cpu using ondemand, cancel dbs timer */
mutex_lock(&dbs_info->timer_mutex);
@@ -475,6 +504,7 @@
mutex_unlock(&dbs_info->timer_mutex);
}
+skip_this_cpu_bypass:
unlock_policy_rwsem_write(cpu);
}
}