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 branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/evalenti/linux-soc-thermal

Pull thermal management fixes from Eduardo Valentin:
"Specifics in this pull request:

- Compilation fixes on SPEAR, and U8500 thermal drivers.
- RCAR thermal driver now recognizes OF-thermal based thermal zones.
- Small code rework on OF-thermal.
- These change have been CI tested using KernelCI bot [1,2]. \o/

I am taking over on Rui's behalf while he is out. Happy New Chinese
Year!

[1] - https://kernelci.org/build/evalenti/kernel/v4.5-rc3-16-ga53b8394ec3c/
[2] - https://kernelci.org/boot/all/job/evalenti/kernel/v4.5-rc3-16-ga53b8394ec3c/"

* 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/evalenti/linux-soc-thermal:
thermal: cpu_cooling: fix out of bounds access in time_in_idle
thermal: allow u8500-thermal driver to be a module
thermal: allow spear-thermal driver to be a module
thermal: spear: use __maybe_unused for PM functions
thermal: rcar: enable to use thermal-zone on DT
thermal: of: use for_each_available_child_of_node for child iterator

+94 -35
+35 -2
Documentation/devicetree/bindings/thermal/rcar-thermal.txt
··· 1 1 * Renesas R-Car Thermal 2 2 3 3 Required properties: 4 - - compatible : "renesas,thermal-<soctype>", "renesas,rcar-thermal" 5 - as fallback. 4 + - compatible : "renesas,thermal-<soctype>", 5 + "renesas,rcar-gen2-thermal" (with thermal-zone) or 6 + "renesas,rcar-thermal" (without thermal-zone) as fallback. 6 7 Examples with soctypes are: 7 8 - "renesas,thermal-r8a73a4" (R-Mobile APE6) 8 9 - "renesas,thermal-r8a7779" (R-Car H1) ··· 36 35 0xe61f0200 0x38 37 36 0xe61f0300 0x38>; 38 37 interrupts = <0 69 IRQ_TYPE_LEVEL_HIGH>; 38 + }; 39 + 40 + Example (with thermal-zone): 41 + 42 + thermal-zones { 43 + cpu_thermal: cpu-thermal { 44 + polling-delay-passive = <1000>; 45 + polling-delay = <5000>; 46 + 47 + thermal-sensors = <&thermal>; 48 + 49 + trips { 50 + cpu-crit { 51 + temperature = <115000>; 52 + hysteresis = <0>; 53 + type = "critical"; 54 + }; 55 + }; 56 + cooling-maps { 57 + }; 58 + }; 59 + }; 60 + 61 + thermal: thermal@e61f0000 { 62 + compatible = "renesas,thermal-r8a7790", 63 + "renesas,rcar-gen2-thermal", 64 + "renesas,rcar-thermal"; 65 + reg = <0 0xe61f0000 0 0x14>, <0 0xe61f0100 0 0x38>; 66 + interrupts = <0 69 IRQ_TYPE_LEVEL_HIGH>; 67 + clocks = <&mstp5_clks R8A7790_CLK_THERMAL>; 68 + power-domains = <&cpg_clocks>; 69 + #thermal-sensor-cells = <0>; 39 70 };
+3
drivers/mfd/db8500-prcmu.c
··· 2048 2048 2049 2049 return 0; 2050 2050 } 2051 + EXPORT_SYMBOL_GPL(db8500_prcmu_config_hotmon); 2051 2052 2052 2053 static int config_hot_period(u16 val) 2053 2054 { ··· 2075 2074 2076 2075 return config_hot_period(cycles32k); 2077 2076 } 2077 + EXPORT_SYMBOL_GPL(db8500_prcmu_start_temp_sense); 2078 2078 2079 2079 int db8500_prcmu_stop_temp_sense(void) 2080 2080 { 2081 2081 return config_hot_period(0xFFFF); 2082 2082 } 2083 + EXPORT_SYMBOL_GPL(db8500_prcmu_stop_temp_sense); 2083 2084 2084 2085 static int prcmu_a9wdog(u8 cmd, u8 d0, u8 d1, u8 d2, u8 d3) 2085 2086 {
+3 -3
drivers/thermal/Kconfig
··· 195 195 passive trip is crossed. 196 196 197 197 config SPEAR_THERMAL 198 - bool "SPEAr thermal sensor driver" 198 + tristate "SPEAr thermal sensor driver" 199 199 depends on PLAT_SPEAR || COMPILE_TEST 200 200 depends on OF 201 201 help ··· 237 237 framework. 238 238 239 239 config DB8500_THERMAL 240 - bool "DB8500 thermal management" 241 - depends on ARCH_U8500 240 + tristate "DB8500 thermal management" 241 + depends on MFD_DB8500_PRCMU 242 242 default y 243 243 help 244 244 Adds DB8500 thermal management implementation according to the thermal
+8 -6
drivers/thermal/cpu_cooling.c
··· 377 377 * get_load() - get load for a cpu since last updated 378 378 * @cpufreq_device: &struct cpufreq_cooling_device for this cpu 379 379 * @cpu: cpu number 380 + * @cpu_idx: index of the cpu in cpufreq_device->allowed_cpus 380 381 * 381 382 * Return: The average load of cpu @cpu in percentage since this 382 383 * function was last called. 383 384 */ 384 - static u32 get_load(struct cpufreq_cooling_device *cpufreq_device, int cpu) 385 + static u32 get_load(struct cpufreq_cooling_device *cpufreq_device, int cpu, 386 + int cpu_idx) 385 387 { 386 388 u32 load; 387 389 u64 now, now_idle, delta_time, delta_idle; 388 390 389 391 now_idle = get_cpu_idle_time(cpu, &now, 0); 390 - delta_idle = now_idle - cpufreq_device->time_in_idle[cpu]; 391 - delta_time = now - cpufreq_device->time_in_idle_timestamp[cpu]; 392 + delta_idle = now_idle - cpufreq_device->time_in_idle[cpu_idx]; 393 + delta_time = now - cpufreq_device->time_in_idle_timestamp[cpu_idx]; 392 394 393 395 if (delta_time <= delta_idle) 394 396 load = 0; 395 397 else 396 398 load = div64_u64(100 * (delta_time - delta_idle), delta_time); 397 399 398 - cpufreq_device->time_in_idle[cpu] = now_idle; 399 - cpufreq_device->time_in_idle_timestamp[cpu] = now; 400 + cpufreq_device->time_in_idle[cpu_idx] = now_idle; 401 + cpufreq_device->time_in_idle_timestamp[cpu_idx] = now; 400 402 401 403 return load; 402 404 } ··· 600 598 u32 load; 601 599 602 600 if (cpu_online(cpu)) 603 - load = get_load(cpufreq_device, cpu); 601 + load = get_load(cpufreq_device, cpu, i); 604 602 else 605 603 load = 0; 606 604
+3 -15
drivers/thermal/of-thermal.c
··· 475 475 476 476 sensor_np = of_node_get(dev->of_node); 477 477 478 - for_each_child_of_node(np, child) { 478 + for_each_available_child_of_node(np, child) { 479 479 struct of_phandle_args sensor_specs; 480 480 int ret, id; 481 - 482 - /* Check whether child is enabled or not */ 483 - if (!of_device_is_available(child)) 484 - continue; 485 481 486 482 /* For now, thermal framework supports only 1 sensor per zone */ 487 483 ret = of_parse_phandle_with_args(child, "thermal-sensors", ··· 877 881 return 0; /* Run successfully on systems without thermal DT */ 878 882 } 879 883 880 - for_each_child_of_node(np, child) { 884 + for_each_available_child_of_node(np, child) { 881 885 struct thermal_zone_device *zone; 882 886 struct thermal_zone_params *tzp; 883 887 int i, mask = 0; 884 888 u32 prop; 885 - 886 - /* Check whether child is enabled or not */ 887 - if (!of_device_is_available(child)) 888 - continue; 889 889 890 890 tz = thermal_of_build_thermal_zone(child); 891 891 if (IS_ERR(tz)) { ··· 960 968 return; 961 969 } 962 970 963 - for_each_child_of_node(np, child) { 971 + for_each_available_child_of_node(np, child) { 964 972 struct thermal_zone_device *zone; 965 - 966 - /* Check whether child is enabled or not */ 967 - if (!of_device_is_available(child)) 968 - continue; 969 973 970 974 zone = thermal_zone_get_zone_by_name(child->name); 971 975 if (IS_ERR(zone))
+40 -5
drivers/thermal/rcar_thermal.c
··· 23 23 #include <linux/interrupt.h> 24 24 #include <linux/io.h> 25 25 #include <linux/module.h> 26 + #include <linux/of_device.h> 26 27 #include <linux/platform_device.h> 27 28 #include <linux/pm_runtime.h> 28 29 #include <linux/reboot.h> ··· 76 75 #define rcar_has_irq_support(priv) ((priv)->common->base) 77 76 #define rcar_id_to_shift(priv) ((priv)->id * 8) 78 77 78 + #define USE_OF_THERMAL 1 79 79 static const struct of_device_id rcar_thermal_dt_ids[] = { 80 80 { .compatible = "renesas,rcar-thermal", }, 81 + { .compatible = "renesas,rcar-gen2-thermal", .data = (void *)USE_OF_THERMAL }, 81 82 {}, 82 83 }; 83 84 MODULE_DEVICE_TABLE(of, rcar_thermal_dt_ids); ··· 203 200 return ret; 204 201 } 205 202 206 - static int rcar_thermal_get_temp(struct thermal_zone_device *zone, int *temp) 203 + static int rcar_thermal_get_current_temp(struct rcar_thermal_priv *priv, 204 + int *temp) 207 205 { 208 - struct rcar_thermal_priv *priv = rcar_zone_to_priv(zone); 209 206 int tmp; 210 207 int ret; 211 208 ··· 227 224 *temp = tmp; 228 225 229 226 return 0; 227 + } 228 + 229 + static int rcar_thermal_of_get_temp(void *data, int *temp) 230 + { 231 + struct rcar_thermal_priv *priv = data; 232 + 233 + return rcar_thermal_get_current_temp(priv, temp); 234 + } 235 + 236 + static int rcar_thermal_get_temp(struct thermal_zone_device *zone, int *temp) 237 + { 238 + struct rcar_thermal_priv *priv = rcar_zone_to_priv(zone); 239 + 240 + return rcar_thermal_get_current_temp(priv, temp); 230 241 } 231 242 232 243 static int rcar_thermal_get_trip_type(struct thermal_zone_device *zone, ··· 299 282 return 0; 300 283 } 301 284 285 + static const struct thermal_zone_of_device_ops rcar_thermal_zone_of_ops = { 286 + .get_temp = rcar_thermal_of_get_temp, 287 + }; 288 + 302 289 static struct thermal_zone_device_ops rcar_thermal_zone_ops = { 303 290 .get_temp = rcar_thermal_get_temp, 304 291 .get_trip_type = rcar_thermal_get_trip_type, ··· 339 318 340 319 priv = container_of(work, struct rcar_thermal_priv, work.work); 341 320 342 - rcar_thermal_get_temp(priv->zone, &cctemp); 321 + ret = rcar_thermal_get_current_temp(priv, &cctemp); 322 + if (ret < 0) 323 + return; 324 + 343 325 ret = rcar_thermal_update_temp(priv); 344 326 if (ret < 0) 345 327 return; 346 328 347 329 rcar_thermal_irq_enable(priv); 348 330 349 - rcar_thermal_get_temp(priv->zone, &nctemp); 331 + ret = rcar_thermal_get_current_temp(priv, &nctemp); 332 + if (ret < 0) 333 + return; 334 + 350 335 if (nctemp != cctemp) 351 336 thermal_zone_device_update(priv->zone); 352 337 } ··· 430 403 struct rcar_thermal_priv *priv; 431 404 struct device *dev = &pdev->dev; 432 405 struct resource *res, *irq; 406 + const struct of_device_id *of_id = of_match_device(rcar_thermal_dt_ids, dev); 407 + unsigned long of_data = (unsigned long)of_id->data; 433 408 int mres = 0; 434 409 int i; 435 410 int ret = -ENODEV; ··· 492 463 if (ret < 0) 493 464 goto error_unregister; 494 465 495 - priv->zone = thermal_zone_device_register("rcar_thermal", 466 + if (of_data == USE_OF_THERMAL) 467 + priv->zone = thermal_zone_of_sensor_register( 468 + dev, i, priv, 469 + &rcar_thermal_zone_of_ops); 470 + else 471 + priv->zone = thermal_zone_device_register( 472 + "rcar_thermal", 496 473 1, 0, priv, 497 474 &rcar_thermal_zone_ops, NULL, 0, 498 475 idle);
+2 -4
drivers/thermal/spear_thermal.c
··· 54 54 .get_temp = thermal_get_temp, 55 55 }; 56 56 57 - #ifdef CONFIG_PM 58 - static int spear_thermal_suspend(struct device *dev) 57 + static int __maybe_unused spear_thermal_suspend(struct device *dev) 59 58 { 60 59 struct platform_device *pdev = to_platform_device(dev); 61 60 struct thermal_zone_device *spear_thermal = platform_get_drvdata(pdev); ··· 71 72 return 0; 72 73 } 73 74 74 - static int spear_thermal_resume(struct device *dev) 75 + static int __maybe_unused spear_thermal_resume(struct device *dev) 75 76 { 76 77 struct platform_device *pdev = to_platform_device(dev); 77 78 struct thermal_zone_device *spear_thermal = platform_get_drvdata(pdev); ··· 93 94 94 95 return 0; 95 96 } 96 - #endif 97 97 98 98 static SIMPLE_DEV_PM_OPS(spear_thermal_pm_ops, spear_thermal_suspend, 99 99 spear_thermal_resume);