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

Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/rzhang/linux

Pull thermal management updates from Zhang Rui:

- fix a race condition issue in power allocator governor (Yi Zeng).

- add support for AP806 and CP110 in armada thermal driver, together
with several improvements (Baruch Siach, Miquel Raynal)

- add support for r8z7743 in rcar thermal driver (Biju Das)

- convert thermal core to use new hwmon API to avoid warning (Fabio
Estevam)

- small fixes and cleanups in thermal core and x86_pkg_thermal,
int3400_thermal, hisi_thermal, mtk_thermal and imx_thermal drivers
(Pravin Shedge, Geert Uytterhoeven, Alexey Khoroshilov, Brian Bian,
Matthias Brugger, Nicolin Chen, Uwe Kleine-König)

* 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/rzhang/linux: (25 commits)
thermal: thermal_hwmon: Convert to hwmon_device_register_with_info()
thermal/x86 pkg temp: Remove debugfs_create_u32() casts
thermal: int3400_thermal: fix error handling in int3400_thermal_probe()
thermal/drivers/hisi: Remove bogus const from function return type
thermal: armada: Give meaningful names to the thermal zones
thermal: armada: Wait sensors validity before exiting the init callback
thermal: armada: Change sensors trim default value
thermal: armada: Update Kconfig and module description
thermal: armada: Add support for Armada CP110
thermal: armada: Add support for Armada AP806
thermal: armada: Use real status register name
thermal: armada: Clarify control registers accesses
thermal: armada: Simplify the check of the validity bit
thermal: armada: Use msleep for long delays
dt-bindings: thermal: Describe Armada AP806 and CP110
dt-bindings: thermal: rcar: Add device tree support for r8a7743
thermal: mtk: Cleanup unused defines
thermal: imx: update to new formula according to NXP AN5215
thermal: imx: use consistent style to write temperatures
thermal: imx: improve comments describing algorithm for temp calculation
...

