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

Merge back cpufreq material for 4.19.

+299 -18
+15
Documentation/devicetree/bindings/arm/marvell/armada-37xx.txt
··· 33 33 compatible = "marvell,armada-3700-nb-pm", "syscon"; 34 34 reg = <0x14000 0x60>; 35 35 } 36 + 37 + AVS 38 + --- 39 + 40 + For AVS an other component is needed: 41 + 42 + Required properties: 43 + - compatible : should contain "marvell,armada-3700-avs", "syscon"; 44 + - reg : the register start and length for the AVS 45 + 46 + Example: 47 + avs: avs@11500 { 48 + compatible = "marvell,armada-3700-avs", "syscon"; 49 + reg = <0x11500 0x40>; 50 + }
+160 -3
drivers/cpufreq/armada-37xx-cpufreq.c
··· 51 51 #define ARMADA_37XX_DVFS_LOAD_2 2 52 52 #define ARMADA_37XX_DVFS_LOAD_3 3 53 53 54 + /* AVS register set */ 55 + #define ARMADA_37XX_AVS_CTL0 0x0 56 + #define ARMADA_37XX_AVS_ENABLE BIT(30) 57 + #define ARMADA_37XX_AVS_HIGH_VDD_LIMIT 16 58 + #define ARMADA_37XX_AVS_LOW_VDD_LIMIT 22 59 + #define ARMADA_37XX_AVS_VDD_MASK 0x3F 60 + #define ARMADA_37XX_AVS_CTL2 0x8 61 + #define ARMADA_37XX_AVS_LOW_VDD_EN BIT(6) 62 + #define ARMADA_37XX_AVS_VSET(x) (0x1C + 4 * (x)) 63 + 54 64 /* 55 65 * On Armada 37xx the Power management manages 4 level of CPU load, 56 66 * each level can be associated with a CPU clock source, a CPU 57 67 * divider, a VDD level, etc... 58 68 */ 59 69 #define LOAD_LEVEL_NR 4 70 + 71 + #define MIN_VOLT_MV 1000 72 + 73 + /* AVS value for the corresponding voltage (in mV) */ 74 + static int avs_map[] = { 75 + 747, 758, 770, 782, 793, 805, 817, 828, 840, 852, 863, 875, 887, 898, 76 + 910, 922, 933, 945, 957, 968, 980, 992, 1003, 1015, 1027, 1038, 1050, 77 + 1062, 1073, 1085, 1097, 1108, 1120, 1132, 1143, 1155, 1167, 1178, 1190, 78 + 1202, 1213, 1225, 1237, 1248, 1260, 1272, 1283, 1295, 1307, 1318, 1330, 79 + 1342 80 + }; 60 81 61 82 struct armada37xx_cpufreq_state { 62 83 struct regmap *regmap; ··· 92 71 struct armada_37xx_dvfs { 93 72 u32 cpu_freq_max; 94 73 u8 divider[LOAD_LEVEL_NR]; 74 + u32 avs[LOAD_LEVEL_NR]; 95 75 }; 96 76 97 77 static struct armada_37xx_dvfs armada_37xx_dvfs[] = { ··· 170 148 clk_set_parent(clk, parent); 171 149 } 172 150 151 + /* 152 + * Find out the armada 37x supported AVS value whose voltage value is 153 + * the round-up closest to the target voltage value. 154 + */ 155 + static u32 armada_37xx_avs_val_match(int target_vm) 156 + { 157 + u32 avs; 158 + 159 + /* Find out the round-up closest supported voltage value */ 160 + for (avs = 0; avs < ARRAY_SIZE(avs_map); avs++) 161 + if (avs_map[avs] >= target_vm) 162 + break; 163 + 164 + /* 165 + * If all supported voltages are smaller than target one, 166 + * choose the largest supported voltage 167 + */ 168 + if (avs == ARRAY_SIZE(avs_map)) 169 + avs = ARRAY_SIZE(avs_map) - 1; 170 + 171 + return avs; 172 + } 173 + 174 + /* 175 + * For Armada 37xx soc, L0(VSET0) VDD AVS value is set to SVC revision 176 + * value or a default value when SVC is not supported. 177 + * - L0 can be read out from the register of AVS_CTRL_0 and L0 voltage 178 + * can be got from the mapping table of avs_map. 179 + * - L1 voltage should be about 100mv smaller than L0 voltage 180 + * - L2 & L3 voltage should be about 150mv smaller than L0 voltage. 181 + * This function calculates L1 & L2 & L3 AVS values dynamically based 182 + * on L0 voltage and fill all AVS values to the AVS value table. 183 + */ 184 + static void __init armada37xx_cpufreq_avs_configure(struct regmap *base, 185 + struct armada_37xx_dvfs *dvfs) 186 + { 187 + unsigned int target_vm; 188 + int load_level = 0; 189 + u32 l0_vdd_min; 190 + 191 + if (base == NULL) 192 + return; 193 + 194 + /* Get L0 VDD min value */ 195 + regmap_read(base, ARMADA_37XX_AVS_CTL0, &l0_vdd_min); 196 + l0_vdd_min = (l0_vdd_min >> ARMADA_37XX_AVS_LOW_VDD_LIMIT) & 197 + ARMADA_37XX_AVS_VDD_MASK; 198 + if (l0_vdd_min >= ARRAY_SIZE(avs_map)) { 199 + pr_err("L0 VDD MIN %d is not correct.\n", l0_vdd_min); 200 + return; 201 + } 202 + dvfs->avs[0] = l0_vdd_min; 203 + 204 + if (avs_map[l0_vdd_min] <= MIN_VOLT_MV) { 205 + /* 206 + * If L0 voltage is smaller than 1000mv, then all VDD sets 207 + * use L0 voltage; 208 + */ 209 + u32 avs_min = armada_37xx_avs_val_match(MIN_VOLT_MV); 210 + 211 + for (load_level = 1; load_level < LOAD_LEVEL_NR; load_level++) 212 + dvfs->avs[load_level] = avs_min; 213 + 214 + return; 215 + } 216 + 217 + /* 218 + * L1 voltage is equal to L0 voltage - 100mv and it must be 219 + * larger than 1000mv 220 + */ 221 + 222 + target_vm = avs_map[l0_vdd_min] - 100; 223 + target_vm = target_vm > MIN_VOLT_MV ? target_vm : MIN_VOLT_MV; 224 + dvfs->avs[1] = armada_37xx_avs_val_match(target_vm); 225 + 226 + /* 227 + * L2 & L3 voltage is equal to L0 voltage - 150mv and it must 228 + * be larger than 1000mv 229 + */ 230 + target_vm = avs_map[l0_vdd_min] - 150; 231 + target_vm = target_vm > MIN_VOLT_MV ? target_vm : MIN_VOLT_MV; 232 + dvfs->avs[2] = dvfs->avs[3] = armada_37xx_avs_val_match(target_vm); 233 + } 234 + 235 + static void __init armada37xx_cpufreq_avs_setup(struct regmap *base, 236 + struct armada_37xx_dvfs *dvfs) 237 + { 238 + unsigned int avs_val = 0, freq; 239 + int load_level = 0; 240 + 241 + if (base == NULL) 242 + return; 243 + 244 + /* Disable AVS before the configuration */ 245 + regmap_update_bits(base, ARMADA_37XX_AVS_CTL0, 246 + ARMADA_37XX_AVS_ENABLE, 0); 247 + 248 + 249 + /* Enable low voltage mode */ 250 + regmap_update_bits(base, ARMADA_37XX_AVS_CTL2, 251 + ARMADA_37XX_AVS_LOW_VDD_EN, 252 + ARMADA_37XX_AVS_LOW_VDD_EN); 253 + 254 + 255 + for (load_level = 1; load_level < LOAD_LEVEL_NR; load_level++) { 256 + freq = dvfs->cpu_freq_max / dvfs->divider[load_level]; 257 + 258 + avs_val = dvfs->avs[load_level]; 259 + regmap_update_bits(base, ARMADA_37XX_AVS_VSET(load_level-1), 260 + ARMADA_37XX_AVS_VDD_MASK << ARMADA_37XX_AVS_HIGH_VDD_LIMIT | 261 + ARMADA_37XX_AVS_VDD_MASK << ARMADA_37XX_AVS_LOW_VDD_LIMIT, 262 + avs_val << ARMADA_37XX_AVS_HIGH_VDD_LIMIT | 263 + avs_val << ARMADA_37XX_AVS_LOW_VDD_LIMIT); 264 + } 265 + 266 + /* Enable AVS after the configuration */ 267 + regmap_update_bits(base, ARMADA_37XX_AVS_CTL0, 268 + ARMADA_37XX_AVS_ENABLE, 269 + ARMADA_37XX_AVS_ENABLE); 270 + 271 + } 272 + 173 273 static void armada37xx_cpufreq_disable_dvfs(struct regmap *base) 174 274 { 175 275 unsigned int reg = ARMADA_37XX_NB_DYN_MOD, ··· 360 216 struct platform_device *pdev; 361 217 unsigned long freq; 362 218 unsigned int cur_frequency; 363 - struct regmap *nb_pm_base; 219 + struct regmap *nb_pm_base, *avs_base; 364 220 struct device *cpu_dev; 365 221 int load_lvl, ret; 366 222 struct clk *clk; ··· 371 227 if (IS_ERR(nb_pm_base)) 372 228 return -ENODEV; 373 229 230 + avs_base = 231 + syscon_regmap_lookup_by_compatible("marvell,armada-3700-avs"); 232 + 233 + /* if AVS is not present don't use it but still try to setup dvfs */ 234 + if (IS_ERR(avs_base)) { 235 + pr_info("Syscon failed for Adapting Voltage Scaling: skip it\n"); 236 + avs_base = NULL; 237 + } 374 238 /* Before doing any configuration on the DVFS first, disable it */ 375 239 armada37xx_cpufreq_disable_dvfs(nb_pm_base); 376 240 ··· 422 270 423 271 armada37xx_cpufreq_state->regmap = nb_pm_base; 424 272 273 + armada37xx_cpufreq_avs_configure(avs_base, dvfs); 274 + armada37xx_cpufreq_avs_setup(avs_base, dvfs); 275 + 425 276 armada37xx_cpufreq_dvfs_setup(nb_pm_base, clk, dvfs->divider); 426 277 clk_put(clk); 427 278 428 279 for (load_lvl = ARMADA_37XX_DVFS_LOAD_0; load_lvl < LOAD_LEVEL_NR; 429 280 load_lvl++) { 281 + unsigned long u_volt = avs_map[dvfs->avs[load_lvl]] * 1000; 430 282 freq = cur_frequency / dvfs->divider[load_lvl]; 431 - 432 - ret = dev_pm_opp_add(cpu_dev, freq, 0); 283 + ret = dev_pm_opp_add(cpu_dev, freq, u_volt); 433 284 if (ret) 434 285 goto remove_opp; 286 + 287 + 435 288 } 436 289 437 290 /* Now that everything is setup, enable the DVFS at hardware level */
+52
drivers/cpufreq/cppc_cpufreq.c
··· 296 296 return ret; 297 297 } 298 298 299 + static inline u64 get_delta(u64 t1, u64 t0) 300 + { 301 + if (t1 > t0 || t0 > ~(u32)0) 302 + return t1 - t0; 303 + 304 + return (u32)t1 - (u32)t0; 305 + } 306 + 307 + static int cppc_get_rate_from_fbctrs(struct cppc_cpudata *cpu, 308 + struct cppc_perf_fb_ctrs fb_ctrs_t0, 309 + struct cppc_perf_fb_ctrs fb_ctrs_t1) 310 + { 311 + u64 delta_reference, delta_delivered; 312 + u64 reference_perf, delivered_perf; 313 + 314 + reference_perf = fb_ctrs_t0.reference_perf; 315 + 316 + delta_reference = get_delta(fb_ctrs_t1.reference, 317 + fb_ctrs_t0.reference); 318 + delta_delivered = get_delta(fb_ctrs_t1.delivered, 319 + fb_ctrs_t0.delivered); 320 + 321 + /* Check to avoid divide-by zero */ 322 + if (delta_reference || delta_delivered) 323 + delivered_perf = (reference_perf * delta_delivered) / 324 + delta_reference; 325 + else 326 + delivered_perf = cpu->perf_ctrls.desired_perf; 327 + 328 + return cppc_cpufreq_perf_to_khz(cpu, delivered_perf); 329 + } 330 + 331 + static unsigned int cppc_cpufreq_get_rate(unsigned int cpunum) 332 + { 333 + struct cppc_perf_fb_ctrs fb_ctrs_t0 = {0}, fb_ctrs_t1 = {0}; 334 + struct cppc_cpudata *cpu = all_cpu_data[cpunum]; 335 + int ret; 336 + 337 + ret = cppc_get_perf_ctrs(cpunum, &fb_ctrs_t0); 338 + if (ret) 339 + return ret; 340 + 341 + udelay(2); /* 2usec delay between sampling */ 342 + 343 + ret = cppc_get_perf_ctrs(cpunum, &fb_ctrs_t1); 344 + if (ret) 345 + return ret; 346 + 347 + return cppc_get_rate_from_fbctrs(cpu, fb_ctrs_t0, fb_ctrs_t1); 348 + } 349 + 299 350 static struct cpufreq_driver cppc_cpufreq_driver = { 300 351 .flags = CPUFREQ_CONST_LOOPS, 301 352 .verify = cppc_verify_policy, 302 353 .target = cppc_cpufreq_set_target, 354 + .get = cppc_cpufreq_get_rate, 303 355 .init = cppc_cpufreq_cpu_init, 304 356 .stop_cpu = cppc_cpufreq_stop_cpu, 305 357 .name = "cppc_cpufreq",
+21
drivers/cpufreq/imx6q-cpufreq.c
··· 9 9 #include <linux/clk.h> 10 10 #include <linux/cpu.h> 11 11 #include <linux/cpufreq.h> 12 + #include <linux/cpu_cooling.h> 12 13 #include <linux/err.h> 13 14 #include <linux/module.h> 14 15 #include <linux/of.h> ··· 51 50 }; 52 51 53 52 static struct device *cpu_dev; 53 + static struct thermal_cooling_device *cdev; 54 54 static bool free_opp; 55 55 static struct cpufreq_frequency_table *freq_table; 56 56 static unsigned int max_freq; ··· 193 191 return 0; 194 192 } 195 193 194 + static void imx6q_cpufreq_ready(struct cpufreq_policy *policy) 195 + { 196 + cdev = of_cpufreq_cooling_register(policy); 197 + 198 + if (!cdev) 199 + dev_err(cpu_dev, 200 + "running cpufreq without cooling device: %ld\n", 201 + PTR_ERR(cdev)); 202 + } 203 + 196 204 static int imx6q_cpufreq_init(struct cpufreq_policy *policy) 197 205 { 198 206 int ret; ··· 214 202 return ret; 215 203 } 216 204 205 + static int imx6q_cpufreq_exit(struct cpufreq_policy *policy) 206 + { 207 + cpufreq_cooling_unregister(cdev); 208 + 209 + return 0; 210 + } 211 + 217 212 static struct cpufreq_driver imx6q_cpufreq_driver = { 218 213 .flags = CPUFREQ_NEED_INITIAL_FREQ_CHECK, 219 214 .verify = cpufreq_generic_frequency_table_verify, 220 215 .target_index = imx6q_set_target, 221 216 .get = cpufreq_generic_get, 222 217 .init = imx6q_cpufreq_init, 218 + .exit = imx6q_cpufreq_exit, 223 219 .name = "imx6q-cpufreq", 220 + .ready = imx6q_cpufreq_ready, 224 221 .attr = cpufreq_generic_attr, 225 222 .suspend = cpufreq_generic_suspend, 226 223 };
+15 -9
drivers/cpufreq/intel_pstate.c
··· 657 657 { 658 658 struct cpudata *cpu_data = all_cpu_data[policy->cpu]; 659 659 char str_preference[21]; 660 - int ret, i = 0; 660 + int ret; 661 661 662 662 ret = sscanf(buf, "%20s", str_preference); 663 663 if (ret != 1) 664 664 return -EINVAL; 665 665 666 - while (energy_perf_strings[i] != NULL) { 667 - if (!strcmp(str_preference, energy_perf_strings[i])) { 668 - intel_pstate_set_energy_pref_index(cpu_data, i); 669 - return count; 670 - } 671 - ++i; 672 - } 666 + ret = match_string(energy_perf_strings, -1, str_preference); 667 + if (ret < 0) 668 + return ret; 673 669 674 - return -EINVAL; 670 + intel_pstate_set_energy_pref_index(cpu_data, ret); 671 + return count; 675 672 } 676 673 677 674 static ssize_t show_energy_performance_preference( ··· 2068 2071 policy->cpuinfo.max_freq = global.turbo_disabled ? 2069 2072 cpu->pstate.max_pstate : cpu->pstate.turbo_pstate; 2070 2073 policy->cpuinfo.max_freq *= cpu->pstate.scaling; 2074 + 2075 + if (hwp_active) { 2076 + unsigned int max_freq; 2077 + 2078 + max_freq = global.turbo_disabled ? 2079 + cpu->pstate.max_freq : cpu->pstate.turbo_freq; 2080 + if (max_freq < policy->cpuinfo.max_freq) 2081 + policy->cpuinfo.max_freq = max_freq; 2082 + } 2071 2083 2072 2084 intel_pstate_init_acpi_perf_limits(policy); 2073 2085
+9
drivers/cpufreq/pcc-cpufreq.c
··· 593 593 return ret; 594 594 } 595 595 596 + if (num_present_cpus() > 4) { 597 + pcc_cpufreq_driver.flags |= CPUFREQ_NO_AUTO_DYNAMIC_SWITCHING; 598 + pr_err("%s: Too many CPUs, dynamic performance scaling disabled\n", 599 + __func__); 600 + pr_err("%s: Try to enable another scaling driver through BIOS settings\n", 601 + __func__); 602 + pr_err("%s: and complain to the system vendor\n", __func__); 603 + } 604 + 596 605 ret = cpufreq_register_driver(&pcc_cpufreq_driver); 597 606 598 607 return ret;
+3 -2
drivers/cpufreq/qcom-cpufreq-kryo.c
··· 109 109 speedbin_nvmem = of_nvmem_cell_get(np, NULL); 110 110 of_node_put(np); 111 111 if (IS_ERR(speedbin_nvmem)) { 112 - dev_err(cpu_dev, "Could not get nvmem cell: %ld\n", 113 - PTR_ERR(speedbin_nvmem)); 112 + if (PTR_ERR(speedbin_nvmem) != -EPROBE_DEFER) 113 + dev_err(cpu_dev, "Could not get nvmem cell: %ld\n", 114 + PTR_ERR(speedbin_nvmem)); 114 115 return PTR_ERR(speedbin_nvmem); 115 116 } 116 117
+24 -4
drivers/thermal/imx_thermal.c
··· 3 3 // Copyright 2013 Freescale Semiconductor, Inc. 4 4 5 5 #include <linux/clk.h> 6 + #include <linux/cpu.h> 6 7 #include <linux/cpufreq.h> 7 8 #include <linux/cpu_cooling.h> 8 9 #include <linux/delay.h> ··· 645 644 }; 646 645 MODULE_DEVICE_TABLE(of, of_imx_thermal_match); 647 646 647 + /* 648 + * Create cooling device in case no #cooling-cells property is available in 649 + * CPU node 650 + */ 651 + static int imx_thermal_register_legacy_cooling(struct imx_thermal_data *data) 652 + { 653 + struct device_node *np = of_get_cpu_node(data->policy->cpu, NULL); 654 + int ret; 655 + 656 + if (!np || !of_find_property(np, "#cooling-cells", NULL)) { 657 + data->cdev = cpufreq_cooling_register(data->policy); 658 + if (IS_ERR(data->cdev)) { 659 + ret = PTR_ERR(data->cdev); 660 + cpufreq_cpu_put(data->policy); 661 + return ret; 662 + } 663 + } 664 + 665 + return 0; 666 + } 667 + 648 668 static int imx_thermal_probe(struct platform_device *pdev) 649 669 { 650 670 struct imx_thermal_data *data; ··· 746 724 return -EPROBE_DEFER; 747 725 } 748 726 749 - data->cdev = cpufreq_cooling_register(data->policy); 750 - if (IS_ERR(data->cdev)) { 751 - ret = PTR_ERR(data->cdev); 727 + ret = imx_thermal_register_legacy_cooling(data); 728 + if (ret) { 752 729 dev_err(&pdev->dev, 753 730 "failed to register cpufreq cooling device: %d\n", ret); 754 - cpufreq_cpu_put(data->policy); 755 731 return ret; 756 732 } 757 733