Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'pm-6.13-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm

Pull power management fixes from Rafael Wysocki:
"These fix some amd-pstate driver issues:

- Detect preferred core support in amd-pstate before driver
registration to avoid initialization ordering issues (K Prateek
Nayak)

- Fix issues with with boost numerator handling in amd-pstate leading
to inconsistently programmed CPPC max performance values (Mario
Limonciello)"

* tag 'pm-6.13-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm:
cpufreq/amd-pstate: Use boost numerator for upper bound of frequencies
cpufreq/amd-pstate: Store the boost numerator as highest perf again
cpufreq/amd-pstate: Detect preferred core support before driver registration

+27 -27
+1 -3
Documentation/admin-guide/pm/amd-pstate.rst
··· 251 251 In some ASICs, the highest CPPC performance is not the one in the ``_CPC`` 252 252 table, so we need to expose it to sysfs. If boost is not active, but 253 253 still supported, this maximum frequency will be larger than the one in 254 - ``cpuinfo``. On systems that support preferred core, the driver will have 255 - different values for some cores than others and this will reflect the values 256 - advertised by the platform at bootup. 254 + ``cpuinfo``. 257 255 This attribute is read-only. 258 256 259 257 ``amd_pstate_lowest_nonlinear_freq``
+26 -24
drivers/cpufreq/amd-pstate.c
··· 374 374 375 375 static int msr_init_perf(struct amd_cpudata *cpudata) 376 376 { 377 - u64 cap1; 377 + u64 cap1, numerator; 378 378 379 379 int ret = rdmsrl_safe_on_cpu(cpudata->cpu, MSR_AMD_CPPC_CAP1, 380 380 &cap1); 381 381 if (ret) 382 382 return ret; 383 383 384 - WRITE_ONCE(cpudata->highest_perf, AMD_CPPC_HIGHEST_PERF(cap1)); 385 - WRITE_ONCE(cpudata->max_limit_perf, AMD_CPPC_HIGHEST_PERF(cap1)); 384 + ret = amd_get_boost_ratio_numerator(cpudata->cpu, &numerator); 385 + if (ret) 386 + return ret; 387 + 388 + WRITE_ONCE(cpudata->highest_perf, numerator); 389 + WRITE_ONCE(cpudata->max_limit_perf, numerator); 386 390 WRITE_ONCE(cpudata->nominal_perf, AMD_CPPC_NOMINAL_PERF(cap1)); 387 391 WRITE_ONCE(cpudata->lowest_nonlinear_perf, AMD_CPPC_LOWNONLIN_PERF(cap1)); 388 392 WRITE_ONCE(cpudata->lowest_perf, AMD_CPPC_LOWEST_PERF(cap1)); ··· 398 394 static int shmem_init_perf(struct amd_cpudata *cpudata) 399 395 { 400 396 struct cppc_perf_caps cppc_perf; 397 + u64 numerator; 401 398 402 399 int ret = cppc_get_perf_caps(cpudata->cpu, &cppc_perf); 403 400 if (ret) 404 401 return ret; 405 402 406 - WRITE_ONCE(cpudata->highest_perf, cppc_perf.highest_perf); 407 - WRITE_ONCE(cpudata->max_limit_perf, cppc_perf.highest_perf); 403 + ret = amd_get_boost_ratio_numerator(cpudata->cpu, &numerator); 404 + if (ret) 405 + return ret; 406 + 407 + WRITE_ONCE(cpudata->highest_perf, numerator); 408 + WRITE_ONCE(cpudata->max_limit_perf, numerator); 408 409 WRITE_ONCE(cpudata->nominal_perf, cppc_perf.nominal_perf); 409 410 WRITE_ONCE(cpudata->lowest_nonlinear_perf, 410 411 cppc_perf.lowest_nonlinear_perf); ··· 570 561 571 562 static int amd_pstate_update_min_max_limit(struct cpufreq_policy *policy) 572 563 { 573 - u32 max_limit_perf, min_limit_perf, lowest_perf, max_perf; 564 + u32 max_limit_perf, min_limit_perf, lowest_perf, max_perf, max_freq; 574 565 struct amd_cpudata *cpudata = policy->driver_data; 575 566 576 - if (cpudata->boost_supported && !policy->boost_enabled) 577 - max_perf = READ_ONCE(cpudata->nominal_perf); 578 - else 579 - max_perf = READ_ONCE(cpudata->highest_perf); 580 - 581 - max_limit_perf = div_u64(policy->max * max_perf, policy->cpuinfo.max_freq); 582 - min_limit_perf = div_u64(policy->min * max_perf, policy->cpuinfo.max_freq); 567 + max_perf = READ_ONCE(cpudata->highest_perf); 568 + max_freq = READ_ONCE(cpudata->max_freq); 569 + max_limit_perf = div_u64(policy->max * max_perf, max_freq); 570 + min_limit_perf = div_u64(policy->min * max_perf, max_freq); 583 571 584 572 lowest_perf = READ_ONCE(cpudata->lowest_perf); 585 573 if (min_limit_perf < lowest_perf) ··· 895 889 { 896 890 int ret; 897 891 u32 min_freq, max_freq; 898 - u64 numerator; 899 892 u32 nominal_perf, nominal_freq; 900 893 u32 lowest_nonlinear_perf, lowest_nonlinear_freq; 901 894 u32 boost_ratio, lowest_nonlinear_ratio; ··· 916 911 917 912 nominal_perf = READ_ONCE(cpudata->nominal_perf); 918 913 919 - ret = amd_get_boost_ratio_numerator(cpudata->cpu, &numerator); 920 - if (ret) 921 - return ret; 922 - boost_ratio = div_u64(numerator << SCHED_CAPACITY_SHIFT, nominal_perf); 914 + boost_ratio = div_u64(cpudata->highest_perf << SCHED_CAPACITY_SHIFT, nominal_perf); 923 915 max_freq = (nominal_freq * boost_ratio >> SCHED_CAPACITY_SHIFT) * 1000; 924 916 925 917 lowest_nonlinear_perf = READ_ONCE(cpudata->lowest_nonlinear_perf); ··· 1871 1869 static_call_update(amd_pstate_update_perf, shmem_update_perf); 1872 1870 } 1873 1871 1874 - ret = amd_pstate_register_driver(cppc_state); 1875 - if (ret) { 1876 - pr_err("failed to register with return %d\n", ret); 1877 - return ret; 1878 - } 1879 - 1880 1872 if (amd_pstate_prefcore) { 1881 1873 ret = amd_detect_prefcore(&amd_pstate_prefcore); 1882 1874 if (ret) 1883 1875 return ret; 1876 + } 1877 + 1878 + ret = amd_pstate_register_driver(cppc_state); 1879 + if (ret) { 1880 + pr_err("failed to register with return %d\n", ret); 1881 + return ret; 1884 1882 } 1885 1883 1886 1884 dev_root = bus_get_dev_root(&cpu_subsys);