+311 -209
+25 -12
Documentation/devicetree/bindings/thermal/armada-thermal.txt
··· 2 2 3 3 Required properties: 4 4 5 - - compatible: Should be set to one of the following: 6 - marvell,armada370-thermal 7 - marvell,armada375-thermal 8 - marvell,armada380-thermal 9 - marvell,armadaxp-thermal 5 + - compatible: Should be set to one of the following: 6 + * marvell,armada370-thermal 7 + * marvell,armada375-thermal 8 + * marvell,armada380-thermal 9 + * marvell,armadaxp-thermal 10 + * marvell,armada-ap806-thermal 11 + * marvell,armada-cp110-thermal 10 12 11 - - reg: Device's register space. 12 - Two entries are expected, see the examples below. 13 - The first one is required for the sensor register; 14 - the second one is required for the control register 15 - to be used for sensor initialization (a.k.a. calibration). 13 + - reg: Device's register space. 14 + Two entries are expected, see the examples below. The first one points 15 + to the status register (4B). The second one points to the control 16 + registers (8B). 17 + Note: The compatibles marvell,armada370-thermal, 18 + marvell,armada380-thermal, and marvell,armadaxp-thermal must point to 19 + "control MSB/control 1", with size of 4 (deprecated binding), or point 20 + to "control LSB/control 0" with size of 8 (current binding). All other 21 + compatibles must point to "control LSB/control 0" with size of 8. 16 22 17 - Example: 23 + Examples: 18 24 25 + /* Legacy bindings */ 19 26 thermal@d0018300 { 20 27 compatible = "marvell,armada370-thermal"; 21 - reg = <0xd0018300 0x4 28 + reg = <0xd0018300 0x4 22 29 0xd0018304 0x4>; 30 + }; 31 + 32 + ap_thermal: thermal@6f8084 { 33 + compatible = "marvell,armada-ap806-thermal"; 34 + reg = <0x6f808C 0x4>, 35 + <0x6f8084 0x8>; 23 36 };
+1
Documentation/devicetree/bindings/thermal/rcar-thermal.txt
··· 6 6 "renesas,rcar-thermal" (without thermal-zone) as fallback. 7 7 Examples with soctypes are: 8 8 - "renesas,thermal-r8a73a4" (R-Mobile APE6) 9 + - "renesas,thermal-r8a7743" (RZ/G1M) 9 10 - "renesas,thermal-r8a7779" (R-Car H1) 10 11 - "renesas,thermal-r8a7790" (R-Car H2) 11 12 - "renesas,thermal-r8a7791" (R-Car M2-W)
+2 -2
drivers/thermal/Kconfig
··· 301 301 thermal zone if trip points reached. 302 302 303 303 config ARMADA_THERMAL 304 - tristate "Armada 370/XP thermal management" 304 + tristate "Marvell EBU Armada SoCs thermal management" 305 305 depends on ARCH_MVEBU || COMPILE_TEST 306 306 depends on HAS_IOMEM 307 307 depends on OF 308 308 help 309 309 Enable this option if you want to have support for thermal management 310 - controller present in Armada 370 and Armada XP SoC. 310 + controller present in Marvell EBU Armada SoCs (370,375,XP,38x,7K,8K). 311 311 312 312 config DA9062_THERMAL 313 313 tristate "DA9062/DA9061 Dialog Semiconductor thermal driver"
+186 -65
drivers/thermal/armada_thermal.c
··· 1 1 /* 2 - * Marvell Armada 370/XP thermal sensor driver 2 + * Marvell EBU Armada SoCs thermal sensor driver 3 3 * 4 4 * Copyright (C) 2013 Marvell 5 5 * ··· 23 23 #include <linux/platform_device.h> 24 24 #include <linux/of_device.h> 25 25 #include <linux/thermal.h> 26 - 27 - #define THERMAL_VALID_MASK 0x1 26 + #include <linux/iopoll.h> 28 27 29 28 /* Thermal Manager Control and Status Register */ 30 29 #define PMU_TDC0_SW_RST_MASK (0x1 << 1) ··· 38 39 #define A375_UNIT_CONTROL_MASK 0x7 39 40 #define A375_READOUT_INVERT BIT(15) 40 41 #define A375_HW_RESETn BIT(8) 41 - #define A380_HW_RESET BIT(8) 42 + 43 + /* Legacy bindings */ 44 + #define LEGACY_CONTROL_MEM_LEN 0x4 45 + 46 + /* Current bindings with the 2 control registers under the same memory area */ 47 + #define LEGACY_CONTROL1_OFFSET 0x0 48 + #define CONTROL0_OFFSET 0x0 49 + #define CONTROL1_OFFSET 0x4 50 + 51 + /* Errata fields */ 52 + #define CONTROL0_TSEN_TC_TRIM_MASK 0x7 53 + #define CONTROL0_TSEN_TC_TRIM_VAL 0x3 54 + 55 + /* TSEN refers to the temperature sensors within the AP */ 56 + #define CONTROL0_TSEN_START BIT(0) 57 + #define CONTROL0_TSEN_RESET BIT(1) 58 + #define CONTROL0_TSEN_ENABLE BIT(2) 59 + 60 + /* EXT_TSEN refers to the external temperature sensors, out of the AP */ 61 + #define CONTROL1_EXT_TSEN_SW_RESET BIT(7) 62 + #define CONTROL1_EXT_TSEN_HW_RESETn BIT(8) 63 + 64 + #define STATUS_POLL_PERIOD_US 1000 65 + #define STATUS_POLL_TIMEOUT_US 100000 42 66 43 67 struct armada_thermal_data; 44 68 45 69 /* Marvell EBU Thermal Sensor Dev Structure */ 46 70 struct armada_thermal_priv { 47 - void __iomem *sensor; 48 - void __iomem *control; 71 + void __iomem *status; 72 + void __iomem *control0; 73 + void __iomem *control1; 49 74 struct armada_thermal_data *data; 50 75 }; 51 76 ··· 82 59 bool (*is_valid)(struct armada_thermal_priv *); 83 60 84 61 /* Formula coeficients: temp = (b - m * reg) / div */ 85 - unsigned long coef_b; 86 - unsigned long coef_m; 87 - unsigned long coef_div; 62 + s64 coef_b; 63 + s64 coef_m; 64 + u32 coef_div; 88 65 bool inverted; 66 + bool signed_sample; 89 67 90 68 /* Register shift and mask to access the sensor temperature */ 91 69 unsigned int temp_shift; 92 70 unsigned int temp_mask; 93 - unsigned int is_valid_shift; 71 + u32 is_valid_bit; 72 + bool needs_control0; 94 73 }; 95 74 96 75 static void armadaxp_init_sensor(struct platform_device *pdev, 97 76 struct armada_thermal_priv *priv) 98 77 { 99 - unsigned long reg; 78 + u32 reg; 100 79 101 - reg = readl_relaxed(priv->control); 80 + reg = readl_relaxed(priv->control1); 102 81 reg |= PMU_TDC0_OTF_CAL_MASK; 103 - writel(reg, priv->control); 82 + writel(reg, priv->control1); 104 83 105 84 /* Reference calibration value */ 106 85 reg &= ~PMU_TDC0_REF_CAL_CNT_MASK; 107 86 reg |= (0xf1 << PMU_TDC0_REF_CAL_CNT_OFFS); 108 - writel(reg, priv->control); 87 + writel(reg, priv->control1); 109 88 110 89 /* Reset the sensor */ 111 - reg = readl_relaxed(priv->control); 112 - writel((reg | PMU_TDC0_SW_RST_MASK), priv->control); 90 + reg = readl_relaxed(priv->control1); 91 + writel((reg | PMU_TDC0_SW_RST_MASK), priv->control1); 113 92 114 - writel(reg, priv->control); 93 + writel(reg, priv->control1); 115 94 116 95 /* Enable the sensor */ 117 - reg = readl_relaxed(priv->sensor); 96 + reg = readl_relaxed(priv->status); 118 97 reg &= ~PMU_TM_DISABLE_MASK; 119 - writel(reg, priv->sensor); 98 + writel(reg, priv->status); 120 99 } 121 100 122 101 static void armada370_init_sensor(struct platform_device *pdev, 123 102 struct armada_thermal_priv *priv) 124 103 { 125 - unsigned long reg; 104 + u32 reg; 126 105 127 - reg = readl_relaxed(priv->control); 106 + reg = readl_relaxed(priv->control1); 128 107 reg |= PMU_TDC0_OTF_CAL_MASK; 129 - writel(reg, priv->control); 108 + writel(reg, priv->control1); 130 109 131 110 /* Reference calibration value */ 132 111 reg &= ~PMU_TDC0_REF_CAL_CNT_MASK; 133 112 reg |= (0xf1 << PMU_TDC0_REF_CAL_CNT_OFFS); 134 - writel(reg, priv->control); 113 + writel(reg, priv->control1); 135 114 136 115 reg &= ~PMU_TDC0_START_CAL_MASK; 137 - writel(reg, priv->control); 116 + writel(reg, priv->control1); 138 117 139 - mdelay(10); 118 + msleep(10); 140 119 } 141 120 142 121 static void armada375_init_sensor(struct platform_device *pdev, 143 122 struct armada_thermal_priv *priv) 144 123 { 145 - unsigned long reg; 124 + u32 reg; 146 125 147 - reg = readl(priv->control + 4); 126 + reg = readl(priv->control1); 148 127 reg &= ~(A375_UNIT_CONTROL_MASK << A375_UNIT_CONTROL_SHIFT); 149 128 reg &= ~A375_READOUT_INVERT; 150 129 reg &= ~A375_HW_RESETn; 151 130 152 - writel(reg, priv->control + 4); 153 - mdelay(20); 131 + writel(reg, priv->control1); 132 + msleep(20); 154 133 155 134 reg |= A375_HW_RESETn; 156 - writel(reg, priv->control + 4); 157 - mdelay(50); 135 + writel(reg, priv->control1); 136 + msleep(50); 137 + } 138 + 139 + static void armada_wait_sensor_validity(struct armada_thermal_priv *priv) 140 + { 141 + u32 reg; 142 + 143 + readl_relaxed_poll_timeout(priv->status, reg, 144 + reg & priv->data->is_valid_bit, 145 + STATUS_POLL_PERIOD_US, 146 + STATUS_POLL_TIMEOUT_US); 158 147 } 159 148 160 149 static void armada380_init_sensor(struct platform_device *pdev, 161 150 struct armada_thermal_priv *priv) 162 151 { 163 - unsigned long reg = readl_relaxed(priv->control); 152 + u32 reg = readl_relaxed(priv->control1); 164 153 165 - /* Reset hardware once */ 166 - if (!(reg & A380_HW_RESET)) { 167 - reg |= A380_HW_RESET; 168 - writel(reg, priv->control); 169 - mdelay(10); 154 + /* Disable the HW/SW reset */ 155 + reg |= CONTROL1_EXT_TSEN_HW_RESETn; 156 + reg &= ~CONTROL1_EXT_TSEN_SW_RESET; 157 + writel(reg, priv->control1); 158 + 159 + /* Set Tsen Tc Trim to correct default value (errata #132698) */ 160 + if (priv->control0) { 161 + reg = readl_relaxed(priv->control0); 162 + reg &= ~CONTROL0_TSEN_TC_TRIM_MASK; 163 + reg |= CONTROL0_TSEN_TC_TRIM_VAL; 164 + writel(reg, priv->control0); 170 165 } 166 + 167 + /* Wait the sensors to be valid or the core will warn the user */ 168 + armada_wait_sensor_validity(priv); 169 + } 170 + 171 + static void armada_ap806_init_sensor(struct platform_device *pdev, 172 + struct armada_thermal_priv *priv) 173 + { 174 + u32 reg; 175 + 176 + reg = readl_relaxed(priv->control0); 177 + reg &= ~CONTROL0_TSEN_RESET; 178 + reg |= CONTROL0_TSEN_START | CONTROL0_TSEN_ENABLE; 179 + writel(reg, priv->control0); 180 + 181 + /* Wait the sensors to be valid or the core will warn the user */ 182 + armada_wait_sensor_validity(priv); 171 183 } 172 184 173 185 static bool armada_is_valid(struct armada_thermal_priv *priv) 174 186 { 175 - unsigned long reg = readl_relaxed(priv->sensor); 187 + u32 reg = readl_relaxed(priv->status); 176 188 177 - return (reg >> priv->data->is_valid_shift) & THERMAL_VALID_MASK; 189 + return reg & priv->data->is_valid_bit; 178 190 } 179 191 180 192 static int armada_get_temp(struct thermal_zone_device *thermal, 181 - int *temp) 193 + int *temp) 182 194 { 183 195 struct armada_thermal_priv *priv = thermal->devdata; 184 - unsigned long reg; 185 - unsigned long m, b, div; 196 + u32 reg, div; 197 + s64 sample, b, m; 186 198 187 199 /* Valid check */ 188 200 if (priv->data->is_valid && !priv->data->is_valid(priv)) { ··· 226 168 return -EIO; 227 169 } 228 170 229 - reg = readl_relaxed(priv->sensor); 171 + reg = readl_relaxed(priv->status); 230 172 reg = (reg >> priv->data->temp_shift) & priv->data->temp_mask; 173 + if (priv->data->signed_sample) 174 + /* The most significant bit is the sign bit */ 175 + sample = sign_extend32(reg, fls(priv->data->temp_mask) - 1); 176 + else 177 + sample = reg; 231 178 232 179 /* Get formula coeficients */ 233 180 b = priv->data->coef_b; ··· 240 177 div = priv->data->coef_div; 241 178 242 179 if (priv->data->inverted) 243 - *temp = ((m * reg) - b) / div; 180 + *temp = div_s64((m * sample) - b, div); 244 181 else 245 - *temp = (b - (m * reg)) / div; 182 + *temp = div_s64(b - (m * sample), div); 183 + 246 184 return 0; 247 185 } 248 186 ··· 255 191 .init_sensor = armadaxp_init_sensor, 256 192 .temp_shift = 10, 257 193 .temp_mask = 0x1ff, 258 - .coef_b = 3153000000UL, 259 - .coef_m = 10000000UL, 194 + .coef_b = 3153000000ULL, 195 + .coef_m = 10000000ULL, 260 196 .coef_div = 13825, 261 197 }; 262 198 263 199 static const struct armada_thermal_data armada370_data = { 264 200 .is_valid = armada_is_valid, 265 201 .init_sensor = armada370_init_sensor, 266 - .is_valid_shift = 9, 202 + .is_valid_bit = BIT(9), 267 203 .temp_shift = 10, 268 204 .temp_mask = 0x1ff, 269 - .coef_b = 3153000000UL, 270 - .coef_m = 10000000UL, 205 + .coef_b = 3153000000ULL, 206 + .coef_m = 10000000ULL, 271 207 .coef_div = 13825, 272 208 }; 273 209 274 210 static const struct armada_thermal_data armada375_data = { 275 211 .is_valid = armada_is_valid, 276 212 .init_sensor = armada375_init_sensor, 277 - .is_valid_shift = 10, 213 + .is_valid_bit = BIT(10), 278 214 .temp_shift = 0, 279 215 .temp_mask = 0x1ff, 280 - .coef_b = 3171900000UL, 281 - .coef_m = 10000000UL, 216 + .coef_b = 3171900000ULL, 217 + .coef_m = 10000000ULL, 282 218 .coef_div = 13616, 219 + .needs_control0 = true, 283 220 }; 284 221 285 222 static const struct armada_thermal_data armada380_data = { 286 223 .is_valid = armada_is_valid, 287 224 .init_sensor = armada380_init_sensor, 288 - .is_valid_shift = 10, 225 + .is_valid_bit = BIT(10), 289 226 .temp_shift = 0, 290 227 .temp_mask = 0x3ff, 291 - .coef_b = 1172499100UL, 292 - .coef_m = 2000096UL, 228 + .coef_b = 1172499100ULL, 229 + .coef_m = 2000096ULL, 293 230 .coef_div = 4201, 294 231 .inverted = true, 232 + }; 233 + 234 + static const struct armada_thermal_data armada_ap806_data = { 235 + .is_valid = armada_is_valid, 236 + .init_sensor = armada_ap806_init_sensor, 237 + .is_valid_bit = BIT(16), 238 + .temp_shift = 0, 239 + .temp_mask = 0x3ff, 240 + .coef_b = -150000LL, 241 + .coef_m = 423ULL, 242 + .coef_div = 1, 243 + .inverted = true, 244 + .signed_sample = true, 245 + .needs_control0 = true, 246 + }; 247 + 248 + static const struct armada_thermal_data armada_cp110_data = { 249 + .is_valid = armada_is_valid, 250 + .init_sensor = armada380_init_sensor, 251 + .is_valid_bit = BIT(10), 252 + .temp_shift = 0, 253 + .temp_mask = 0x3ff, 254 + .coef_b = 1172499100ULL, 255 + .coef_m = 2000096ULL, 256 + .coef_div = 4201, 257 + .inverted = true, 258 + .needs_control0 = true, 295 259 }; 296 260 297 261 static const struct of_device_id armada_thermal_id_table[] = { ··· 340 248 .data = &armada380_data, 341 249 }, 342 250 { 251 + .compatible = "marvell,armada-ap806-thermal", 252 + .data = &armada_ap806_data, 253 + }, 254 + { 255 + .compatible = "marvell,armada-cp110-thermal", 256 + .data = &armada_cp110_data, 257 + }, 258 + { 343 259 /* sentinel */ 344 260 }, 345 261 }; ··· 355 255 356 256 static int armada_thermal_probe(struct platform_device *pdev) 357 257 { 258 + void __iomem *control = NULL; 358 259 struct thermal_zone_device *thermal; 359 260 const struct of_device_id *match; 360 261 struct armada_thermal_priv *priv; ··· 370 269 return -ENOMEM; 371 270 372 271 res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 373 - priv->sensor = devm_ioremap_resource(&pdev->dev, res); 374 - if (IS_ERR(priv->sensor)) 375 - return PTR_ERR(priv->sensor); 272 + priv->status = devm_ioremap_resource(&pdev->dev, res); 273 + if (IS_ERR(priv->status)) 274 + return PTR_ERR(priv->status); 376 275 377 276 res = platform_get_resource(pdev, IORESOURCE_MEM, 1); 378 - priv->control = devm_ioremap_resource(&pdev->dev, res); 379 - if (IS_ERR(priv->control)) 380 - return PTR_ERR(priv->control); 277 + control = devm_ioremap_resource(&pdev->dev, res); 278 + if (IS_ERR(control)) 279 + return PTR_ERR(control); 381 280 382 281 priv->data = (struct armada_thermal_data *)match->data; 282 + 283 + /* 284 + * Legacy DT bindings only described "control1" register (also referred 285 + * as "control MSB" on old documentation). New bindings cover 286 + * "control0/control LSB" and "control1/control MSB" registers within 287 + * the same resource, which is then of size 8 instead of 4. 288 + */ 289 + if (resource_size(res) == LEGACY_CONTROL_MEM_LEN) { 290 + /* ->control0 unavailable in this configuration */ 291 + if (priv->data->needs_control0) { 292 + dev_err(&pdev->dev, "No access to control0 register\n"); 293 + return -EINVAL; 294 + } 295 + 296 + priv->control1 = control + LEGACY_CONTROL1_OFFSET; 297 + } else { 298 + priv->control0 = control + CONTROL0_OFFSET; 299 + priv->control1 = control + CONTROL1_OFFSET; 300 + } 301 + 383 302 priv->data->init_sensor(pdev, priv); 384 303 385 - thermal = thermal_zone_device_register("armada_thermal", 0, 0, 386 - priv, &ops, NULL, 0, 0); 304 + thermal = thermal_zone_device_register(dev_name(&pdev->dev), 0, 0, priv, 305 + &ops, NULL, 0, 0); 387 306 if (IS_ERR(thermal)) { 388 307 dev_err(&pdev->dev, 389 308 "Failed to register thermal zone device\n"); ··· 437 316 module_platform_driver(armada_thermal_driver); 438 317 439 318 MODULE_AUTHOR("Ezequiel Garcia <ezequiel.garcia@free-electrons.com>"); 440 - MODULE_DESCRIPTION("Armada 370/XP thermal driver"); 319 + MODULE_DESCRIPTION("Marvell EBU Armada SoCs thermal driver"); 441 320 MODULE_LICENSE("GPL v2");
+1 -1
drivers/thermal/hisi_thermal.c
··· 527 527 static int hisi_thermal_probe(struct platform_device *pdev) 528 528 { 529 529 struct hisi_thermal_data *data; 530 - int const (*platform_probe)(struct hisi_thermal_data *); 530 + int (*platform_probe)(struct hisi_thermal_data *); 531 531 struct device *dev = &pdev->dev; 532 532 int ret; 533 533
+33 -41
drivers/thermal/imx_thermal.c
··· 70 70 #define IMX_POLLING_DELAY 2000 /* millisecond */ 71 71 #define IMX_PASSIVE_DELAY 1000 72 72 73 - #define FACTOR0 10000000 74 - #define FACTOR1 15976 75 - #define FACTOR2 4297157 76 - 77 73 #define TEMPMON_IMX6Q 1 78 74 #define TEMPMON_IMX6SX 2 79 75 ··· 343 347 .set_trip_temp = imx_set_trip_temp, 344 348 }; 345 349 346 - static int imx_init_calib(struct platform_device *pdev, u32 val) 350 + static int imx_init_calib(struct platform_device *pdev, u32 ocotp_ana1) 347 351 { 348 352 struct imx_thermal_data *data = platform_get_drvdata(pdev); 349 - int t1, n1; 353 + int n1; 350 354 u64 temp64; 351 355 352 - if (val == 0 || val == ~0) { 356 + if (ocotp_ana1 == 0 || ocotp_ana1 == ~0) { 353 357 dev_err(&pdev->dev, "invalid sensor calibration data\n"); 354 358 return -EINVAL; 355 359 } 356 360 357 361 /* 358 - * Sensor data layout: 359 - * [31:20] - sensor value @ 25C 360 - * Use universal formula now and only need sensor value @ 25C 361 - * slope = 0.4297157 - (0.0015976 * 25C fuse) 362 + * The sensor is calibrated at 25 °C (aka T1) and the value measured 363 + * (aka N1) at this temperature is provided in bits [31:20] in the 364 + * i.MX's OCOTP value ANA1. 365 + * To find the actual temperature T, the following formula has to be used 366 + * when reading value n from the sensor: 367 + * 368 + * T = T1 + (N - N1) / (0.4148468 - 0.0015423 * N1) °C + 3.580661 °C 369 + * = [T1' - N1 / (0.4148468 - 0.0015423 * N1) °C] + N / (0.4148468 - 0.0015423 * N1) °C 370 + * = [T1' + N1 / (0.0015423 * N1 - 0.4148468) °C] - N / (0.0015423 * N1 - 0.4148468) °C 371 + * = c2 - c1 * N 372 + * 373 + * with 374 + * 375 + * T1' = 28.580661 °C 376 + * c1 = 1 / (0.0015423 * N1 - 0.4297157) °C 377 + * c2 = T1' + N1 / (0.0015423 * N1 - 0.4148468) °C 378 + * = T1' + N1 * c1 362 379 */ 363 - n1 = val >> 20; 364 - t1 = 25; /* t1 always 25C */ 380 + n1 = ocotp_ana1 >> 20; 365 381 366 - /* 367 - * Derived from linear interpolation: 368 - * slope = 0.4297157 - (0.0015976 * 25C fuse) 369 - * slope = (FACTOR2 - FACTOR1 * n1) / FACTOR0 370 - * (Nmeas - n1) / (Tmeas - t1) = slope 371 - * We want to reduce this down to the minimum computation necessary 372 - * for each temperature read. Also, we want Tmeas in millicelsius 373 - * and we don't want to lose precision from integer division. So... 374 - * Tmeas = (Nmeas - n1) / slope + t1 375 - * milli_Tmeas = 1000 * (Nmeas - n1) / slope + 1000 * t1 376 - * milli_Tmeas = -1000 * (n1 - Nmeas) / slope + 1000 * t1 377 - * Let constant c1 = (-1000 / slope) 378 - * milli_Tmeas = (n1 - Nmeas) * c1 + 1000 * t1 379 - * Let constant c2 = n1 *c1 + 1000 * t1 380 - * milli_Tmeas = c2 - Nmeas * c1 381 - */ 382 - temp64 = FACTOR0; 383 - temp64 *= 1000; 384 - do_div(temp64, FACTOR1 * n1 - FACTOR2); 382 + temp64 = 10000000; /* use 10^7 as fixed point constant for values in formula */ 383 + temp64 *= 1000; /* to get result in °mC */ 384 + do_div(temp64, 15423 * n1 - 4148468); 385 385 data->c1 = temp64; 386 - data->c2 = n1 * data->c1 + 1000 * t1; 386 + data->c2 = n1 * data->c1 + 28581; 387 387 388 388 return 0; 389 389 } 390 390 391 - static void imx_init_temp_grade(struct platform_device *pdev, u32 val) 391 + static void imx_init_temp_grade(struct platform_device *pdev, u32 ocotp_mem0) 392 392 { 393 393 struct imx_thermal_data *data = platform_get_drvdata(pdev); 394 394 395 395 /* The maximum die temp is specified by the Temperature Grade */ 396 - switch ((val >> 6) & 0x3) { 397 - case 0: /* Commercial (0 to 95C) */ 396 + switch ((ocotp_mem0 >> 6) & 0x3) { 397 + case 0: /* Commercial (0 to 95 °C) */ 398 398 data->temp_grade = "Commercial"; 399 399 data->temp_max = 95000; 400 400 break; 401 - case 1: /* Extended Commercial (-20 to 105C) */ 401 + case 1: /* Extended Commercial (-20 °C to 105 °C) */ 402 402 data->temp_grade = "Extended Commercial"; 403 403 data->temp_max = 105000; 404 404 break; 405 - case 2: /* Industrial (-40 to 105C) */ 405 + case 2: /* Industrial (-40 °C to 105 °C) */ 406 406 data->temp_grade = "Industrial"; 407 407 data->temp_max = 105000; 408 408 break; 409 - case 3: /* Automotive (-40 to 125C) */ 409 + case 3: /* Automotive (-40 °C to 125 °C) */ 410 410 data->temp_grade = "Automotive"; 411 411 data->temp_max = 125000; 412 412 break; 413 413 } 414 414 415 415 /* 416 - * Set the critical trip point at 5C under max 417 - * Set the passive trip point at 10C under max (can change via sysfs) 416 + * Set the critical trip point at 5 °C under max 417 + * Set the passive trip point at 10 °C under max (changeable via sysfs) 418 418 */ 419 419 data->temp_critical = data->temp_max - (1000 * 5); 420 420 data->temp_passive = data->temp_max - (1000 * 10);
+8 -4
drivers/thermal/int340x_thermal/int3400_thermal.c
··· 211 211 thermal_prop); 212 212 break; 213 213 default: 214 - dev_err(&priv->adev->dev, "Unsupported event [0x%x]\n", event); 214 + /* Ignore unknown notification codes sent to INT3400 device */ 215 215 break; 216 216 } 217 217 } ··· 319 319 320 320 result = sysfs_create_group(&pdev->dev.kobj, &uuid_attribute_group); 321 321 if (result) 322 - goto free_zone; 322 + goto free_rel_misc; 323 323 324 324 result = acpi_install_notify_handler( 325 325 priv->adev->handle, ACPI_DEVICE_NOTIFY, int3400_notify, 326 326 (void *)priv); 327 327 if (result) 328 - goto free_zone; 328 + goto free_sysfs; 329 329 330 330 return 0; 331 331 332 - free_zone: 332 + free_sysfs: 333 + sysfs_remove_group(&pdev->dev.kobj, &uuid_attribute_group); 334 + free_rel_misc: 335 + if (!priv->rel_misc_dev_res) 336 + acpi_thermal_rel_misc_device_remove(priv->adev->handle); 333 337 thermal_zone_device_unregister(priv->thermal); 334 338 free_art_trt: 335 339 kfree(priv->trts);
+1 -8
drivers/thermal/mtk_thermal.c
··· 32 32 #include <linux/types.h> 33 33 34 34 /* AUXADC Registers */ 35 - #define AUXADC_CON0_V 0x000 36 - #define AUXADC_CON1_V 0x004 37 35 #define AUXADC_CON1_SET_V 0x008 38 36 #define AUXADC_CON1_CLR_V 0x00c 39 37 #define AUXADC_CON2_V 0x010 40 38 #define AUXADC_DATA(channel) (0x14 + (channel) * 4) 41 - #define AUXADC_MISC_V 0x094 42 - 43 - #define AUXADC_CON1_CHANNEL(x) BIT(x) 44 39 45 40 #define APMIXED_SYS_TS_CON1 0x604 46 41 ··· 152 157 153 158 /* The number of sensing points per bank */ 154 159 #define MT2712_NUM_SENSORS_PER_ZONE 4 155 - 156 - #define THERMAL_NAME "mtk-thermal" 157 160 158 161 struct mtk_thermal; 159 162 ··· 758 765 .probe = mtk_thermal_probe, 759 766 .remove = mtk_thermal_remove, 760 767 .driver = { 761 - .name = THERMAL_NAME, 768 + .name = "mtk-thermal", 762 769 .of_match_table = mtk_thermal_of_match, 763 770 }, 764 771 };
-1
drivers/thermal/of-thermal.c
··· 30 30 #include <linux/err.h> 31 31 #include <linux/export.h> 32 32 #include <linux/string.h> 33 - #include <linux/thermal.h> 34 33 35 34 #include "thermal_core.h" 36 35
+2
drivers/thermal/power_allocator.c
··· 523 523 struct thermal_instance *instance; 524 524 struct power_allocator_params *params = tz->governor_data; 525 525 526 + mutex_lock(&tz->lock); 526 527 list_for_each_entry(instance, &tz->thermal_instances, tz_node) { 527 528 if ((instance->trip != params->trip_max_desired_temperature) || 528 529 (!cdev_is_power_actor(instance->cdev))) ··· 535 534 mutex_unlock(&instance->cdev->lock); 536 535 thermal_cdev_update(instance->cdev); 537 536 } 537 + mutex_unlock(&tz->lock); 538 538 } 539 539 540 540 /**
+47 -56
drivers/thermal/tegra/soctherm.c
··· 341 341 return 0; 342 342 } 343 343 344 - static int 345 - thermtrip_program(struct device *dev, const struct tegra_tsensor_group *sg, 346 - int trip_temp); 347 - static int 348 - throttrip_program(struct device *dev, const struct tegra_tsensor_group *sg, 349 - struct soctherm_throt_cfg *stc, int trip_temp); 350 - static struct soctherm_throt_cfg * 351 - find_throttle_cfg_by_name(struct tegra_soctherm *ts, const char *name); 352 - 353 - static int tegra_thermctl_set_trip_temp(void *data, int trip, int temp) 354 - { 355 - struct tegra_thermctl_zone *zone = data; 356 - struct thermal_zone_device *tz = zone->tz; 357 - struct tegra_soctherm *ts = zone->ts; 358 - const struct tegra_tsensor_group *sg = zone->sg; 359 - struct device *dev = zone->dev; 360 - enum thermal_trip_type type; 361 - int ret; 362 - 363 - if (!tz) 364 - return -EINVAL; 365 - 366 - ret = tz->ops->get_trip_type(tz, trip, &type); 367 - if (ret) 368 - return ret; 369 - 370 - if (type == THERMAL_TRIP_CRITICAL) { 371 - return thermtrip_program(dev, sg, temp); 372 - } else if (type == THERMAL_TRIP_HOT) { 373 - int i; 374 - 375 - for (i = 0; i < THROTTLE_SIZE; i++) { 376 - struct thermal_cooling_device *cdev; 377 - struct soctherm_throt_cfg *stc; 378 - 379 - if (!ts->throt_cfgs[i].init) 380 - continue; 381 - 382 - cdev = ts->throt_cfgs[i].cdev; 383 - if (get_thermal_instance(tz, cdev, trip)) 384 - stc = find_throttle_cfg_by_name(ts, cdev->type); 385 - else 386 - continue; 387 - 388 - return throttrip_program(dev, sg, stc, temp); 389 - } 390 - } 391 - 392 - return 0; 393 - } 394 - 395 - static const struct thermal_zone_of_device_ops tegra_of_thermal_ops = { 396 - .get_temp = tegra_thermctl_get_temp, 397 - .set_trip_temp = tegra_thermctl_set_trip_temp, 398 - }; 399 - 400 344 /** 401 345 * enforce_temp_range() - check and enforce temperature range [min, max] 402 346 * @trip_temp: the trip temperature to check ··· 470 526 471 527 return NULL; 472 528 } 529 + 530 + static int tegra_thermctl_set_trip_temp(void *data, int trip, int temp) 531 + { 532 + struct tegra_thermctl_zone *zone = data; 533 + struct thermal_zone_device *tz = zone->tz; 534 + struct tegra_soctherm *ts = zone->ts; 535 + const struct tegra_tsensor_group *sg = zone->sg; 536 + struct device *dev = zone->dev; 537 + enum thermal_trip_type type; 538 + int ret; 539 + 540 + if (!tz) 541 + return -EINVAL; 542 + 543 + ret = tz->ops->get_trip_type(tz, trip, &type); 544 + if (ret) 545 + return ret; 546 + 547 + if (type == THERMAL_TRIP_CRITICAL) { 548 + return thermtrip_program(dev, sg, temp); 549 + } else if (type == THERMAL_TRIP_HOT) { 550 + int i; 551 + 552 + for (i = 0; i < THROTTLE_SIZE; i++) { 553 + struct thermal_cooling_device *cdev; 554 + struct soctherm_throt_cfg *stc; 555 + 556 + if (!ts->throt_cfgs[i].init) 557 + continue; 558 + 559 + cdev = ts->throt_cfgs[i].cdev; 560 + if (get_thermal_instance(tz, cdev, trip)) 561 + stc = find_throttle_cfg_by_name(ts, cdev->type); 562 + else 563 + continue; 564 + 565 + return throttrip_program(dev, sg, stc, temp); 566 + } 567 + } 568 + 569 + return 0; 570 + } 571 + 572 + static const struct thermal_zone_of_device_ops tegra_of_thermal_ops = { 573 + .get_temp = tegra_thermctl_get_temp, 574 + .set_trip_temp = tegra_thermctl_set_trip_temp, 575 + }; 473 576 474 577 static int get_hot_temp(struct thermal_zone_device *tz, int *trip, int *temp) 475 578 {
+3 -17
drivers/thermal/thermal_hwmon.c
··· 59 59 static DEFINE_MUTEX(thermal_hwmon_list_lock); 60 60 61 61 static ssize_t 62 - name_show(struct device *dev, struct device_attribute *attr, char *buf) 63 - { 64 - struct thermal_hwmon_device *hwmon = dev_get_drvdata(dev); 65 - return sprintf(buf, "%s\n", hwmon->type); 66 - } 67 - static DEVICE_ATTR_RO(name); 68 - 69 - static ssize_t 70 62 temp_input_show(struct device *dev, struct device_attribute *attr, char *buf) 71 63 { 72 64 int temperature; ··· 157 165 158 166 INIT_LIST_HEAD(&hwmon->tz_list); 159 167 strlcpy(hwmon->type, tz->type, THERMAL_NAME_LENGTH); 160 - hwmon->device = hwmon_device_register(NULL); 168 + hwmon->device = hwmon_device_register_with_info(NULL, hwmon->type, 169 + hwmon, NULL, NULL); 161 170 if (IS_ERR(hwmon->device)) { 162 171 result = PTR_ERR(hwmon->device); 163 172 goto free_mem; 164 173 } 165 - dev_set_drvdata(hwmon->device, hwmon); 166 - result = device_create_file(hwmon->device, &dev_attr_name); 167 - if (result) 168 - goto free_mem; 169 174 170 175 register_sys_interface: 171 176 temp = kzalloc(sizeof(*temp), GFP_KERNEL); ··· 211 222 free_temp_mem: 212 223 kfree(temp); 213 224 unregister_name: 214 - if (new_hwmon_device) { 215 - device_remove_file(hwmon->device, &dev_attr_name); 225 + if (new_hwmon_device) 216 226 hwmon_device_unregister(hwmon->device); 217 - } 218 227 free_mem: 219 228 if (new_hwmon_device) 220 229 kfree(hwmon); ··· 254 267 list_del(&hwmon->node); 255 268 mutex_unlock(&thermal_hwmon_list_lock); 256 269 257 - device_remove_file(hwmon->device, &dev_attr_name); 258 270 hwmon_device_unregister(hwmon->device); 259 271 kfree(hwmon); 260 272 }
+2 -2
drivers/thermal/x86_pkg_temp_thermal.c
··· 96 96 return -ENOENT; 97 97 98 98 d = debugfs_create_u32("pkg_thres_interrupt", S_IRUGO, debugfs, 99 - (u32 *)&pkg_interrupt_cnt); 99 + &pkg_interrupt_cnt); 100 100 if (!d) 101 101 goto err_out; 102 102 103 103 d = debugfs_create_u32("pkg_thres_work", S_IRUGO, debugfs, 104 - (u32 *)&pkg_work_cnt); 104 + &pkg_work_cnt); 105 105 if (!d) 106 106 goto err_out; 107 107