[PATCH v4 1/3] cpufreq: cppc: Add update_limits support for Highest Performance changes

From: Xueqin Luo

Date: Mon Jun 08 2026 - 06:22:12 EST


ACPI CPPC specification requires OSPM to re-evaluate the Highest
Performance register when Notify(0x85) is received for a processor
device.

Implement cppc_cpufreq_update_limits() to refresh the cached
highest_perf capability through cppc_get_highest_perf() and update
policy->cpuinfo.max_freq accordingly. Use refresh_frequency_limits()
to let the cpufreq core update policy->max via the standard
cpufreq_set_policy() path instead of setting it directly.

Re-evaluate policy->boost_supported when highest_perf changes, as
boost capability depends on highest_perf exceeding nominal_perf.

Signed-off-by: Xueqin Luo <luoxueqin@xxxxxxxxxx>
---
drivers/cpufreq/cppc_cpufreq.c | 39 ++++++++++++++++++++++++++++++++++
1 file changed, 39 insertions(+)

diff --git a/drivers/cpufreq/cppc_cpufreq.c b/drivers/cpufreq/cppc_cpufreq.c
index bf5175f7551c..56f13086ccee 100644
--- a/drivers/cpufreq/cppc_cpufreq.c
+++ b/drivers/cpufreq/cppc_cpufreq.c
@@ -843,6 +843,44 @@ static int cppc_cpufreq_set_boost(struct cpufreq_policy *policy, int state)
return 0;
}

+static void cppc_cpufreq_update_limits(struct cpufreq_policy *policy)
+{
+ struct cppc_cpudata *cpu_data = policy->driver_data;
+ u64 prev_highest_perf;
+ u64 highest_perf;
+ int ret;
+
+ guard(cpufreq_policy_write)(policy);
+
+ prev_highest_perf = cpu_data->perf_caps.highest_perf;
+
+ ret = cppc_get_highest_perf(policy->cpu, &highest_perf);
+ if (ret)
+ return;
+
+ if (highest_perf == prev_highest_perf)
+ return;
+
+ cpu_data->perf_caps.highest_perf = highest_perf;
+
+ /*
+ * Re-evaluate boost capability based on the updated Highest
+ * Performance. Boost is supported when highest_perf exceeds
+ * nominal_perf.
+ */
+ policy->boost_supported = highest_perf >
+ cpu_data->perf_caps.nominal_perf;
+
+ policy->cpuinfo.max_freq = cppc_perf_to_khz(&cpu_data->perf_caps,
+ policy->boost_enabled ?
+ highest_perf : cpu_data->perf_caps.nominal_perf);
+
+ refresh_frequency_limits(policy);
+
+ pr_debug("CPU%d: highest_perf updated %llu -> %llu\n",
+ policy->cpu, prev_highest_perf, highest_perf);
+}
+
static ssize_t show_freqdomain_cpus(struct cpufreq_policy *policy, char *buf)
{
struct cppc_cpudata *cpu_data = policy->driver_data;
@@ -1036,6 +1074,7 @@ static struct cpufreq_driver cppc_cpufreq_driver = {
.init = cppc_cpufreq_cpu_init,
.exit = cppc_cpufreq_cpu_exit,
.set_boost = cppc_cpufreq_set_boost,
+ .update_limits = cppc_cpufreq_update_limits,
.attr = cppc_cpufreq_attr,
.name = "cppc_cpufreq",
};
--
2.43.0