Skip to content

Commit 593dc1c

Browse files
myungjooJeffrey Clark
authored andcommitted
CPUfreq ondemand: update sampling rate without waiting for next sampling
When a new sampling rate is shorter than the current one, (e.g., 1 sec --> 10 ms) regardless how short the new one is, the current ondemand mechanism wait for the previously set timer to be expired. For example, if the user has just expressed that the sampling rate should be 10 ms from now and the previous was 1000 ms, the new rate may become effective 999 ms later, which could be not acceptable for the user if the user has intended to speed up sampling because the system is expected to react to CPU load fluctuation quickly from __now__. In order to address this issue, we need to cancel the previously set timer (schedule_delayed_work) and reset the timer if resetting timer is expected to trigger the delayed_work ealier. Signed-off-by: MyungJoo Ham <[email protected]> Signed-off-by: Kyungmin Park <[email protected]>
1 parent d2279d5 commit 593dc1c

File tree

1 file changed

+57
-1
lines changed

1 file changed

+57
-1
lines changed

drivers/cpufreq/cpufreq_ondemand.c

Lines changed: 57 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -304,6 +304,62 @@ static ssize_t show_powersave_bias
304304
return snprintf(buf, PAGE_SIZE, "%d\n", dbs_tuners_ins.powersave_bias);
305305
}
306306

307+
/**
308+
* update_sampling_rate - update sampling rate effective immediately if needed.
309+
* @new_rate: new sampling rate
310+
*
311+
* If new rate is smaller than the old, simply updaing
312+
* dbs_tuners_int.sampling_rate might not be appropriate. For example,
313+
* if the original sampling_rate was 1 second and the requested new sampling
314+
* rate is 10 ms because the user needs immediate reaction from ondemand
315+
* governor, but not sure if higher frequency will be required or not,
316+
* then, the governor may change the sampling rate too late; up to 1 second
317+
* later. Thus, if we are reducing the sampling rate, we need to make the
318+
* new value effective immediately.
319+
*/
320+
static void update_sampling_rate(unsigned int new_rate)
321+
{
322+
int cpu;
323+
324+
dbs_tuners_ins.sampling_rate = new_rate
325+
= max(new_rate, min_sampling_rate);
326+
327+
for_each_online_cpu(cpu) {
328+
struct cpufreq_policy *policy;
329+
struct cpu_dbs_info_s *dbs_info;
330+
unsigned long next_sampling, appointed_at;
331+
332+
policy = cpufreq_cpu_get(cpu);
333+
if (!policy)
334+
continue;
335+
dbs_info = &per_cpu(od_cpu_dbs_info, policy->cpu);
336+
cpufreq_cpu_put(policy);
337+
338+
mutex_lock(&dbs_info->timer_mutex);
339+
340+
if (!delayed_work_pending(&dbs_info->work)) {
341+
mutex_unlock(&dbs_info->timer_mutex);
342+
continue;
343+
}
344+
345+
next_sampling = jiffies + usecs_to_jiffies(new_rate);
346+
appointed_at = dbs_info->work.timer.expires;
347+
348+
349+
if (time_before(next_sampling, appointed_at)) {
350+
351+
mutex_unlock(&dbs_info->timer_mutex);
352+
cancel_delayed_work_sync(&dbs_info->work);
353+
mutex_lock(&dbs_info->timer_mutex);
354+
355+
schedule_delayed_work_on(dbs_info->cpu, &dbs_info->work,
356+
usecs_to_jiffies(new_rate));
357+
358+
}
359+
mutex_unlock(&dbs_info->timer_mutex);
360+
}
361+
}
362+
307363
static ssize_t store_sampling_rate(struct kobject *a, struct attribute *b,
308364
const char *buf, size_t count)
309365
{
@@ -312,7 +368,7 @@ static ssize_t store_sampling_rate(struct kobject *a, struct attribute *b,
312368
ret = sscanf(buf, "%u", &input);
313369
if (ret != 1)
314370
return -EINVAL;
315-
dbs_tuners_ins.sampling_rate = max(input, min_sampling_rate);
371+
update_sampling_rate(input);
316372
return count;
317373
}
318374

0 commit comments

Comments
 (0)