Revert "cpufreq: schedutil: Fix for CR 2040904"

This reverts commit b8b6f565c0.

CAF's hispeed boost and predicted load features aren't any good. Remove
them entirely to prevent userspace from trying to enable them
(specifically pl) and to reduce useless overhead in schedutil, since it
runs *very* often.

Change-Id: I0446b49a59e5dce8e1b7712bdb654c9a5e6ff0ed
Signed-off-by: Danny Lin <danny@kdrag0n.dev>
Signed-off-by: Alexander Winkowski <dereference23@outlook.com>
fourteen
Danny Lin 5 years ago committed by Jenna
parent 3577495855
commit 9845d42b1f
  1. 257
      kernel/sched/cpufreq_schedutil.c

@ -25,9 +25,6 @@ struct sugov_tunables {
struct gov_attr_set attr_set;
unsigned int up_rate_limit_us;
unsigned int down_rate_limit_us;
unsigned int hispeed_load;
unsigned int hispeed_freq;
bool pl;
};
struct sugov_policy {
@ -42,14 +39,8 @@ struct sugov_policy {
s64 up_rate_delay_ns;
s64 down_rate_delay_ns;
s64 freq_update_delay_ns;
u64 last_ws;
u64 curr_cycles;
u64 last_cyc_update_time;
unsigned long avg_cap;
unsigned int next_freq;
unsigned int cached_raw_freq;
unsigned long hispeed_util;
unsigned long max;
/* The next fields are only needed if fast switch cannot be used. */
struct irq_work irq_work;
@ -161,71 +152,6 @@ static inline bool use_pelt(void)
#endif
}
static inline bool conservative_pl(void)
{
#ifdef CONFIG_SCHED_WALT
return sysctl_sched_conservative_pl;
#else
return false;
#endif
}
static unsigned long freq_to_util(struct sugov_policy *sg_policy,
unsigned int freq)
{
return mult_frac(sg_policy->max, freq,
sg_policy->policy->cpuinfo.max_freq);
}
#define KHZ 1000
static void sugov_track_cycles(struct sugov_policy *sg_policy,
unsigned int prev_freq,
u64 upto)
{
u64 delta_ns, cycles;
u64 next_ws = sg_policy->last_ws + sched_ravg_window;
if (unlikely(!sysctl_sched_use_walt_cpu_util))
return;
upto = min(upto, next_ws);
/* Track cycles in current window */
delta_ns = upto - sg_policy->last_cyc_update_time;
delta_ns *= prev_freq;
do_div(delta_ns, (NSEC_PER_SEC / KHZ));
cycles = delta_ns;
sg_policy->curr_cycles += cycles;
sg_policy->last_cyc_update_time = upto;
}
static void sugov_calc_avg_cap(struct sugov_policy *sg_policy, u64 curr_ws,
unsigned int prev_freq)
{
u64 last_ws = sg_policy->last_ws;
unsigned int avg_freq;
if (unlikely(!sysctl_sched_use_walt_cpu_util))
return;
BUG_ON(curr_ws < last_ws);
if (curr_ws <= last_ws)
return;
/* If we skipped some windows */
if (curr_ws > (last_ws + sched_ravg_window)) {
avg_freq = prev_freq;
/* Reset tracking history */
sg_policy->last_cyc_update_time = curr_ws;
} else {
sugov_track_cycles(sg_policy, prev_freq, curr_ws);
avg_freq = sg_policy->curr_cycles;
avg_freq /= sched_ravg_window / (NSEC_PER_SEC / KHZ);
}
sg_policy->avg_cap = freq_to_util(sg_policy, avg_freq);
sg_policy->curr_cycles = 0;
sg_policy->last_ws = curr_ws;
}
static void sugov_update_commit(struct sugov_policy *sg_policy, u64 time,
unsigned int next_freq)
{
@ -242,7 +168,6 @@ static void sugov_update_commit(struct sugov_policy *sg_policy, u64 time,
sg_policy->last_freq_update_time = time;
if (policy->fast_switch_enabled) {
sugov_track_cycles(sg_policy, sg_policy->policy->cur, time);
next_freq = cpufreq_driver_fast_switch(policy, next_freq);
if (!next_freq)
return;
@ -258,7 +183,6 @@ static void sugov_update_commit(struct sugov_policy *sg_policy, u64 time,
}
}
#define TARGET_LOAD 80
/**
* get_next_freq - Compute a new frequency for a given cpufreq policy.
* @sg_policy: schedutil policy object to compute the new frequency for.
@ -378,49 +302,17 @@ static bool sugov_cpu_is_busy(struct sugov_cpu *sg_cpu)
static inline bool sugov_cpu_is_busy(struct sugov_cpu *sg_cpu) { return false; }
#endif /* CONFIG_NO_HZ_COMMON */
#define NL_RATIO 75
#define DEFAULT_HISPEED_LOAD 90
static void sugov_walt_adjust(struct sugov_cpu *sg_cpu, unsigned long *util,
unsigned long *max)
{
struct sugov_policy *sg_policy = sg_cpu->sg_policy;
bool is_migration = sg_cpu->flags & SCHED_CPUFREQ_INTERCLUSTER_MIG;
unsigned long nl = sg_cpu->walt_load.nl;
unsigned long cpu_util = sg_cpu->util;
bool is_hiload;
unsigned long pl = sg_cpu->walt_load.pl;
if (unlikely(!sysctl_sched_use_walt_cpu_util))
return;
is_hiload = (cpu_util >= mult_frac(sg_policy->avg_cap,
sg_policy->tunables->hispeed_load,
100));
if (is_hiload && !is_migration)
*util = max(*util, sg_policy->hispeed_util);
if (is_hiload && nl >= mult_frac(cpu_util, NL_RATIO, 100))
*util = *max;
if (sg_policy->tunables->pl) {
if (conservative_pl())
pl = mult_frac(pl, TARGET_LOAD, 100);
*util = max(*util, pl);
}
}
static void sugov_update_single(struct update_util_data *hook, u64 time,
unsigned int flags)
{
struct sugov_cpu *sg_cpu = container_of(hook, struct sugov_cpu, update_util);
struct sugov_policy *sg_policy = sg_cpu->sg_policy;
struct cpufreq_policy *policy = sg_policy->policy;
unsigned long util, max, hs_util;
unsigned long util, max;
unsigned int next_f;
bool busy;
if (!sg_policy->tunables->pl && flags & SCHED_CPUFREQ_PL)
if (flags & SCHED_CPUFREQ_PL)
return;
flags &= ~SCHED_CPUFREQ_RT_DL;
@ -432,32 +324,12 @@ static void sugov_update_single(struct update_util_data *hook, u64 time,
busy = use_pelt() && sugov_cpu_is_busy(sg_cpu);
raw_spin_lock(&sg_policy->update_lock);
if (flags & SCHED_CPUFREQ_RT_DL) {
next_f = policy->cpuinfo.max_freq;
} else {
sugov_get_util(&util, &max, sg_cpu->cpu);
if (sg_policy->max != max) {
sg_policy->max = max;
hs_util = freq_to_util(sg_policy,
sg_policy->tunables->hispeed_freq);
hs_util = mult_frac(hs_util, TARGET_LOAD, 100);
sg_policy->hispeed_util = hs_util;
}
sg_cpu->util = util;
sg_cpu->max = max;
sg_cpu->flags = flags;
sugov_calc_avg_cap(sg_policy, sg_cpu->walt_load.ws,
sg_policy->policy->cur);
trace_sugov_util_update(sg_cpu->cpu, sg_cpu->util,
sg_policy->avg_cap, max, sg_cpu->walt_load.nl,
sg_cpu->walt_load.pl, flags);
sugov_iowait_boost(sg_cpu, &util, &max);
sugov_walt_adjust(sg_cpu, &util, &max);
next_f = get_next_freq(sg_policy, util, max);
/*
* Do not reduce the frequency if the CPU has not been idle
@ -472,7 +344,6 @@ static void sugov_update_single(struct update_util_data *hook, u64 time,
}
}
sugov_update_commit(sg_policy, time, next_f);
raw_spin_unlock(&sg_policy->update_lock);
}
static unsigned int sugov_next_freq_shared(struct sugov_cpu *sg_cpu, u64 time)
@ -504,22 +375,14 @@ static unsigned int sugov_next_freq_shared(struct sugov_cpu *sg_cpu, u64 time)
if (j_sg_cpu->flags & SCHED_CPUFREQ_RT_DL)
return policy->cpuinfo.max_freq;
/*
* If the util value for all CPUs in a policy is 0, just using >
* will result in a max value of 1. WALT stats can later update
* the aggregated util value, causing get_next_freq() to compute
* freq = max_freq * 1.25 * (util / max) for nonzero util,
* leading to spurious jumps to fmax.
*/
j_util = j_sg_cpu->util;
j_max = j_sg_cpu->max;
if (j_util * max >= j_max * util) {
if (j_util * max > j_max * util) {
util = j_util;
max = j_max;
}
sugov_iowait_boost(j_sg_cpu, &util, &max);
sugov_walt_adjust(j_sg_cpu, &util, &max);
}
return get_next_freq(sg_policy, util, max);
@ -530,10 +393,10 @@ static void sugov_update_shared(struct update_util_data *hook, u64 time,
{
struct sugov_cpu *sg_cpu = container_of(hook, struct sugov_cpu, update_util);
struct sugov_policy *sg_policy = sg_cpu->sg_policy;
unsigned long util, max, hs_util;
unsigned long util, max;
unsigned int next_f;
if (!sg_policy->tunables->pl && flags & SCHED_CPUFREQ_PL)
if (flags & SCHED_CPUFREQ_PL)
return;
sugov_get_util(&util, &max, sg_cpu->cpu);
@ -542,14 +405,6 @@ static void sugov_update_shared(struct update_util_data *hook, u64 time,
raw_spin_lock(&sg_policy->update_lock);
if (sg_policy->max != max) {
sg_policy->max = max;
hs_util = freq_to_util(sg_policy,
sg_policy->tunables->hispeed_freq);
hs_util = mult_frac(hs_util, TARGET_LOAD, 100);
sg_policy->hispeed_util = hs_util;
}
sg_cpu->util = util;
sg_cpu->max = max;
sg_cpu->flags = flags;
@ -557,13 +412,6 @@ static void sugov_update_shared(struct update_util_data *hook, u64 time,
sugov_set_iowait_boost(sg_cpu, time, flags);
sg_cpu->last_update = time;
sugov_calc_avg_cap(sg_policy, sg_cpu->walt_load.ws,
sg_policy->policy->cur);
trace_sugov_util_update(sg_cpu->cpu, sg_cpu->util, sg_policy->avg_cap,
max, sg_cpu->walt_load.nl,
sg_cpu->walt_load.pl, flags);
if (sugov_should_update_freq(sg_policy, time) &&
!(flags & SCHED_CPUFREQ_CONTINUE)) {
if (flags & SCHED_CPUFREQ_RT_DL)
@ -580,13 +428,8 @@ static void sugov_update_shared(struct update_util_data *hook, u64 time,
static void sugov_work(struct kthread_work *work)
{
struct sugov_policy *sg_policy = container_of(work, struct sugov_policy, work);
unsigned long flags;
mutex_lock(&sg_policy->work_lock);
raw_spin_lock_irqsave(&sg_policy->update_lock, flags);
sugov_track_cycles(sg_policy, sg_policy->policy->cur,
sched_ktime_clock());
raw_spin_unlock_irqrestore(&sg_policy->update_lock, flags);
__cpufreq_driver_target(sg_policy->policy, sg_policy->next_freq,
CPUFREQ_RELATION_L);
mutex_unlock(&sg_policy->work_lock);
@ -691,88 +534,12 @@ static ssize_t down_rate_limit_us_store(struct gov_attr_set *attr_set,
return count;
}
static ssize_t hispeed_load_show(struct gov_attr_set *attr_set, char *buf)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
return scnprintf(buf, PAGE_SIZE, "%u\n", tunables->hispeed_load);
}
static ssize_t hispeed_load_store(struct gov_attr_set *attr_set,
const char *buf, size_t count)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
if (kstrtouint(buf, 10, &tunables->hispeed_load))
return -EINVAL;
tunables->hispeed_load = min(100U, tunables->hispeed_load);
return count;
}
static ssize_t hispeed_freq_show(struct gov_attr_set *attr_set, char *buf)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
return scnprintf(buf, PAGE_SIZE, "%u\n", tunables->hispeed_freq);
}
static ssize_t hispeed_freq_store(struct gov_attr_set *attr_set,
const char *buf, size_t count)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
unsigned int val;
struct sugov_policy *sg_policy;
unsigned long hs_util;
unsigned long flags;
if (kstrtouint(buf, 10, &val))
return -EINVAL;
tunables->hispeed_freq = val;
list_for_each_entry(sg_policy, &attr_set->policy_list, tunables_hook) {
raw_spin_lock_irqsave(&sg_policy->update_lock, flags);
hs_util = freq_to_util(sg_policy,
sg_policy->tunables->hispeed_freq);
hs_util = mult_frac(hs_util, TARGET_LOAD, 100);
sg_policy->hispeed_util = hs_util;
raw_spin_unlock_irqrestore(&sg_policy->update_lock, flags);
}
return count;
}
static ssize_t pl_show(struct gov_attr_set *attr_set, char *buf)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
return scnprintf(buf, PAGE_SIZE, "%u\n", tunables->pl);
}
static ssize_t pl_store(struct gov_attr_set *attr_set, const char *buf,
size_t count)
{
struct sugov_tunables *tunables = to_sugov_tunables(attr_set);
if (kstrtobool(buf, &tunables->pl))
return -EINVAL;
return count;
}
static struct governor_attr up_rate_limit_us = __ATTR_RW(up_rate_limit_us);
static struct governor_attr down_rate_limit_us = __ATTR_RW(down_rate_limit_us);
static struct governor_attr hispeed_load = __ATTR_RW(hispeed_load);
static struct governor_attr hispeed_freq = __ATTR_RW(hispeed_freq);
static struct governor_attr pl = __ATTR_RW(pl);
static struct attribute *sugov_attributes[] = {
&up_rate_limit_us.attr,
&down_rate_limit_us.attr,
&hispeed_load.attr,
&hispeed_freq.attr,
&pl.attr,
NULL
};
@ -887,9 +654,6 @@ static void sugov_tunables_save(struct cpufreq_policy *policy,
per_cpu(cached_tunables, cpu) = cached;
}
cached->pl = tunables->pl;
cached->hispeed_load = tunables->hispeed_load;
cached->hispeed_freq = tunables->hispeed_freq;
cached->up_rate_limit_us = tunables->up_rate_limit_us;
cached->down_rate_limit_us = tunables->down_rate_limit_us;
}
@ -911,9 +675,6 @@ static void sugov_tunables_restore(struct cpufreq_policy *policy)
if (!cached)
return;
tunables->pl = cached->pl;
tunables->hispeed_load = cached->hispeed_load;
tunables->hispeed_freq = cached->hispeed_freq;
tunables->up_rate_limit_us = cached->up_rate_limit_us;
tunables->down_rate_limit_us = cached->down_rate_limit_us;
update_min_rate_limit_ns(sg_policy);
@ -965,8 +726,6 @@ static int sugov_init(struct cpufreq_policy *policy)
cpufreq_policy_transition_delay_us(policy);
tunables->down_rate_limit_us =
cpufreq_policy_transition_delay_us(policy);
tunables->hispeed_load = DEFAULT_HISPEED_LOAD;
tunables->hispeed_freq = 0;
policy->governor_data = sg_policy;
sg_policy->tunables = tunables;
@ -1086,16 +845,10 @@ static void sugov_limits(struct cpufreq_policy *policy)
if (!policy->fast_switch_enabled) {
mutex_lock(&sg_policy->work_lock);
raw_spin_lock_irqsave(&sg_policy->update_lock, flags);
sugov_track_cycles(sg_policy, sg_policy->policy->cur,
sched_ktime_clock());
raw_spin_unlock_irqrestore(&sg_policy->update_lock, flags);
cpufreq_policy_apply_limits(policy);
mutex_unlock(&sg_policy->work_lock);
} else {
raw_spin_lock_irqsave(&sg_policy->update_lock, flags);
sugov_track_cycles(sg_policy, sg_policy->policy->cur,
ktime_get_ns());
ret = cpufreq_policy_apply_limits_fast(policy);
if (ret && policy->cur != ret) {
policy->cur = ret;

Loading…
Cancel
Save