Hi,
On 06/27/2016 06:29 AM, Viresh Kumar wrote:
cpufreq drivers aren't required to provide a sorted frequency table today, and even the ones which provide a sorted table aren't handled efficiently by cpufreq core.
This patch adds infrastructure to verify if the freq-table provided by the drivers is sorted or not, and use efficient helpers if they are sorted.
<snip>
@@ -610,6 +617,227 @@ int cpufreq_boost_trigger_state(int state); int cpufreq_boost_enabled(void); int cpufreq_enable_boost_support(void); bool policy_has_boost_freq(struct cpufreq_policy *policy);
+/* Find lowest freq at or above target in a table in ascending order */ +static inline int cpufreq_table_find_index_al(struct cpufreq_policy *policy,
unsigned int target_freq)+{
- struct cpufreq_frequency_table *table = policy->freq_table;
- unsigned int freq;
- int i, best = -1;
- for (i = 0; table[i].frequency != CPUFREQ_TABLE_END; i++) {
freq = table[i].frequency;if (freq >= target_freq)return i;best = i;- }
- return best;
+}
+/* Find lowest freq at or above target in a table in descending order */ +static inline int cpufreq_table_find_index_dl(struct cpufreq_policy *policy,
unsigned int target_freq)+{
- struct cpufreq_frequency_table *table = policy->freq_table;
- unsigned int freq;
- int i, best = -1;
- for (i = 0; table[i].frequency != CPUFREQ_TABLE_END; i++) {
freq = table[i].frequency;if (freq == target_freq)return i;if (freq > target_freq) {best = i;continue;}/* No freq found below target_freq */
"below" should be "above"
+/* Find closest freq to target in a table in ascending order */ +static inline int cpufreq_table_find_index_ac(struct cpufreq_policy *policy,
unsigned int target_freq)+{
- struct cpufreq_frequency_table *table = policy->freq_table;
- unsigned int freq;
- int i, best = -1;
- for (i = 0; table[i].frequency != CPUFREQ_TABLE_END; i++) {
freq = table[i].frequency;if (freq == target_freq)return i;if (freq < target_freq) {best = i;continue;}/* No freq found below target_freq */if (best == -1)return i;/* Choose the closest freq */if (target_freq - table[best].frequency > freq - target_freq)return i;return best;- }
- return best;
+}
+/* Find closest freq to target in a table in descending order */ +static inline int cpufreq_table_find_index_dc(struct cpufreq_policy *policy,
unsigned int target_freq)+{
- struct cpufreq_frequency_table *table = policy->freq_table;
- unsigned int freq;
- int i, best = -1;
- for (i = 0; table[i].frequency != CPUFREQ_TABLE_END; i++) {
freq = table[i].frequency;if (freq == target_freq)return i;if (freq > target_freq) {best = i;continue;}/* No freq found below target_freq */
"below" should be "above"
if (best == -1)return i;/* Choose the closest freq */if (target_freq - table[best].frequency > freq - target_freq)
Here, table[best].frequency > target_freq, and freq < and target_freq, so you should reverse the sign of both sides of the inequation:
if (table[best].frequency - target_freq > target_freq - freq)
return i;return best;- }
- return best;
+}
Regards, Francesco