summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJunjie Wu <junjiew@codeaurora.org>2015-04-30 12:57:20 -0700
committerDavid Keitel <dkeitel@codeaurora.org>2016-03-23 20:03:17 -0700
commit9a35bf0f82cca3864bc685910f3bcefd3318ece1 (patch)
tree9253a13349fbbf5790d3434a69d6d8b5654c329b
parent3af8f8a21906ee9a942e7e26f953519df46232ed (diff)
cpufreq: interactive: Skip delay in frequency changes due to migration
The above hispeed delay and min sample time delays are used to distinguish between sporadic load changes versus steady state load changes. The governor tried to make sure the frequency changes only when the load change is a steady state load change. However, when the load change is for predictable reasons like migration, the delays only negatively affect performance and power. Once a significant load is migrated into a CPU, it's fairly reasonable to assume it's going to continue contributing that additional load. Similarly once a significant load is migrated away from a CPU, it's fairly reasonable to assume the load will be gone forever. Future migrations can bring back a load or take it away, but the notifications that come along with it will allow us to quickly correct for it. For this reason, when the load change is due to a notification, do not delay frequency changes. Change-Id: I19ad294b599e30654fbbeb0c56e8b50b0e19198f [junjiew@codeaurora.org: Resolved merge conflicts.] Signed-off-by: Junjie Wu <junjiew@codeaurora.org>
-rw-r--r--drivers/cpufreq/cpufreq_interactive.c13
1 files changed, 9 insertions, 4 deletions
diff --git a/drivers/cpufreq/cpufreq_interactive.c b/drivers/cpufreq/cpufreq_interactive.c
index 155f5bd9b4f7..229843ed8799 100644
--- a/drivers/cpufreq/cpufreq_interactive.c
+++ b/drivers/cpufreq/cpufreq_interactive.c
@@ -412,7 +412,7 @@ static u64 update_load(int cpu)
}
#define MAX_LOCAL_LOAD 100
-static void cpufreq_interactive_timer(unsigned long data)
+static void __cpufreq_interactive_timer(unsigned long data, bool is_notif)
{
u64 now;
unsigned int delta_time;
@@ -518,7 +518,7 @@ static void cpufreq_interactive_timer(unsigned long data)
new_freq = pcpu->freq_table[index].frequency;
- if (pcpu->target_freq >= pcpu->policy->max
+ if (!is_notif && pcpu->target_freq >= pcpu->policy->max
&& new_freq < pcpu->target_freq
&& now - pcpu->max_freq_hyst_start_time <
tunables->max_freq_hysteresis) {
@@ -533,7 +533,7 @@ static void cpufreq_interactive_timer(unsigned long data)
* floor frequency for the minimum sample time since last validated.
*/
max_fvtime = max(pcpu->pol_floor_val_time, pcpu->loc_floor_val_time);
- if (new_freq < pcpu->floor_freq &&
+ if (!is_notif && new_freq < pcpu->floor_freq &&
pcpu->target_freq >= pcpu->policy->cur) {
if (now - max_fvtime < tunables->min_sample_time) {
trace_cpufreq_interactive_notyet(
@@ -587,6 +587,11 @@ exit:
return;
}
+static void cpufreq_interactive_timer(unsigned long data)
+{
+ __cpufreq_interactive_timer(data, false);
+}
+
static void cpufreq_interactive_idle_end(void)
{
struct cpufreq_interactive_cpuinfo *pcpu =
@@ -749,7 +754,7 @@ static int load_change_callback(struct notifier_block *nb, unsigned long val,
trace_cpufreq_interactive_load_change(cpu);
del_timer(&pcpu->cpu_timer);
del_timer(&pcpu->cpu_slack_timer);
- cpufreq_interactive_timer(cpu);
+ __cpufreq_interactive_timer(cpu, true);
up_read(&pcpu->enable_sem);
return 0;