* [PATCH v3 00/11] Support cooling device with ID in the OF
@ 2026-05-26 14:08 Daniel Lezcano
2026-05-26 14:08 ` [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register() Daniel Lezcano
` (10 more replies)
0 siblings, 11 replies; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Ultra short description. DT Cooling device description:
Old: <&mycdev min max>
New: <&mycdev min max> OR/AND <&mycdev id min max>
Based on
https://git.kernel.org/pub/scm/linux/kernel/git/thermal/linux.git/log/?h=thermal/linux-next
A cooling device can be a single cooling device or a cooling device
controller with multiple cooling devices attached to it.
The thermal framework builds a connection between a cooling device and
a thermal zone when there is a trip point to be mitigated by the
cooling device. In the Linux kernel thermal semantic, the action of
connecting the cooling device and the thermal zone is called a
binding.
The description of the aforementioned connection depends on the
firmware definition and in our case it is through the device tree. The
cooling map describes this connection.
How is it done ?
For a single cooling device, the DT describes:
* A cooling device:
mycooling_device {
...
};
* A cooling map in a thermal zone
mythermal_zone {
...
cooling-maps {
map0 {
...
cooling-device = <&mycooling_device min max>;
...
};
}
...
};
For a cooling device controller with multiple cooling devices
attached, the DT describes:
* A cooling device controller:
mycooling_device_ctrl {
mycooling_device1 {
...
};
mycooling_device2 {
...
};
...
mycooling_deviceN {
...
};
};
* A cooling map in a thermal zone
mythermal_zone {
...
cooling-maps {
map0 {
...
cooling-device = <&mycooling_device1 min max>;
...
};
}
...
};
When the cooling device "mycooling_device" is registered, then the
binding function will browse all the cooling maps and matches the node
device pointer to do the association (the pĥandle in the cooling map
vs the cooling device node).
That is how the connection between the cooling device and the thermal
zone is done.
DT maintainers consider the above description with child nodes is
incorrect if a child node doesn't have its own bindings as explained
in the documentation [1].
Gaurav Kohli posted a series to support the QMI TMD (Qualcomm
Messaging Interface based Thermal Mitigation Devices) [2]. This device
is a dedicated, centralized cooling device controller managing a set
of cooling devices.
Because of the above restrictions with child nodes there is no DT
bindings allowing to do the connection between the cooling device
inside the cooling device controller and a thermal zone.
A QMI TMD is not a standalone cooling device neither a multiple
cooling devices with their own DT description.
For this reason, the proposed changes with child nodes has been
rejected [3].
As a solution, it has been proposed to fold all these child nodes into
an array and add an id in the cooling maps to identify the cooling
device entry in the controller node [4].
Given the thermal zone has the same mechanism [5], that is a phandle
to a sensor node and an sensor specifier. The proposed approach makes
sense as it is consistent with the thermal zone description.
This series provides a cleanup around the usage of the OF code which
is interleaved with non-OF code. The OF and the non-OF code are
separated and remain self-encapsulated.
Then the function to register a cooling device is renamed to reflect
the legacy usage and a new function is introduced with the id
parameter.
Finally, the DT bindings is updated with the new format and the
thermal OF is changed to handle the new DT bindings.
Given the trivial changes impacting the files outside of the thermal
framework, this series is designed to have all changes going through
the thermal tree.
Thanks!
[1] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/devicetree/bindings/writing-bindings.rst
[2] https://lore.kernel.org/all/20260127155722.2797783-1-gaurav.kohli@oss.qualcomm.com/
[3] https://lore.kernel.org/all/546faeda-d896-403c-a449-5c9b0cd7159e@kernel.org/
[4] https://lore.kernel.org/all/74f59ef0-ead7-483f-a80e-a3da2f6ebcdb@oss.qualcomm.com/
[5] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/devicetree/bindings/thermal/thermal-zones.yaml#n99
---
Changelog:
- V4
- Reworked splitted functions to register a cooling device and
merged separately
- V3
- Reordered and reworked the patches to be git bisect safe
- Reworked devm usage by using a more adequate function doing the
same as the group of calls to devm*
- Pass an init callback instead of moving
thermal_cooling_device_init_complete() out of the function and
calling it in different places
- Sent separetely changes to the tegra soctherm driver
- V2
- Added stubs for OF functions in order to prevent to break the git
bisectability compilation
- Added missing call to thermal_cooling_device_init_complete() in
devm_thermal_of_cooling_device_register()
- Fixed assymetry in devm_ calls for the tegra/soctherm() driver
- Fixed kernel documentation for API changes
- Added missing static inline for a API stub
- Hardened the test with two or three arguments in the cooling spec
- Narrowed const: 2 strict in pwm-fan
---
Daniel Lezcano (9):
thermal/core: Introduce non-OF thermal_cooling_device_register()
thermal/core: Add devm_thermal_cooling_device_register()
hwmon: Use non-OF thermal cooling device registration API
thermal/core: Make cooling device OF node conditional on
CONFIG_THERMAL_OF
thermal/of: Move cooling device OF helpers out of thermal core
thermal/of: Rename the devm_thermal_of_cooling_device_register()
function
thermal/of: Add cooling device ID support
thermal/of: Pass cdev_id and introduce devm registration helper
thermal/of: Support cooling device ID in cooling-spec
Gaurav Kohli (1):
dt-bindings: thermal: cooling-devices: Update support for 3 cells
cooling device
.../devicetree/bindings/hwmon/pwm-fan.yaml | 3 +-
.../thermal/thermal-cooling-devices.yaml | 8 +-
.../bindings/thermal/thermal-zones.yaml | 3 +-
drivers/gpu/drm/etnaviv/etnaviv_gpu.c | 5 +-
drivers/hwmon/amc6821.c | 2 +-
drivers/hwmon/aspeed-pwm-tacho.c | 5 +-
drivers/hwmon/cros_ec_hwmon.c | 4 +-
drivers/hwmon/dell-smm-hwmon.c | 4 +-
drivers/hwmon/emc2305.c | 6 +-
drivers/hwmon/gpio-fan.c | 6 +-
drivers/hwmon/max6650.c | 6 +-
drivers/hwmon/mlxreg-fan.c | 4 +-
drivers/hwmon/npcm750-pwm-fan.c | 6 +-
drivers/hwmon/pwm-fan.c | 5 +-
drivers/hwmon/qnap-mcu-hwmon.c | 6 +-
drivers/hwmon/tc654.c | 5 +-
drivers/memory/tegra/tegra210-emc-core.c | 4 +-
drivers/soc/qcom/qcom_aoss.c | 2 +-
drivers/thermal/cpufreq_cooling.c | 2 +-
drivers/thermal/cpuidle_cooling.c | 2 +-
drivers/thermal/devfreq_cooling.c | 2 +-
drivers/thermal/khadas_mcu_fan.c | 7 +-
drivers/thermal/tegra/soctherm.c | 6 +-
drivers/thermal/thermal_core.c | 85 ++--------
drivers/thermal/thermal_core.h | 5 +
drivers/thermal/thermal_of.c | 148 +++++++++++++++++-
include/linux/thermal.h | 69 +++++---
27 files changed, 273 insertions(+), 137 deletions(-)
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register()
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 9:47 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register() Daniel Lezcano
` (9 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Split the cooling device registration API into OF and non-OF variants.
Introduce thermal_cooling_device_register() for non-device-tree users
and rework thermal_of_cooling_device_register() to use the new
alloc/add split.
This removes the need for the internal __thermal_cooling_device_register()
helper and makes the separation between OF and non-OF users explicit.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/thermal/thermal_core.c | 60 ++++++++++++++--------------------
1 file changed, 24 insertions(+), 36 deletions(-)
diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
index db01361569d7..0b3db889d60d 100644
--- a/drivers/thermal/thermal_core.c
+++ b/drivers/thermal/thermal_core.c
@@ -1059,8 +1059,7 @@ static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void
}
/**
- * __thermal_cooling_device_register() - register a new thermal cooling device
- * @np: a pointer to a device tree node.
+ * thermal_cooling_device_register() - register a new thermal cooling device
* @type: the thermal cooling device type.
* @devdata: device private data.
* @ops: standard thermal cooling devices callbacks.
@@ -1068,16 +1067,13 @@ static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void
* This interface function adds a new thermal cooling device (fan/processor/...)
* to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
* to all the thermal zone devices registered at the same time.
- * It also gives the opportunity to link the cooling device to a device tree
- * node, so that it can be bound to a thermal zone created out of device tree.
*
* Return: a pointer to the created struct thermal_cooling_device or an
* ERR_PTR. Caller must check return value with IS_ERR*() helpers.
*/
-static struct thermal_cooling_device *
-__thermal_cooling_device_register(struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
+struct thermal_cooling_device *
+thermal_cooling_device_register(const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
{
struct thermal_cooling_device *cdev;
int ret;
@@ -1086,34 +1082,12 @@ __thermal_cooling_device_register(struct device_node *np,
if (IS_ERR(cdev))
return cdev;
- cdev->np = np;
-
ret = thermal_cooling_device_add(cdev, devdata);
if (ret)
return ERR_PTR(ret);
return cdev;
}
-
-/**
- * thermal_cooling_device_register() - register a new thermal cooling device
- * @type: the thermal cooling device type.
- * @devdata: device private data.
- * @ops: standard thermal cooling devices callbacks.
- *
- * This interface function adds a new thermal cooling device (fan/processor/...)
- * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
- * to all the thermal zone devices registered at the same time.
- *
- * Return: a pointer to the created struct thermal_cooling_device or an
- * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
- */
-struct thermal_cooling_device *
-thermal_cooling_device_register(const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
-{
- return __thermal_cooling_device_register(NULL, type, devdata, ops);
-}
EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
/**
@@ -1121,22 +1095,36 @@ EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
* @np: a pointer to a device tree node.
* @type: the thermal cooling device type.
* @devdata: device private data.
- * @ops: standard thermal cooling devices callbacks.
+ * @ops: standard thermal cooling devices callbacks.
*
- * This function will register a cooling device with device tree node reference.
* This interface function adds a new thermal cooling device (fan/processor/...)
* to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
* to all the thermal zone devices registered at the same time.
+ * It also gives the opportunity to link the cooling device to a device tree
+ * node, so that it can be bound to a thermal zone created out of device tree.
*
* Return: a pointer to the created struct thermal_cooling_device or an
* ERR_PTR. Caller must check return value with IS_ERR*() helpers.
*/
struct thermal_cooling_device *
thermal_of_cooling_device_register(struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
{
- return __thermal_cooling_device_register(np, type, devdata, ops);
+ struct thermal_cooling_device *cdev;
+ int ret;
+
+ cdev = thermal_cooling_device_alloc(type, ops);
+ if (IS_ERR(cdev))
+ return cdev;
+
+ cdev->np = np;
+
+ ret = thermal_cooling_device_add(cdev, devdata);
+ if (ret)
+ return ERR_PTR(ret);
+
+ return cdev;
}
EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
@@ -1173,7 +1161,7 @@ devm_thermal_of_cooling_device_register(struct device *dev,
struct thermal_cooling_device *cdev;
int ret;
- cdev = __thermal_cooling_device_register(np, type, devdata, ops);
+ cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
if (IS_ERR(cdev))
return cdev;
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register()
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
2026-05-26 14:08 ` [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register() Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 12:55 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API Daniel Lezcano
` (8 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Introduce a device-managed variant of the non-OF cooling device
registration API.
This complements devm_thermal_of_cooling_device_register() and allows
non-device-tree users to register cooling devices with automatic
cleanup tied to the device lifecycle.
The helper relies on devm_add_action_or_reset() to release the cooling
device via thermal_cooling_device_release() on driver detach or probe
failure.
This keeps the API consistent across OF and non-OF users and avoids
manual cleanup in error paths.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/thermal/thermal_core.c | 35 ++++++++++++++++++++++++++++++++++
include/linux/thermal.h | 7 +++++--
2 files changed, 40 insertions(+), 2 deletions(-)
diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
index 0b3db889d60d..bb4fc3ff2ad5 100644
--- a/drivers/thermal/thermal_core.c
+++ b/drivers/thermal/thermal_core.c
@@ -1173,6 +1173,41 @@ devm_thermal_of_cooling_device_register(struct device *dev,
}
EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
+/**
+ * devm_thermal_cooling_device_register() - register a thermal cooling device
+ *
+ * @dev: a valid struct device pointer of a sensor device.
+ * @type: the thermal cooling device type.
+ * @devdata: device private data.
+ * @ops: standard thermal cooling devices callbacks.
+ *
+ * This function will register a cooling device. This interface
+ * function adds a new thermal cooling device (fan/processor/...) to
+ * /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind
+ * itself to all the thermal zone devices registered at the same time.
+ *
+ * Return: a pointer to the created struct thermal_cooling_device or an
+ * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
+ */
+struct thermal_cooling_device *
+devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ struct thermal_cooling_device *cdev;
+ int ret;
+
+ cdev = thermal_cooling_device_register(type, devdata, ops);
+ if (IS_ERR(cdev))
+ return cdev;
+
+ ret = devm_add_action_or_reset(dev, thermal_cooling_device_release, cdev);
+ if (ret)
+ return ERR_PTR(ret);
+
+ return cdev;
+}
+EXPORT_SYMBOL_GPL(devm_thermal_cooling_device_register);
+
static bool thermal_cooling_device_present(struct thermal_cooling_device *cdev)
{
struct thermal_cooling_device *pos = NULL;
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index 0ddc77aeeca2..fc3f4a098370 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -253,8 +253,11 @@ void thermal_zone_device_update(struct thermal_zone_device *,
struct thermal_cooling_device *thermal_cooling_device_register(const char *,
void *, const struct thermal_cooling_device_ops *);
struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np, const char *, void *,
- const struct thermal_cooling_device_ops *);
+devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
+struct thermal_cooling_device *
+thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
struct thermal_cooling_device *
devm_thermal_of_cooling_device_register(struct device *dev,
struct device_node *np,
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
2026-05-26 14:08 ` [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register() Daniel Lezcano
2026-05-26 14:08 ` [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register() Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 12:55 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF Daniel Lezcano
` (7 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon,
open list:CHROMEOS EC HARDWARE MONITORING
Some HWMON drivers register cooling devices using the OF helper
devm_thermal_of_cooling_device_register() with a NULL device node.
With the introduction of a dedicated non-OF registration API,
switch these users to devm_thermal_cooling_device_register()
to make the intent explicit and avoid relying on OF-specific helpers.
This is a pure refactoring with no functional change.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
Acked-by: Guenter Roeck <linux@roeck-us.net>
---
drivers/hwmon/cros_ec_hwmon.c | 4 ++--
drivers/hwmon/dell-smm-hwmon.c | 4 ++--
drivers/hwmon/mlxreg-fan.c | 4 ++--
3 files changed, 6 insertions(+), 6 deletions(-)
diff --git a/drivers/hwmon/cros_ec_hwmon.c b/drivers/hwmon/cros_ec_hwmon.c
index 6cf5ab0f4b73..77dd9f28962d 100644
--- a/drivers/hwmon/cros_ec_hwmon.c
+++ b/drivers/hwmon/cros_ec_hwmon.c
@@ -532,8 +532,8 @@ static void cros_ec_hwmon_register_fan_cooling_devices(struct device *dev,
cpriv->hwmon_priv = priv;
cpriv->index = i;
- cdev = devm_thermal_of_cooling_device_register(dev, NULL, type, cpriv,
- &cros_ec_thermal_cooling_ops);
+ cdev = devm_thermal_cooling_device_register(dev, type, cpriv,
+ &cros_ec_thermal_cooling_ops);
if (IS_ERR(cdev)) {
dev_warn(dev, "failed to register fan %zu as a cooling device: %pe\n", i,
cdev);
diff --git a/drivers/hwmon/dell-smm-hwmon.c b/drivers/hwmon/dell-smm-hwmon.c
index 038edffc1ac7..47b373ea6db4 100644
--- a/drivers/hwmon/dell-smm-hwmon.c
+++ b/drivers/hwmon/dell-smm-hwmon.c
@@ -1161,8 +1161,8 @@ static int dell_smm_init_cdev(struct device *dev, u8 fan_num)
if (cdata) {
cdata->fan_num = fan_num;
cdata->data = data;
- cdev = devm_thermal_of_cooling_device_register(dev, NULL, name, cdata,
- &dell_smm_cooling_ops);
+ cdev = devm_thermal_cooling_device_register(dev, name, cdata,
+ &dell_smm_cooling_ops);
if (IS_ERR(cdev)) {
devm_kfree(dev, cdata);
ret = PTR_ERR(cdev);
diff --git a/drivers/hwmon/mlxreg-fan.c b/drivers/hwmon/mlxreg-fan.c
index 137a90dd2075..860de6cfd8a4 100644
--- a/drivers/hwmon/mlxreg-fan.c
+++ b/drivers/hwmon/mlxreg-fan.c
@@ -583,8 +583,8 @@ static int mlxreg_fan_cooling_config(struct device *dev, struct mlxreg_fan *fan)
pwm->fan = fan;
/* Set minimal PWM speed. */
pwm->last_hwmon_state = MLXREG_FAN_PWM_DUTY2STATE(MLXREG_FAN_MIN_DUTY);
- pwm->cdev = devm_thermal_of_cooling_device_register(dev, NULL, mlxreg_fan_name[i],
- pwm, &mlxreg_fan_cooling_ops);
+ pwm->cdev = devm_thermal_cooling_device_register(dev, mlxreg_fan_name[i],
+ pwm, &mlxreg_fan_cooling_ops);
if (IS_ERR(pwm->cdev)) {
dev_err(dev, "Failed to register cooling device\n");
return PTR_ERR(pwm->cdev);
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (2 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 13:27 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core Daniel Lezcano
` (6 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
The device node pointer stored in struct thermal_cooling_device is
only used by the OF-specific thermal code to associate cooling devices
with thermal zones defined in device tree.
Now that OF and non-OF registration paths are separated and non-OF
users no longer rely on devm_thermal_of_cooling_device_register() with
a NULL device node, the np field is no longer required for non-OF
configurations.
Make this field conditional on CONFIG_THERMAL_OF to reduce memory
footprint and better reflect its usage.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
include/linux/thermal.h | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index fc3f4a098370..60e596e7d7ae 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -125,7 +125,6 @@ struct thermal_cooling_device {
const char *type;
unsigned long max_state;
struct device device;
- struct device_node *np;
void *devdata;
void *stats;
const struct thermal_cooling_device_ops *ops;
@@ -133,6 +132,9 @@ struct thermal_cooling_device {
struct mutex lock; /* protect thermal_instances list */
struct list_head thermal_instances;
struct list_head node;
+#ifdef CONFIG_THERMAL_OF
+ struct device_node *np;
+#endif
#ifdef CONFIG_THERMAL_DEBUGFS
struct thermal_debugfs *debugfs;
#endif
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (3 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 13:26 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function Daniel Lezcano
` (5 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
The functions:
- thermal_of_cooling_device_register()
- devm_thermal_of_cooling_device_register()
are specific to device tree usage but are currently implemented in
thermal_core.c.
Move them to thermal_of.c to better reflect the separation between
generic thermal core code and OF-specific logic.
This change is enabled by the recent split of the cooling device
registration into allocation and addition phases, allowing OF-specific
handling (such as device node assignment) to be isolated from the core.
No functional change intended.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/thermal/thermal_core.c | 80 +-------------------------------
drivers/thermal/thermal_core.h | 5 ++
drivers/thermal/thermal_of.c | 83 ++++++++++++++++++++++++++++++++++
include/linux/thermal.h | 49 ++++++++++++--------
4 files changed, 119 insertions(+), 98 deletions(-)
diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
index bb4fc3ff2ad5..28a20d4b475c 100644
--- a/drivers/thermal/thermal_core.c
+++ b/drivers/thermal/thermal_core.c
@@ -963,7 +963,7 @@ static void thermal_cdev_release(struct device *dev)
kfree(cdev);
}
-static struct thermal_cooling_device *
+struct thermal_cooling_device *
thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_device_ops *ops)
{
struct thermal_cooling_device *cdev;
@@ -1002,7 +1002,7 @@ thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_devi
return ERR_PTR(ret);
}
-static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata)
+int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata)
{
unsigned long current_state;
int ret;
@@ -1090,44 +1090,6 @@ thermal_cooling_device_register(const char *type, void *devdata,
}
EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
-/**
- * thermal_of_cooling_device_register() - register an OF thermal cooling device
- * @np: a pointer to a device tree node.
- * @type: the thermal cooling device type.
- * @devdata: device private data.
- * @ops: standard thermal cooling devices callbacks.
- *
- * This interface function adds a new thermal cooling device (fan/processor/...)
- * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
- * to all the thermal zone devices registered at the same time.
- * It also gives the opportunity to link the cooling device to a device tree
- * node, so that it can be bound to a thermal zone created out of device tree.
- *
- * Return: a pointer to the created struct thermal_cooling_device or an
- * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
- */
-struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
-{
- struct thermal_cooling_device *cdev;
- int ret;
-
- cdev = thermal_cooling_device_alloc(type, ops);
- if (IS_ERR(cdev))
- return cdev;
-
- cdev->np = np;
-
- ret = thermal_cooling_device_add(cdev, devdata);
- if (ret)
- return ERR_PTR(ret);
-
- return cdev;
-}
-EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
-
static void thermal_cooling_device_release(void *data)
{
struct thermal_cooling_device *cdev = data;
@@ -1135,44 +1097,6 @@ static void thermal_cooling_device_release(void *data)
thermal_cooling_device_unregister(cdev);
}
-/**
- * devm_thermal_of_cooling_device_register() - register an OF thermal cooling
- * device
- * @dev: a valid struct device pointer of a sensor device.
- * @np: a pointer to a device tree node.
- * @type: the thermal cooling device type.
- * @devdata: device private data.
- * @ops: standard thermal cooling devices callbacks.
- *
- * This function will register a cooling device with device tree node reference.
- * This interface function adds a new thermal cooling device (fan/processor/...)
- * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
- * to all the thermal zone devices registered at the same time.
- *
- * Return: a pointer to the created struct thermal_cooling_device or an
- * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
- */
-struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
-{
- struct thermal_cooling_device *cdev;
- int ret;
-
- cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
- if (IS_ERR(cdev))
- return cdev;
-
- ret = devm_add_action_or_reset(dev, thermal_cooling_device_release, cdev);
- if (ret)
- return ERR_PTR(ret);
-
- return cdev;
-}
-EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
-
/**
* devm_thermal_cooling_device_register() - register a thermal cooling device
*
diff --git a/drivers/thermal/thermal_core.h b/drivers/thermal/thermal_core.h
index 0acb7d9587ca..e98b0aa5aacc 100644
--- a/drivers/thermal/thermal_core.h
+++ b/drivers/thermal/thermal_core.h
@@ -267,6 +267,11 @@ void thermal_zone_device_critical_shutdown(struct thermal_zone_device *tz);
void thermal_governor_update_tz(struct thermal_zone_device *tz,
enum thermal_notify_event reason);
+struct thermal_cooling_device *
+thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_device_ops *ops);
+
+int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata);
+
/* Helpers */
#define for_each_trip_desc(__tz, __td) \
for (__td = __tz->trips; __td - __tz->trips < __tz->num_trips; __td++)
diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
index 75fb7663c507..8c49d449d43f 100644
--- a/drivers/thermal/thermal_of.c
+++ b/drivers/thermal/thermal_of.c
@@ -510,3 +510,86 @@ void devm_thermal_of_zone_unregister(struct device *dev, struct thermal_zone_dev
devm_thermal_of_zone_match, tz));
}
EXPORT_SYMBOL_GPL(devm_thermal_of_zone_unregister);
+
+/**
+ * thermal_of_cooling_device_register() - register an OF thermal cooling device
+ * @np: a pointer to a device tree node.
+ * @type: the thermal cooling device type.
+ * @devdata: device private data.
+ * @ops: standard thermal cooling devices callbacks.
+ *
+ * This interface function adds a new thermal cooling device (fan/processor/...)
+ * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
+ * to all the thermal zone devices registered at the same time.
+ * It also gives the opportunity to link the cooling device to a device tree
+ * node, so that it can be bound to a thermal zone created out of device tree.
+ *
+ * Return: a pointer to the created struct thermal_cooling_device or an
+ * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
+ */
+struct thermal_cooling_device *
+thermal_of_cooling_device_register(struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ struct thermal_cooling_device *cdev;
+ int ret;
+
+ cdev = thermal_cooling_device_alloc(type, ops);
+ if (IS_ERR(cdev))
+ return cdev;
+
+ cdev->np = np;
+
+ ret = thermal_cooling_device_add(cdev, devdata);
+ if (ret)
+ return ERR_PTR(ret);
+
+ return cdev;
+}
+EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
+
+static void thermal_of_cooling_device_release(void *data)
+{
+ struct thermal_cooling_device *cdev = data;
+
+ thermal_cooling_device_unregister(cdev);
+}
+
+/**
+ * devm_thermal_of_cooling_device_register() - register an OF thermal cooling
+ * device
+ * @dev: a valid struct device pointer of a sensor device.
+ * @np: a pointer to a device tree node.
+ * @type: the thermal cooling device type.
+ * @devdata: device private data.
+ * @ops: standard thermal cooling devices callbacks.
+ *
+ * This function will register a cooling device with device tree node reference.
+ * This interface function adds a new thermal cooling device (fan/processor/...)
+ * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
+ * to all the thermal zone devices registered at the same time.
+ *
+ * Return: a pointer to the created struct thermal_cooling_device or an
+ * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
+ */
+struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ struct thermal_cooling_device *cdev;
+ int ret;
+
+ cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
+ if (IS_ERR(cdev))
+ return cdev;
+
+ ret = devm_add_action_or_reset(dev, thermal_of_cooling_device_release, cdev);
+ if (ret)
+ return ERR_PTR(ret);
+
+ return cdev;
+}
+EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index 60e596e7d7ae..6d1862ac187f 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -200,6 +200,15 @@ struct thermal_zone_device *devm_thermal_of_zone_register(struct device *dev, in
void devm_thermal_of_zone_unregister(struct device *dev, struct thermal_zone_device *tz);
+struct thermal_cooling_device *
+thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
+
+struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
#else
static inline
@@ -213,6 +222,23 @@ static inline void devm_thermal_of_zone_unregister(struct device *dev,
struct thermal_zone_device *tz)
{
}
+
+static inline struct thermal_cooling_device *
+thermal_of_cooling_device_register(struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ return ERR_PTR(-ENODEV);
+}
+
+static inline struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ return ERR_PTR(-ENODEV);
+}
#endif
int for_each_thermal_trip(struct thermal_zone_device *tz,
@@ -254,17 +280,11 @@ void thermal_zone_device_update(struct thermal_zone_device *,
struct thermal_cooling_device *thermal_cooling_device_register(const char *,
void *, const struct thermal_cooling_device_ops *);
+
struct thermal_cooling_device *
devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
const struct thermal_cooling_device_ops *ops);
-struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops);
-struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops);
+
void thermal_cooling_device_update(struct thermal_cooling_device *);
void thermal_cooling_device_unregister(struct thermal_cooling_device *);
struct thermal_zone_device *thermal_zone_get_zone_by_name(const char *name);
@@ -310,18 +330,7 @@ thermal_cooling_device_register(const char *type, void *devdata,
const struct thermal_cooling_device_ops *ops)
{ return ERR_PTR(-ENODEV); }
static inline struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
-{ return ERR_PTR(-ENODEV); }
-static inline struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
-{
- return ERR_PTR(-ENODEV);
-}
+
static inline void thermal_cooling_device_unregister(
struct thermal_cooling_device *cdev)
{ }
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (4 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 15:17 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 07/10] thermal/of: Add cooling device ID support Daniel Lezcano
` (4 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon, Krzysztof Kozlowski,
Thierry Reding, Nathan Chancellor, Nick Desaulniers,
Bill Wendling, Justin Stitt, Ingo Molnar, Thomas Gleixner,
Jiri Slaby (SUSE),
Mikko Perttunen, Svyatoslav Ryhel,
moderated list:ARM/ASPEED MACHINE SUPPORT,
moderated list:ARM/ASPEED MACHINE SUPPORT,
moderated list:ARM/NUVOTON NPCM ARCHITECTURE,
open list:TEGRA ARCHITECTURE SUPPORT,
open list:ARM/QUALCOMM MAILING LIST,
open list:KHADAS MCU MFD DRIVER,
open list:CLANG/LLVM BUILD SUPPORT
To clarify that the function operates on child nodes, rename:
devm_thermal_of_cooling_device_register()
|
v
devm_thermal_of_child_cooling_device_register()
Used the command:
find . -type f -name '*.[ch]' -exec \
sed -i 's/devm_thermal_of_cooling_device_register/\
devm_thermal_of_child_cooling_device_register/g' {} \;
Did not used clang-format-diff because it does not indent correctly
and checkpatch complained. Manually reindented to make checkpatch
happy
This prepares for upcoming support of cooling devices identified by
an ID rather than device tree child nodes.
No functional change.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/hwmon/amc6821.c | 2 +-
drivers/hwmon/aspeed-pwm-tacho.c | 5 +++--
drivers/hwmon/emc2305.c | 6 +++---
drivers/hwmon/gpio-fan.c | 6 ++++--
drivers/hwmon/max6650.c | 6 +++---
drivers/hwmon/npcm750-pwm-fan.c | 6 ++++--
drivers/hwmon/pwm-fan.c | 5 +++--
drivers/hwmon/qnap-mcu-hwmon.c | 6 +++---
drivers/hwmon/tc654.c | 5 +++--
drivers/memory/tegra/tegra210-emc-core.c | 4 ++--
drivers/soc/qcom/qcom_aoss.c | 2 +-
drivers/thermal/khadas_mcu_fan.c | 7 ++++---
drivers/thermal/tegra/soctherm.c | 6 +++---
drivers/thermal/thermal_of.c | 15 +++++++++------
include/linux/thermal.h | 16 ++++++++--------
15 files changed, 54 insertions(+), 43 deletions(-)
diff --git a/drivers/hwmon/amc6821.c b/drivers/hwmon/amc6821.c
index d5f864b360b0..8e5926b06070 100644
--- a/drivers/hwmon/amc6821.c
+++ b/drivers/hwmon/amc6821.c
@@ -1076,7 +1076,7 @@ static int amc6821_probe(struct i2c_client *client)
"Failed to initialize hwmon\n");
if (IS_ENABLED(CONFIG_THERMAL) && fan_np && data->fan_cooling_levels)
- return PTR_ERR_OR_ZERO(devm_thermal_of_cooling_device_register(dev,
+ return PTR_ERR_OR_ZERO(devm_thermal_of_child_cooling_device_register(dev,
fan_np, client->name, data, &amc6821_cooling_ops));
return 0;
diff --git a/drivers/hwmon/aspeed-pwm-tacho.c b/drivers/hwmon/aspeed-pwm-tacho.c
index aa159bf158a3..1c5945d4ba37 100644
--- a/drivers/hwmon/aspeed-pwm-tacho.c
+++ b/drivers/hwmon/aspeed-pwm-tacho.c
@@ -841,8 +841,9 @@ static int aspeed_create_pwm_cooling(struct device *dev,
}
snprintf(cdev->name, MAX_CDEV_NAME_LEN, "%pOFn%d", child, pwm_port);
- cdev->tcdev = devm_thermal_of_cooling_device_register(dev, child,
- cdev->name, cdev, &aspeed_pwm_cool_ops);
+ cdev->tcdev = devm_thermal_of_child_cooling_device_register(dev, child,
+ cdev->name, cdev,
+ &aspeed_pwm_cool_ops);
if (IS_ERR(cdev->tcdev))
return PTR_ERR(cdev->tcdev);
diff --git a/drivers/hwmon/emc2305.c b/drivers/hwmon/emc2305.c
index 64b213e1451e..2505e9fac499 100644
--- a/drivers/hwmon/emc2305.c
+++ b/drivers/hwmon/emc2305.c
@@ -309,9 +309,9 @@ static int emc2305_set_single_tz(struct device *dev, struct device_node *fan_nod
pwm = data->pwm_min[cdev_idx];
data->cdev_data[cdev_idx].cdev =
- devm_thermal_of_cooling_device_register(dev, fan_node,
- emc2305_fan_name[idx], data,
- &emc2305_cooling_ops);
+ devm_thermal_of_child_cooling_device_register(dev, fan_node,
+ emc2305_fan_name[idx], data,
+ &emc2305_cooling_ops);
if (IS_ERR(data->cdev_data[cdev_idx].cdev)) {
dev_err(dev, "Failed to register cooling device %s\n", emc2305_fan_name[idx]);
diff --git a/drivers/hwmon/gpio-fan.c b/drivers/hwmon/gpio-fan.c
index a8892ced1e54..084828e1e281 100644
--- a/drivers/hwmon/gpio-fan.c
+++ b/drivers/hwmon/gpio-fan.c
@@ -592,8 +592,10 @@ static int gpio_fan_probe(struct platform_device *pdev)
}
/* Optional cooling device register for Device tree platforms */
- fan_data->cdev = devm_thermal_of_cooling_device_register(dev, np,
- "gpio-fan", fan_data, &gpio_fan_cool_ops);
+ fan_data->cdev = devm_thermal_of_child_cooling_device_register(dev, np,
+ "gpio-fan",
+ fan_data,
+ &gpio_fan_cool_ops);
dev_info(dev, "GPIO fan initialized\n");
diff --git a/drivers/hwmon/max6650.c b/drivers/hwmon/max6650.c
index 56b8157885bb..3466edd7d501 100644
--- a/drivers/hwmon/max6650.c
+++ b/drivers/hwmon/max6650.c
@@ -794,9 +794,9 @@ static int max6650_probe(struct i2c_client *client)
return err;
if (IS_ENABLED(CONFIG_THERMAL)) {
- cooling_dev = devm_thermal_of_cooling_device_register(dev,
- dev->of_node, client->name,
- data, &max6650_cooling_ops);
+ cooling_dev = devm_thermal_of_child_cooling_device_register(dev, dev->of_node,
+ client->name, data,
+ &max6650_cooling_ops);
if (IS_ERR(cooling_dev)) {
dev_warn(dev, "thermal cooling device register failed: %ld\n",
PTR_ERR(cooling_dev));
diff --git a/drivers/hwmon/npcm750-pwm-fan.c b/drivers/hwmon/npcm750-pwm-fan.c
index c8f5e695fb6d..aea0b8659f5f 100644
--- a/drivers/hwmon/npcm750-pwm-fan.c
+++ b/drivers/hwmon/npcm750-pwm-fan.c
@@ -857,8 +857,10 @@ static int npcm7xx_create_pwm_cooling(struct device *dev,
snprintf(cdev->name, THERMAL_NAME_LENGTH, "%pOFn%d", child,
pwm_port);
- cdev->tcdev = devm_thermal_of_cooling_device_register(dev, child,
- cdev->name, cdev, &npcm7xx_pwm_cool_ops);
+ cdev->tcdev = devm_thermal_of_child_cooling_device_register(dev, child,
+ cdev->name,
+ cdev,
+ &npcm7xx_pwm_cool_ops);
if (IS_ERR(cdev->tcdev))
return PTR_ERR(cdev->tcdev);
diff --git a/drivers/hwmon/pwm-fan.c b/drivers/hwmon/pwm-fan.c
index 37269db2de84..e6a567d58579 100644
--- a/drivers/hwmon/pwm-fan.c
+++ b/drivers/hwmon/pwm-fan.c
@@ -685,8 +685,9 @@ static int pwm_fan_probe(struct platform_device *pdev)
ctx->pwm_fan_state = ctx->pwm_fan_max_state;
if (IS_ENABLED(CONFIG_THERMAL)) {
- cdev = devm_thermal_of_cooling_device_register(dev,
- dev->of_node, "pwm-fan", ctx, &pwm_fan_cooling_ops);
+ cdev = devm_thermal_of_child_cooling_device_register(dev, dev->of_node,
+ "pwm-fan", ctx,
+ &pwm_fan_cooling_ops);
if (IS_ERR(cdev)) {
ret = PTR_ERR(cdev);
dev_err(dev,
diff --git a/drivers/hwmon/qnap-mcu-hwmon.c b/drivers/hwmon/qnap-mcu-hwmon.c
index e86e64c4d391..c1c1e9d6f340 100644
--- a/drivers/hwmon/qnap-mcu-hwmon.c
+++ b/drivers/hwmon/qnap-mcu-hwmon.c
@@ -337,9 +337,9 @@ static int qnap_mcu_hwmon_probe(struct platform_device *pdev)
* levels and only succeed with either no or correct cooling levels.
*/
if (IS_ENABLED(CONFIG_THERMAL) && hwm->fan_cooling_levels) {
- cdev = devm_thermal_of_cooling_device_register(dev,
- to_of_node(hwm->fan_node), "qnap-mcu-hwmon",
- hwm, &qnap_mcu_hwmon_cooling_ops);
+ cdev = devm_thermal_of_child_cooling_device_register(dev, to_of_node(hwm->fan_node),
+ "qnap-mcu-hwmon", hwm,
+ &qnap_mcu_hwmon_cooling_ops);
if (IS_ERR(cdev))
return dev_err_probe(dev, PTR_ERR(cdev),
"Failed to register qnap-mcu-hwmon as cooling device\n");
diff --git a/drivers/hwmon/tc654.c b/drivers/hwmon/tc654.c
index 39fe5836f237..ba18b442b81e 100644
--- a/drivers/hwmon/tc654.c
+++ b/drivers/hwmon/tc654.c
@@ -541,8 +541,9 @@ static int tc654_probe(struct i2c_client *client)
if (IS_ENABLED(CONFIG_THERMAL)) {
struct thermal_cooling_device *cdev;
- cdev = devm_thermal_of_cooling_device_register(dev, dev->of_node, client->name,
- hwmon_dev, &tc654_fan_cool_ops);
+ cdev = devm_thermal_of_child_cooling_device_register(dev, dev->of_node,
+ client->name, hwmon_dev,
+ &tc654_fan_cool_ops);
return PTR_ERR_OR_ZERO(cdev);
}
diff --git a/drivers/memory/tegra/tegra210-emc-core.c b/drivers/memory/tegra/tegra210-emc-core.c
index e96ca4157d48..065ae8bc2830 100644
--- a/drivers/memory/tegra/tegra210-emc-core.c
+++ b/drivers/memory/tegra/tegra210-emc-core.c
@@ -1966,8 +1966,8 @@ static int tegra210_emc_probe(struct platform_device *pdev)
tegra210_emc_debugfs_init(emc);
- cd = devm_thermal_of_cooling_device_register(emc->dev, np, "emc", emc,
- &tegra210_emc_cd_ops);
+ cd = devm_thermal_of_child_cooling_device_register(emc->dev, np, "emc", emc,
+ &tegra210_emc_cd_ops);
if (IS_ERR(cd)) {
err = PTR_ERR(cd);
dev_err(emc->dev, "failed to register cooling device: %d\n",
diff --git a/drivers/soc/qcom/qcom_aoss.c b/drivers/soc/qcom/qcom_aoss.c
index c255662b8fc3..259c41f0c34e 100644
--- a/drivers/soc/qcom/qcom_aoss.c
+++ b/drivers/soc/qcom/qcom_aoss.c
@@ -381,7 +381,7 @@ static int qmp_cooling_device_add(struct qmp *qmp,
qmp_cdev->qmp = qmp;
qmp_cdev->state = !qmp_cdev_max_state;
qmp_cdev->name = cdev_name;
- qmp_cdev->cdev = devm_thermal_of_cooling_device_register
+ qmp_cdev->cdev = devm_thermal_of_child_cooling_device_register
(qmp->dev, node,
cdev_name,
qmp_cdev, &qmp_cooling_device_ops);
diff --git a/drivers/thermal/khadas_mcu_fan.c b/drivers/thermal/khadas_mcu_fan.c
index d35e5313bea4..21b3d0a71bd0 100644
--- a/drivers/thermal/khadas_mcu_fan.c
+++ b/drivers/thermal/khadas_mcu_fan.c
@@ -90,9 +90,10 @@ static int khadas_mcu_fan_probe(struct platform_device *pdev)
ctx->mcu = mcu;
platform_set_drvdata(pdev, ctx);
- cdev = devm_thermal_of_cooling_device_register(dev->parent,
- dev->parent->of_node, "khadas-mcu-fan", ctx,
- &khadas_mcu_fan_cooling_ops);
+ cdev = devm_thermal_of_child_cooling_device_register(dev->parent,
+ dev->parent->of_node,
+ "khadas-mcu-fan", ctx,
+ &khadas_mcu_fan_cooling_ops);
if (IS_ERR(cdev)) {
ret = PTR_ERR(cdev);
dev_err(dev, "Failed to register khadas-mcu-fan as cooling device: %d\n",
diff --git a/drivers/thermal/tegra/soctherm.c b/drivers/thermal/tegra/soctherm.c
index 6a56638c98f1..d8e988a0d43e 100644
--- a/drivers/thermal/tegra/soctherm.c
+++ b/drivers/thermal/tegra/soctherm.c
@@ -1707,9 +1707,9 @@ static void soctherm_init_hw_throt_cdev(struct platform_device *pdev)
stc->init = true;
} else {
- tcd = devm_thermal_of_cooling_device_register(dev, np_stcc,
- (char *)name, ts,
- &throt_cooling_ops);
+ tcd = devm_thermal_of_child_cooling_device_register(dev, np_stcc,
+ (char *)name, ts,
+ &throt_cooling_ops);
if (IS_ERR_OR_NULL(tcd)) {
dev_err(dev,
"throttle-cfg: %s: failed to register cooling device\n",
diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
index 8c49d449d43f..b59d2588ff7a 100644
--- a/drivers/thermal/thermal_of.c
+++ b/drivers/thermal/thermal_of.c
@@ -557,7 +557,7 @@ static void thermal_of_cooling_device_release(void *data)
}
/**
- * devm_thermal_of_cooling_device_register() - register an OF thermal cooling
+ * devm_thermal_of_child_cooling_device_register() - register an OF thermal cooling
* device
* @dev: a valid struct device pointer of a sensor device.
* @np: a pointer to a device tree node.
@@ -570,14 +570,17 @@ static void thermal_of_cooling_device_release(void *data)
* to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
* to all the thermal zone devices registered at the same time.
*
+ * This function should be used when a cooling controller has child
+ * nodes which are referenced in the thermal zone cooling map.
+ *
* Return: a pointer to the created struct thermal_cooling_device or an
* ERR_PTR. Caller must check return value with IS_ERR*() helpers.
*/
struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
+devm_thermal_of_child_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
{
struct thermal_cooling_device *cdev;
int ret;
@@ -592,4 +595,4 @@ devm_thermal_of_cooling_device_register(struct device *dev,
return cdev;
}
-EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
+EXPORT_SYMBOL_GPL(devm_thermal_of_child_cooling_device_register);
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index 6d1862ac187f..e6328234a42b 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -205,10 +205,10 @@ thermal_of_cooling_device_register(struct device_node *np, const char *type, voi
const struct thermal_cooling_device_ops *ops);
struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops);
+devm_thermal_of_child_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
#else
static inline
@@ -232,10 +232,10 @@ thermal_of_cooling_device_register(struct device_node *np,
}
static inline struct thermal_cooling_device *
-devm_thermal_of_cooling_device_register(struct device *dev,
- struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
+devm_thermal_of_child_cooling_device_register(struct device *dev,
+ struct device_node *np,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
{
return ERR_PTR(-ENODEV);
}
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 07/10] thermal/of: Add cooling device ID support
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (5 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 15:18 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper Daniel Lezcano
` (3 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon,
moderated list:DRM DRIVERS FOR VIVANTE GPU IP,
open list:DRM DRIVERS FOR VIVANTE GPU IP
Introduce an identifier (cdev_id) for cooling devices registered from
device tree.
This prepares support for a new DT binding where cooling devices are
identified by a tuple (device node, ID), instead of relying on child
nodes.
Existing users are updated to pass a default ID of 0, preserving the
current behavior.
Future changes will extend the cooling map parsing to match cooling
devices based on both the device node and the ID.
No functional change intended.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/gpu/drm/etnaviv/etnaviv_gpu.c | 5 +++--
drivers/thermal/cpufreq_cooling.c | 2 +-
drivers/thermal/cpuidle_cooling.c | 2 +-
drivers/thermal/devfreq_cooling.c | 2 +-
drivers/thermal/thermal_of.c | 14 ++++++++------
include/linux/thermal.h | 6 ++++--
6 files changed, 18 insertions(+), 13 deletions(-)
diff --git a/drivers/gpu/drm/etnaviv/etnaviv_gpu.c b/drivers/gpu/drm/etnaviv/etnaviv_gpu.c
index a891d4f1f843..552631c3554a 100644
--- a/drivers/gpu/drm/etnaviv/etnaviv_gpu.c
+++ b/drivers/gpu/drm/etnaviv/etnaviv_gpu.c
@@ -1791,8 +1791,9 @@ static int etnaviv_gpu_bind(struct device *dev, struct device *master,
int ret;
if (IS_ENABLED(CONFIG_DRM_ETNAVIV_THERMAL)) {
- gpu->cooling = thermal_of_cooling_device_register(dev->of_node,
- (char *)dev_name(dev), gpu, &cooling_ops);
+ gpu->cooling = thermal_of_cooling_device_register(dev->of_node, 0,
+ dev_name(dev),
+ gpu, &cooling_ops);
if (IS_ERR(gpu->cooling))
return PTR_ERR(gpu->cooling);
}
diff --git a/drivers/thermal/cpufreq_cooling.c b/drivers/thermal/cpufreq_cooling.c
index 32bf5ab44f4a..768859a7aed0 100644
--- a/drivers/thermal/cpufreq_cooling.c
+++ b/drivers/thermal/cpufreq_cooling.c
@@ -592,7 +592,7 @@ __cpufreq_cooling_register(struct device_node *np,
if (!name)
goto remove_qos_req;
- cdev = thermal_of_cooling_device_register(np, name, cpufreq_cdev,
+ cdev = thermal_of_cooling_device_register(np, 0, name, cpufreq_cdev,
cooling_ops);
kfree(name);
diff --git a/drivers/thermal/cpuidle_cooling.c b/drivers/thermal/cpuidle_cooling.c
index 425f596614e8..bbd2e91cf5ab 100644
--- a/drivers/thermal/cpuidle_cooling.c
+++ b/drivers/thermal/cpuidle_cooling.c
@@ -207,7 +207,7 @@ static int __cpuidle_cooling_register(struct device_node *np,
goto out_unregister;
}
- cdev = thermal_of_cooling_device_register(np, name, idle_cdev,
+ cdev = thermal_of_cooling_device_register(np, 0, name, idle_cdev,
&cpuidle_cooling_ops);
if (IS_ERR(cdev)) {
ret = PTR_ERR(cdev);
diff --git a/drivers/thermal/devfreq_cooling.c b/drivers/thermal/devfreq_cooling.c
index 1c7dffc8d45f..0330a8112832 100644
--- a/drivers/thermal/devfreq_cooling.c
+++ b/drivers/thermal/devfreq_cooling.c
@@ -454,7 +454,7 @@ of_devfreq_cooling_register_power(struct device_node *np, struct devfreq *df,
if (!name)
goto remove_qos_req;
- cdev = thermal_of_cooling_device_register(np, name, dfc, ops);
+ cdev = thermal_of_cooling_device_register(np, 0, name, dfc, ops);
kfree(name);
if (IS_ERR(cdev)) {
diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
index b59d2588ff7a..0110b195f7a3 100644
--- a/drivers/thermal/thermal_of.c
+++ b/drivers/thermal/thermal_of.c
@@ -514,6 +514,7 @@ EXPORT_SYMBOL_GPL(devm_thermal_of_zone_unregister);
/**
* thermal_of_cooling_device_register() - register an OF thermal cooling device
* @np: a pointer to a device tree node.
+ * @cdev_id: a cooling device id in the cooling controller
* @type: the thermal cooling device type.
* @devdata: device private data.
* @ops: standard thermal cooling devices callbacks.
@@ -528,9 +529,9 @@ EXPORT_SYMBOL_GPL(devm_thermal_of_zone_unregister);
* ERR_PTR. Caller must check return value with IS_ERR*() helpers.
*/
struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np,
- const char *type, void *devdata,
- const struct thermal_cooling_device_ops *ops)
+thermal_of_cooling_device_register(struct device_node *np, u32 cdev_id,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
{
struct thermal_cooling_device *cdev;
int ret;
@@ -540,6 +541,7 @@ thermal_of_cooling_device_register(struct device_node *np,
return cdev;
cdev->np = np;
+ cdev->cdev_id = cdev_id;
ret = thermal_cooling_device_add(cdev, devdata);
if (ret)
@@ -585,9 +587,9 @@ devm_thermal_of_child_cooling_device_register(struct device *dev,
struct thermal_cooling_device *cdev;
int ret;
- cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
- if (IS_ERR(cdev))
- return cdev;
+ cdev = thermal_of_cooling_device_register(np, 0, type, devdata, ops);
+ if (IS_ERR(cdev))
+ return cdev;
ret = devm_add_action_or_reset(dev, thermal_of_cooling_device_release, cdev);
if (ret)
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index e6328234a42b..fb7649439dfa 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -134,6 +134,7 @@ struct thermal_cooling_device {
struct list_head node;
#ifdef CONFIG_THERMAL_OF
struct device_node *np;
+ u32 cdev_id;
#endif
#ifdef CONFIG_THERMAL_DEBUGFS
struct thermal_debugfs *debugfs;
@@ -201,7 +202,8 @@ struct thermal_zone_device *devm_thermal_of_zone_register(struct device *dev, in
void devm_thermal_of_zone_unregister(struct device *dev, struct thermal_zone_device *tz);
struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
+thermal_of_cooling_device_register(struct device_node *np, u32 cdev_id,
+ const char *type, void *data,
const struct thermal_cooling_device_ops *ops);
struct thermal_cooling_device *
@@ -224,7 +226,7 @@ static inline void devm_thermal_of_zone_unregister(struct device *dev,
}
static inline struct thermal_cooling_device *
-thermal_of_cooling_device_register(struct device_node *np,
+thermal_of_cooling_device_register(struct device_node *np, u32 cdev_id,
const char *type, void *devdata,
const struct thermal_cooling_device_ops *ops)
{
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (6 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 07/10] thermal/of: Add cooling device ID support Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 15:21 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec Daniel Lezcano
` (2 subsequent siblings)
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Extend the OF cooling device registration to support an explicit
cooling device identifier (cdev_id), preparing for upcoming DT
bindings where cooling devices are identified by a tuple (device node,
id) instead of relying on child nodes.
Introduce a new helper:
devm_thermal_of_cooling_device_register()
which registers a cooling device using the device's of_node and an
explicit cdev_id. This complements the existing
devm_thermal_of_child_cooling_device_register() helper, which
remains dedicated to the legacy child-node based bindings.
Internally, factorize the devm registration logic into a common
helper to avoid code duplication.
Existing users are unaffected, as the child-based helper continues
to pass a default cdev_id of 0, preserving current behavior.
This change is a preparatory step for supporting indexed cooling
devices in thermal OF bindings.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/thermal/thermal_of.c | 58 ++++++++++++++++++++++++++++--------
include/linux/thermal.h | 13 ++++++++
2 files changed, 59 insertions(+), 12 deletions(-)
diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
index 0110b195f7a3..3584024b76f5 100644
--- a/drivers/thermal/thermal_of.c
+++ b/drivers/thermal/thermal_of.c
@@ -558,6 +558,51 @@ static void thermal_of_cooling_device_release(void *data)
thermal_cooling_device_unregister(cdev);
}
+static struct thermal_cooling_device *
+__devm_thermal_of_cooling_device_register(struct device *dev, struct device_node *np,
+ u32 cdev_id, const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ struct thermal_cooling_device *cdev;
+ int ret;
+
+ cdev = thermal_of_cooling_device_register(np, cdev_id, type, devdata, ops);
+ if (IS_ERR(cdev))
+ return cdev;
+
+ ret = devm_add_action_or_reset(dev, thermal_of_cooling_device_release, cdev);
+ if (ret)
+ return ERR_PTR(ret);
+
+ return cdev;
+}
+
+/**
+ * devm_thermal_of_cooling_device_register() - register an OF thermal cooling device
+ * @dev: a valid struct device pointer of a sensor device.
+ * @cdev_id: a cooling device index in the cooling controller
+ * @type: the thermal cooling device type.
+ * @devdata: device private data.
+ * @ops: standard thermal cooling devices callbacks.
+ *
+ * This function will register a cooling device with device tree node reference.
+ * This interface function adds a new thermal cooling device (fan/processor/...)
+ * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
+ * to all the thermal zone devices registered at the same time.
+ *
+ * Return: a pointer to the created struct thermal_cooling_device or an
+ * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
+ */
+struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev, u32 cdev_id,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ return __devm_thermal_of_cooling_device_register(dev, dev->of_node, cdev_id,
+ type, devdata, ops);
+}
+EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
+
/**
* devm_thermal_of_child_cooling_device_register() - register an OF thermal cooling
* device
@@ -584,17 +629,6 @@ devm_thermal_of_child_cooling_device_register(struct device *dev,
const char *type, void *devdata,
const struct thermal_cooling_device_ops *ops)
{
- struct thermal_cooling_device *cdev;
- int ret;
-
- cdev = thermal_of_cooling_device_register(np, 0, type, devdata, ops);
- if (IS_ERR(cdev))
- return cdev;
-
- ret = devm_add_action_or_reset(dev, thermal_of_cooling_device_release, cdev);
- if (ret)
- return ERR_PTR(ret);
-
- return cdev;
+ return __devm_thermal_of_cooling_device_register(dev, np, 0, type, devdata, ops);
}
EXPORT_SYMBOL_GPL(devm_thermal_of_child_cooling_device_register);
diff --git a/include/linux/thermal.h b/include/linux/thermal.h
index fb7649439dfa..81be6e6061b3 100644
--- a/include/linux/thermal.h
+++ b/include/linux/thermal.h
@@ -206,6 +206,11 @@ thermal_of_cooling_device_register(struct device_node *np, u32 cdev_id,
const char *type, void *data,
const struct thermal_cooling_device_ops *ops);
+struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev, u32 cdev_id,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops);
+
struct thermal_cooling_device *
devm_thermal_of_child_cooling_device_register(struct device *dev,
struct device_node *np,
@@ -233,6 +238,14 @@ thermal_of_cooling_device_register(struct device_node *np, u32 cdev_id,
return ERR_PTR(-ENODEV);
}
+static inline struct thermal_cooling_device *
+devm_thermal_of_cooling_device_register(struct device *dev, u32 cdev_id,
+ const char *type, void *devdata,
+ const struct thermal_cooling_device_ops *ops)
+{
+ return ERR_PTR(-ENODEV);
+}
+
static inline struct thermal_cooling_device *
devm_thermal_of_child_cooling_device_register(struct device *dev,
struct device_node *np,
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (7 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 15:25 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device Daniel Lezcano
2026-05-29 8:35 ` [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF Daniel Lezcano
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Extend the cooling device specifier parsing to support an optional
cooling device identifier (cdev_id).
Two formats are now supported:
- Legacy format:
<&cdev lower upper>
- Indexed format:
<&cdev cdev_id lower upper>
When the indexed format is used, both the device node and the
cdev_id must match in order to bind a cooling device to a thermal
zone. The legacy format continues to match on the device node only,
preserving backward compatibility.
Update the parsing logic accordingly to handle both formats and
extract the mitigation limits from the appropriate arguments.
This is a preparatory step for upcoming DT bindings describing
cooling devices using (device node, id) tuples instead of child
nodes.
No functional change for existing device trees.
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
---
drivers/thermal/thermal_of.c | 26 ++++++++++++++++++++++----
1 file changed, 22 insertions(+), 4 deletions(-)
diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
index 3584024b76f5..100fd8a0c8ce 100644
--- a/drivers/thermal/thermal_of.c
+++ b/drivers/thermal/thermal_of.c
@@ -259,16 +259,34 @@ static bool thermal_of_get_cooling_spec(struct device_node *map_np, int index,
of_node_put(cooling_spec.np);
- if (cooling_spec.args_count < 2) {
- pr_err("wrong reference to cooling device, missing limits\n");
+ /*
+ * There are two formats:
+ * - Legacy format : <&cdev lower upper>
+ * - New format : <&cdev cdev_id lower upper>
+ *
+ * With the new format, along with the device node pointer,
+ * the cdev_id must match with the cooling device cdev_id in
+ * order to bind
+ */
+ if (cooling_spec.args_count < 2 || cooling_spec.args_count > 3) {
+ pr_err("Invalid number of cooling device parameters\n");
return false;
}
if (cooling_spec.np != cdev->np)
return false;
- c->lower = cooling_spec.args[0];
- c->upper = cooling_spec.args[1];
+ if (cooling_spec.args_count == 3 &&
+ cooling_spec.args[0] != cdev->cdev_id)
+ return false;
+
+ if (cooling_spec.args_count != 3) {
+ c->lower = cooling_spec.args[0];
+ c->upper = cooling_spec.args[1];
+ } else {
+ c->lower = cooling_spec.args[1];
+ c->upper = cooling_spec.args[2];
+ }
c->weight = weight;
return true;
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (8 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec Daniel Lezcano
@ 2026-05-26 14:08 ` Daniel Lezcano
2026-05-29 15:26 ` Lukasz Luba
2026-05-29 8:35 ` [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF Daniel Lezcano
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-26 14:08 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon, Gaurav Kohli,
Krzysztof Kozlowski,
open list:OPEN FIRMWARE AND FLATTENED DEVICE TREE BINDINGS
From: Gaurav Kohli <gaurav.kohli@oss.qualcomm.com>
Extend the thermal cooling device binding to support a 3 cells specifier
along with the 2 cells format.
Update #cooling-cells property to enum to support both 2 and 3 arguments.
Fix pwm-fan.yaml to restrict the number of cells to 'const: 2'
Signed-off-by: Gaurav Kohli <gaurav.kohli@oss.qualcomm.com>
Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
Reviewed-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
---
Documentation/devicetree/bindings/hwmon/pwm-fan.yaml | 3 ++-
.../bindings/thermal/thermal-cooling-devices.yaml | 8 ++++++--
.../devicetree/bindings/thermal/thermal-zones.yaml | 3 ++-
3 files changed, 10 insertions(+), 4 deletions(-)
diff --git a/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml b/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
index a84cc3a4cfdc..6a24851fd80d 100644
--- a/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
+++ b/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
@@ -63,7 +63,8 @@ properties:
description: The PWM that is used to control the fan.
maxItems: 1
- "#cooling-cells": true
+ "#cooling-cells":
+ const: 2
required:
- compatible
diff --git a/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml b/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
index b9022f1613d8..28f5818f1e60 100644
--- a/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
+++ b/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
@@ -44,10 +44,14 @@ select: true
properties:
"#cooling-cells":
description:
- Must be 2, in order to specify minimum and maximum cooling state used in
+ Must be 2 or 3. If 2, specifies minimum and maximum cooling state used in
the cooling-maps reference. The first cell is the minimum cooling state
and the second cell is the maximum cooling state requested.
- const: 2
+ If 3, the first cell specifies the thermal mitigation device specifier
+ index for devices that support multiple thermal mitigation mechanisms.
+ The two other cells are respectively the minimum cooling state and the
+ maximum cooling state.
+ enum: [2, 3]
additionalProperties: true
diff --git a/Documentation/devicetree/bindings/thermal/thermal-zones.yaml b/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
index 07d9f576ffe7..999ad40a20d5 100644
--- a/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
+++ b/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
@@ -211,7 +211,8 @@ patternProperties:
device. Using the THERMAL_NO_LIMIT (-1UL) constant in the
cooling-device phandle limit specifier lets the framework
use the minimum and maximum cooling state for that cooling
- device automatically.
+ device automatically. If three arguments are specified,
+ the first argument is the cooling device specifier.
contribution:
$ref: /schemas/types.yaml#/definitions/uint32
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
` (9 preceding siblings ...)
2026-05-26 14:08 ` [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device Daniel Lezcano
@ 2026-05-29 8:35 ` Daniel Lezcano
2026-05-29 12:35 ` Rafael J. Wysocki
10 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-29 8:35 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: Zhang Rui, Lukasz Luba, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Hi Rafael,
On 5/26/26 16:08, Daniel Lezcano wrote:
[ ... ]
> ---
> Changelog:
> - V4
> - Reworked splitted functions to register a cooling device and
> merged separately
Are you fine with the thermal core changes in this series ?
Is it ok if I pick the series in my branch (and may be send a early PR) ?
> - V3
> - Reordered and reworked the patches to be git bisect safe
> - Reworked devm usage by using a more adequate function doing the
> same as the group of calls to devm*
> - Pass an init callback instead of moving
> thermal_cooling_device_init_complete() out of the function and
> calling it in different places
> - Sent separetely changes to the tegra soctherm driver
> - V2
> - Added stubs for OF functions in order to prevent to break the git
> bisectability compilation
> - Added missing call to thermal_cooling_device_init_complete() in
> devm_thermal_of_cooling_device_register()
> - Fixed assymetry in devm_ calls for the tegra/soctherm() driver
> - Fixed kernel documentation for API changes
> - Added missing static inline for a API stub
> - Hardened the test with two or three arguments in the cooling spec
> - Narrowed const: 2 strict in pwm-fan
> ---
>
> Daniel Lezcano (9):
> thermal/core: Introduce non-OF thermal_cooling_device_register()
> thermal/core: Add devm_thermal_cooling_device_register()
> hwmon: Use non-OF thermal cooling device registration API
> thermal/core: Make cooling device OF node conditional on
> CONFIG_THERMAL_OF
> thermal/of: Move cooling device OF helpers out of thermal core
> thermal/of: Rename the devm_thermal_of_cooling_device_register()
> function
> thermal/of: Add cooling device ID support
> thermal/of: Pass cdev_id and introduce devm registration helper
> thermal/of: Support cooling device ID in cooling-spec
>
> Gaurav Kohli (1):
> dt-bindings: thermal: cooling-devices: Update support for 3 cells
> cooling device
>
> .../devicetree/bindings/hwmon/pwm-fan.yaml | 3 +-
> .../thermal/thermal-cooling-devices.yaml | 8 +-
> .../bindings/thermal/thermal-zones.yaml | 3 +-
> drivers/gpu/drm/etnaviv/etnaviv_gpu.c | 5 +-
> drivers/hwmon/amc6821.c | 2 +-
> drivers/hwmon/aspeed-pwm-tacho.c | 5 +-
> drivers/hwmon/cros_ec_hwmon.c | 4 +-
> drivers/hwmon/dell-smm-hwmon.c | 4 +-
> drivers/hwmon/emc2305.c | 6 +-
> drivers/hwmon/gpio-fan.c | 6 +-
> drivers/hwmon/max6650.c | 6 +-
> drivers/hwmon/mlxreg-fan.c | 4 +-
> drivers/hwmon/npcm750-pwm-fan.c | 6 +-
> drivers/hwmon/pwm-fan.c | 5 +-
> drivers/hwmon/qnap-mcu-hwmon.c | 6 +-
> drivers/hwmon/tc654.c | 5 +-
> drivers/memory/tegra/tegra210-emc-core.c | 4 +-
> drivers/soc/qcom/qcom_aoss.c | 2 +-
> drivers/thermal/cpufreq_cooling.c | 2 +-
> drivers/thermal/cpuidle_cooling.c | 2 +-
> drivers/thermal/devfreq_cooling.c | 2 +-
> drivers/thermal/khadas_mcu_fan.c | 7 +-
> drivers/thermal/tegra/soctherm.c | 6 +-
> drivers/thermal/thermal_core.c | 85 ++--------
> drivers/thermal/thermal_core.h | 5 +
> drivers/thermal/thermal_of.c | 148 +++++++++++++++++-
> include/linux/thermal.h | 69 +++++---
> 27 files changed, 273 insertions(+), 137 deletions(-)
>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register()
2026-05-26 14:08 ` [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register() Daniel Lezcano
@ 2026-05-29 9:47 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 9:47 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> Split the cooling device registration API into OF and non-OF variants.
>
> Introduce thermal_cooling_device_register() for non-device-tree users
> and rework thermal_of_cooling_device_register() to use the new
> alloc/add split.
>
> This removes the need for the internal __thermal_cooling_device_register()
> helper and makes the separation between OF and non-OF users explicit.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/thermal/thermal_core.c | 60 ++++++++++++++--------------------
> 1 file changed, 24 insertions(+), 36 deletions(-)
>
> diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
> index db01361569d7..0b3db889d60d 100644
> --- a/drivers/thermal/thermal_core.c
> +++ b/drivers/thermal/thermal_core.c
> @@ -1059,8 +1059,7 @@ static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void
> }
>
> /**
> - * __thermal_cooling_device_register() - register a new thermal cooling device
> - * @np: a pointer to a device tree node.
> + * thermal_cooling_device_register() - register a new thermal cooling device
> * @type: the thermal cooling device type.
> * @devdata: device private data.
> * @ops: standard thermal cooling devices callbacks.
> @@ -1068,16 +1067,13 @@ static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void
> * This interface function adds a new thermal cooling device (fan/processor/...)
> * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> * to all the thermal zone devices registered at the same time.
> - * It also gives the opportunity to link the cooling device to a device tree
> - * node, so that it can be bound to a thermal zone created out of device tree.
> *
> * Return: a pointer to the created struct thermal_cooling_device or an
> * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> */
> -static struct thermal_cooling_device *
> -__thermal_cooling_device_register(struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> +struct thermal_cooling_device *
> +thermal_cooling_device_register(const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> {
> struct thermal_cooling_device *cdev;
> int ret;
> @@ -1086,34 +1082,12 @@ __thermal_cooling_device_register(struct device_node *np,
> if (IS_ERR(cdev))
> return cdev;
>
> - cdev->np = np;
> -
> ret = thermal_cooling_device_add(cdev, devdata);
> if (ret)
> return ERR_PTR(ret);
>
> return cdev;
> }
> -
> -/**
> - * thermal_cooling_device_register() - register a new thermal cooling device
> - * @type: the thermal cooling device type.
> - * @devdata: device private data.
> - * @ops: standard thermal cooling devices callbacks.
> - *
> - * This interface function adds a new thermal cooling device (fan/processor/...)
> - * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> - * to all the thermal zone devices registered at the same time.
> - *
> - * Return: a pointer to the created struct thermal_cooling_device or an
> - * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> - */
> -struct thermal_cooling_device *
> -thermal_cooling_device_register(const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> -{
> - return __thermal_cooling_device_register(NULL, type, devdata, ops);
> -}
> EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
>
> /**
> @@ -1121,22 +1095,36 @@ EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
> * @np: a pointer to a device tree node.
> * @type: the thermal cooling device type.
> * @devdata: device private data.
> - * @ops: standard thermal cooling devices callbacks.
> + * @ops: standard thermal cooling devices callbacks.
> *
> - * This function will register a cooling device with device tree node reference.
> * This interface function adds a new thermal cooling device (fan/processor/...)
> * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> * to all the thermal zone devices registered at the same time.
> + * It also gives the opportunity to link the cooling device to a device tree
> + * node, so that it can be bound to a thermal zone created out of device tree.
> *
> * Return: a pointer to the created struct thermal_cooling_device or an
> * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> */
> struct thermal_cooling_device *
> thermal_of_cooling_device_register(struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> {
> - return __thermal_cooling_device_register(np, type, devdata, ops);
> + struct thermal_cooling_device *cdev;
> + int ret;
> +
> + cdev = thermal_cooling_device_alloc(type, ops);
> + if (IS_ERR(cdev))
> + return cdev;
> +
> + cdev->np = np;
> +
> + ret = thermal_cooling_device_add(cdev, devdata);
> + if (ret)
> + return ERR_PTR(ret);
> +
> + return cdev;
> }
> EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
>
> @@ -1173,7 +1161,7 @@ devm_thermal_of_cooling_device_register(struct device *dev,
> struct thermal_cooling_device *cdev;
> int ret;
>
> - cdev = __thermal_cooling_device_register(np, type, devdata, ops);
> + cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
> if (IS_ERR(cdev))
> return cdev;
>
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-29 8:35 ` [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF Daniel Lezcano
@ 2026-05-29 12:35 ` Rafael J. Wysocki
2026-05-29 12:41 ` Daniel Lezcano
0 siblings, 1 reply; 28+ messages in thread
From: Rafael J. Wysocki @ 2026-05-29 12:35 UTC (permalink / raw)
To: Daniel Lezcano
Cc: rafael, daniel.lezcano, Zhang Rui, Lukasz Luba, Rob Herring,
Krzysztof Kozlowski, Conor Dooley, Lucas Stach, Russell King,
Christian Gmeiner, David Airlie, Simona Vetter, Guenter Roeck,
Joel Stanley, Andrew Jeffery, Thomas Weißschuh,
Benson Leung, Pali Rohár, Avi Fishman, Tomer Maimon,
Tali Perry, Patrick Venture, Nancy Yuen, Benjamin Fair,
Heiko Stuebner, Thierry Reding, Jonathan Hunter, Bjorn Andersson,
Konrad Dybcio, Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong,
Amit Kucheria, linux-pm, linux-kernel, linux-hwmon
Hi Daniel,
On Fri, May 29, 2026 at 10:35 AM Daniel Lezcano
<daniel.lezcano@oss.qualcomm.com> wrote:
>
>
> Hi Rafael,
>
> On 5/26/26 16:08, Daniel Lezcano wrote:
>
> [ ... ]
>
> > ---
> > Changelog:
> > - V4
> > - Reworked splitted functions to register a cooling device and
> > merged separately
>
> Are you fine with the thermal core changes in this series ?
Generally, yes, I am, but let me have one more look at it.
> Is it ok if I pick the series in my branch (and may be send a early PR) ?
I have no comments, I'll respond with an Acked-by to it later today.
Thanks!
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-29 12:35 ` Rafael J. Wysocki
@ 2026-05-29 12:41 ` Daniel Lezcano
2026-05-29 15:29 ` Lukasz Luba
0 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-29 12:41 UTC (permalink / raw)
To: Rafael J. Wysocki
Cc: daniel.lezcano, Zhang Rui, Lukasz Luba, Rob Herring,
Krzysztof Kozlowski, Conor Dooley, Lucas Stach, Russell King,
Christian Gmeiner, David Airlie, Simona Vetter, Guenter Roeck,
Joel Stanley, Andrew Jeffery, Thomas Weißschuh,
Benson Leung, Pali Rohár, Avi Fishman, Tomer Maimon,
Tali Perry, Patrick Venture, Nancy Yuen, Benjamin Fair,
Heiko Stuebner, Thierry Reding, Jonathan Hunter, Bjorn Andersson,
Konrad Dybcio, Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong,
Amit Kucheria, linux-pm, linux-kernel, linux-hwmon
On 5/29/26 14:35, Rafael J. Wysocki wrote:
> Hi Daniel,
>
> On Fri, May 29, 2026 at 10:35 AM Daniel Lezcano
> <daniel.lezcano@oss.qualcomm.com> wrote:
>>
>>
>> Hi Rafael,
>>
>> On 5/26/26 16:08, Daniel Lezcano wrote:
>>
>> [ ... ]
>>
>>> ---
>>> Changelog:
>>> - V4
>>> - Reworked splitted functions to register a cooling device and
>>> merged separately
>>
>> Are you fine with the thermal core changes in this series ?
>
> Generally, yes, I am, but let me have one more look at it.
>
>> Is it ok if I pick the series in my branch (and may be send a early PR) ?
>
> I have no comments, I'll respond with an Acked-by to it later today.
>
> Thanks!
Thanks
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register()
2026-05-26 14:08 ` [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register() Daniel Lezcano
@ 2026-05-29 12:55 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 12:55 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> Introduce a device-managed variant of the non-OF cooling device
> registration API.
>
> This complements devm_thermal_of_cooling_device_register() and allows
> non-device-tree users to register cooling devices with automatic
> cleanup tied to the device lifecycle.
>
> The helper relies on devm_add_action_or_reset() to release the cooling
> device via thermal_cooling_device_release() on driver detach or probe
> failure.
>
> This keeps the API consistent across OF and non-OF users and avoids
> manual cleanup in error paths.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/thermal/thermal_core.c | 35 ++++++++++++++++++++++++++++++++++
> include/linux/thermal.h | 7 +++++--
> 2 files changed, 40 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
> index 0b3db889d60d..bb4fc3ff2ad5 100644
> --- a/drivers/thermal/thermal_core.c
> +++ b/drivers/thermal/thermal_core.c
> @@ -1173,6 +1173,41 @@ devm_thermal_of_cooling_device_register(struct device *dev,
> }
> EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
>
> +/**
> + * devm_thermal_cooling_device_register() - register a thermal cooling device
> + *
> + * @dev: a valid struct device pointer of a sensor device.
> + * @type: the thermal cooling device type.
> + * @devdata: device private data.
> + * @ops: standard thermal cooling devices callbacks.
> + *
> + * This function will register a cooling device. This interface
> + * function adds a new thermal cooling device (fan/processor/...) to
> + * /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind
> + * itself to all the thermal zone devices registered at the same time.
> + *
> + * Return: a pointer to the created struct thermal_cooling_device or an
> + * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> + */
> +struct thermal_cooling_device *
> +devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> +{
> + struct thermal_cooling_device *cdev;
> + int ret;
> +
> + cdev = thermal_cooling_device_register(type, devdata, ops);
> + if (IS_ERR(cdev))
> + return cdev;
> +
> + ret = devm_add_action_or_reset(dev, thermal_cooling_device_release, cdev);
> + if (ret)
> + return ERR_PTR(ret);
> +
> + return cdev;
> +}
> +EXPORT_SYMBOL_GPL(devm_thermal_cooling_device_register);
> +
> static bool thermal_cooling_device_present(struct thermal_cooling_device *cdev)
> {
> struct thermal_cooling_device *pos = NULL;
> diff --git a/include/linux/thermal.h b/include/linux/thermal.h
> index 0ddc77aeeca2..fc3f4a098370 100644
> --- a/include/linux/thermal.h
> +++ b/include/linux/thermal.h
> @@ -253,8 +253,11 @@ void thermal_zone_device_update(struct thermal_zone_device *,
> struct thermal_cooling_device *thermal_cooling_device_register(const char *,
> void *, const struct thermal_cooling_device_ops *);
> struct thermal_cooling_device *
> -thermal_of_cooling_device_register(struct device_node *np, const char *, void *,
> - const struct thermal_cooling_device_ops *);
> +devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops);
> +struct thermal_cooling_device *
> +thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops);
> struct thermal_cooling_device *
> devm_thermal_of_cooling_device_register(struct device *dev,
> struct device_node *np,
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API
2026-05-26 14:08 ` [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API Daniel Lezcano
@ 2026-05-29 12:55 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 12:55 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon,
open list:CHROMEOS EC HARDWARE MONITORING
On 5/26/26 15:08, Daniel Lezcano wrote:
> Some HWMON drivers register cooling devices using the OF helper
> devm_thermal_of_cooling_device_register() with a NULL device node.
>
> With the introduction of a dedicated non-OF registration API,
> switch these users to devm_thermal_cooling_device_register()
> to make the intent explicit and avoid relying on OF-specific helpers.
>
> This is a pure refactoring with no functional change.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> Acked-by: Guenter Roeck <linux@roeck-us.net>
> ---
> drivers/hwmon/cros_ec_hwmon.c | 4 ++--
> drivers/hwmon/dell-smm-hwmon.c | 4 ++--
> drivers/hwmon/mlxreg-fan.c | 4 ++--
> 3 files changed, 6 insertions(+), 6 deletions(-)
>
> diff --git a/drivers/hwmon/cros_ec_hwmon.c b/drivers/hwmon/cros_ec_hwmon.c
> index 6cf5ab0f4b73..77dd9f28962d 100644
> --- a/drivers/hwmon/cros_ec_hwmon.c
> +++ b/drivers/hwmon/cros_ec_hwmon.c
> @@ -532,8 +532,8 @@ static void cros_ec_hwmon_register_fan_cooling_devices(struct device *dev,
>
> cpriv->hwmon_priv = priv;
> cpriv->index = i;
> - cdev = devm_thermal_of_cooling_device_register(dev, NULL, type, cpriv,
> - &cros_ec_thermal_cooling_ops);
> + cdev = devm_thermal_cooling_device_register(dev, type, cpriv,
> + &cros_ec_thermal_cooling_ops);
> if (IS_ERR(cdev)) {
> dev_warn(dev, "failed to register fan %zu as a cooling device: %pe\n", i,
> cdev);
> diff --git a/drivers/hwmon/dell-smm-hwmon.c b/drivers/hwmon/dell-smm-hwmon.c
> index 038edffc1ac7..47b373ea6db4 100644
> --- a/drivers/hwmon/dell-smm-hwmon.c
> +++ b/drivers/hwmon/dell-smm-hwmon.c
> @@ -1161,8 +1161,8 @@ static int dell_smm_init_cdev(struct device *dev, u8 fan_num)
> if (cdata) {
> cdata->fan_num = fan_num;
> cdata->data = data;
> - cdev = devm_thermal_of_cooling_device_register(dev, NULL, name, cdata,
> - &dell_smm_cooling_ops);
> + cdev = devm_thermal_cooling_device_register(dev, name, cdata,
> + &dell_smm_cooling_ops);
> if (IS_ERR(cdev)) {
> devm_kfree(dev, cdata);
> ret = PTR_ERR(cdev);
> diff --git a/drivers/hwmon/mlxreg-fan.c b/drivers/hwmon/mlxreg-fan.c
> index 137a90dd2075..860de6cfd8a4 100644
> --- a/drivers/hwmon/mlxreg-fan.c
> +++ b/drivers/hwmon/mlxreg-fan.c
> @@ -583,8 +583,8 @@ static int mlxreg_fan_cooling_config(struct device *dev, struct mlxreg_fan *fan)
> pwm->fan = fan;
> /* Set minimal PWM speed. */
> pwm->last_hwmon_state = MLXREG_FAN_PWM_DUTY2STATE(MLXREG_FAN_MIN_DUTY);
> - pwm->cdev = devm_thermal_of_cooling_device_register(dev, NULL, mlxreg_fan_name[i],
> - pwm, &mlxreg_fan_cooling_ops);
> + pwm->cdev = devm_thermal_cooling_device_register(dev, mlxreg_fan_name[i],
> + pwm, &mlxreg_fan_cooling_ops);
> if (IS_ERR(pwm->cdev)) {
> dev_err(dev, "Failed to register cooling device\n");
> return PTR_ERR(pwm->cdev);
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core
2026-05-26 14:08 ` [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core Daniel Lezcano
@ 2026-05-29 13:26 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 13:26 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> The functions:
> - thermal_of_cooling_device_register()
> - devm_thermal_of_cooling_device_register()
>
> are specific to device tree usage but are currently implemented in
> thermal_core.c.
>
> Move them to thermal_of.c to better reflect the separation between
> generic thermal core code and OF-specific logic.
>
> This change is enabled by the recent split of the cooling device
> registration into allocation and addition phases, allowing OF-specific
> handling (such as device node assignment) to be isolated from the core.
>
> No functional change intended.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/thermal/thermal_core.c | 80 +-------------------------------
> drivers/thermal/thermal_core.h | 5 ++
> drivers/thermal/thermal_of.c | 83 ++++++++++++++++++++++++++++++++++
> include/linux/thermal.h | 49 ++++++++++++--------
> 4 files changed, 119 insertions(+), 98 deletions(-)
>
> diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
> index bb4fc3ff2ad5..28a20d4b475c 100644
> --- a/drivers/thermal/thermal_core.c
> +++ b/drivers/thermal/thermal_core.c
> @@ -963,7 +963,7 @@ static void thermal_cdev_release(struct device *dev)
> kfree(cdev);
> }
>
> -static struct thermal_cooling_device *
> +struct thermal_cooling_device *
> thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_device_ops *ops)
> {
> struct thermal_cooling_device *cdev;
> @@ -1002,7 +1002,7 @@ thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_devi
> return ERR_PTR(ret);
> }
>
> -static int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata)
> +int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata)
> {
> unsigned long current_state;
> int ret;
> @@ -1090,44 +1090,6 @@ thermal_cooling_device_register(const char *type, void *devdata,
> }
> EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
>
> -/**
> - * thermal_of_cooling_device_register() - register an OF thermal cooling device
> - * @np: a pointer to a device tree node.
> - * @type: the thermal cooling device type.
> - * @devdata: device private data.
> - * @ops: standard thermal cooling devices callbacks.
> - *
> - * This interface function adds a new thermal cooling device (fan/processor/...)
> - * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> - * to all the thermal zone devices registered at the same time.
> - * It also gives the opportunity to link the cooling device to a device tree
> - * node, so that it can be bound to a thermal zone created out of device tree.
> - *
> - * Return: a pointer to the created struct thermal_cooling_device or an
> - * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> - */
> -struct thermal_cooling_device *
> -thermal_of_cooling_device_register(struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> -{
> - struct thermal_cooling_device *cdev;
> - int ret;
> -
> - cdev = thermal_cooling_device_alloc(type, ops);
> - if (IS_ERR(cdev))
> - return cdev;
> -
> - cdev->np = np;
> -
> - ret = thermal_cooling_device_add(cdev, devdata);
> - if (ret)
> - return ERR_PTR(ret);
> -
> - return cdev;
> -}
> -EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
> -
> static void thermal_cooling_device_release(void *data)
> {
> struct thermal_cooling_device *cdev = data;
> @@ -1135,44 +1097,6 @@ static void thermal_cooling_device_release(void *data)
> thermal_cooling_device_unregister(cdev);
> }
>
> -/**
> - * devm_thermal_of_cooling_device_register() - register an OF thermal cooling
> - * device
> - * @dev: a valid struct device pointer of a sensor device.
> - * @np: a pointer to a device tree node.
> - * @type: the thermal cooling device type.
> - * @devdata: device private data.
> - * @ops: standard thermal cooling devices callbacks.
> - *
> - * This function will register a cooling device with device tree node reference.
> - * This interface function adds a new thermal cooling device (fan/processor/...)
> - * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> - * to all the thermal zone devices registered at the same time.
> - *
> - * Return: a pointer to the created struct thermal_cooling_device or an
> - * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> - */
> -struct thermal_cooling_device *
> -devm_thermal_of_cooling_device_register(struct device *dev,
> - struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> -{
> - struct thermal_cooling_device *cdev;
> - int ret;
> -
> - cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
> - if (IS_ERR(cdev))
> - return cdev;
> -
> - ret = devm_add_action_or_reset(dev, thermal_cooling_device_release, cdev);
> - if (ret)
> - return ERR_PTR(ret);
> -
> - return cdev;
> -}
> -EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
> -
> /**
> * devm_thermal_cooling_device_register() - register a thermal cooling device
> *
> diff --git a/drivers/thermal/thermal_core.h b/drivers/thermal/thermal_core.h
> index 0acb7d9587ca..e98b0aa5aacc 100644
> --- a/drivers/thermal/thermal_core.h
> +++ b/drivers/thermal/thermal_core.h
> @@ -267,6 +267,11 @@ void thermal_zone_device_critical_shutdown(struct thermal_zone_device *tz);
> void thermal_governor_update_tz(struct thermal_zone_device *tz,
> enum thermal_notify_event reason);
>
> +struct thermal_cooling_device *
> +thermal_cooling_device_alloc(const char *type, const struct thermal_cooling_device_ops *ops);
> +
> +int thermal_cooling_device_add(struct thermal_cooling_device *cdev, void *devdata);
> +
> /* Helpers */
> #define for_each_trip_desc(__tz, __td) \
> for (__td = __tz->trips; __td - __tz->trips < __tz->num_trips; __td++)
> diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
> index 75fb7663c507..8c49d449d43f 100644
> --- a/drivers/thermal/thermal_of.c
> +++ b/drivers/thermal/thermal_of.c
> @@ -510,3 +510,86 @@ void devm_thermal_of_zone_unregister(struct device *dev, struct thermal_zone_dev
> devm_thermal_of_zone_match, tz));
> }
> EXPORT_SYMBOL_GPL(devm_thermal_of_zone_unregister);
> +
> +/**
> + * thermal_of_cooling_device_register() - register an OF thermal cooling device
> + * @np: a pointer to a device tree node.
> + * @type: the thermal cooling device type.
> + * @devdata: device private data.
> + * @ops: standard thermal cooling devices callbacks.
> + *
> + * This interface function adds a new thermal cooling device (fan/processor/...)
> + * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> + * to all the thermal zone devices registered at the same time.
> + * It also gives the opportunity to link the cooling device to a device tree
> + * node, so that it can be bound to a thermal zone created out of device tree.
> + *
> + * Return: a pointer to the created struct thermal_cooling_device or an
> + * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> + */
> +struct thermal_cooling_device *
> +thermal_of_cooling_device_register(struct device_node *np,
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> +{
> + struct thermal_cooling_device *cdev;
> + int ret;
> +
> + cdev = thermal_cooling_device_alloc(type, ops);
> + if (IS_ERR(cdev))
> + return cdev;
> +
> + cdev->np = np;
> +
> + ret = thermal_cooling_device_add(cdev, devdata);
> + if (ret)
> + return ERR_PTR(ret);
> +
> + return cdev;
> +}
> +EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
> +
> +static void thermal_of_cooling_device_release(void *data)
> +{
> + struct thermal_cooling_device *cdev = data;
> +
> + thermal_cooling_device_unregister(cdev);
> +}
> +
> +/**
> + * devm_thermal_of_cooling_device_register() - register an OF thermal cooling
> + * device
> + * @dev: a valid struct device pointer of a sensor device.
> + * @np: a pointer to a device tree node.
> + * @type: the thermal cooling device type.
> + * @devdata: device private data.
> + * @ops: standard thermal cooling devices callbacks.
> + *
> + * This function will register a cooling device with device tree node reference.
> + * This interface function adds a new thermal cooling device (fan/processor/...)
> + * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
> + * to all the thermal zone devices registered at the same time.
> + *
> + * Return: a pointer to the created struct thermal_cooling_device or an
> + * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
> + */
> +struct thermal_cooling_device *
> +devm_thermal_of_cooling_device_register(struct device *dev,
> + struct device_node *np,
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> +{
> + struct thermal_cooling_device *cdev;
> + int ret;
> +
> + cdev = thermal_of_cooling_device_register(np, type, devdata, ops);
> + if (IS_ERR(cdev))
> + return cdev;
> +
> + ret = devm_add_action_or_reset(dev, thermal_of_cooling_device_release, cdev);
> + if (ret)
> + return ERR_PTR(ret);
> +
> + return cdev;
> +}
> +EXPORT_SYMBOL_GPL(devm_thermal_of_cooling_device_register);
> diff --git a/include/linux/thermal.h b/include/linux/thermal.h
> index 60e596e7d7ae..6d1862ac187f 100644
> --- a/include/linux/thermal.h
> +++ b/include/linux/thermal.h
> @@ -200,6 +200,15 @@ struct thermal_zone_device *devm_thermal_of_zone_register(struct device *dev, in
>
> void devm_thermal_of_zone_unregister(struct device *dev, struct thermal_zone_device *tz);
>
> +struct thermal_cooling_device *
> +thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops);
> +
> +struct thermal_cooling_device *
> +devm_thermal_of_cooling_device_register(struct device *dev,
> + struct device_node *np,
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops);
> #else
>
> static inline
> @@ -213,6 +222,23 @@ static inline void devm_thermal_of_zone_unregister(struct device *dev,
> struct thermal_zone_device *tz)
> {
> }
> +
> +static inline struct thermal_cooling_device *
> +thermal_of_cooling_device_register(struct device_node *np,
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> +{
> + return ERR_PTR(-ENODEV);
> +}
> +
> +static inline struct thermal_cooling_device *
> +devm_thermal_of_cooling_device_register(struct device *dev,
> + struct device_node *np,
> + const char *type, void *devdata,
> + const struct thermal_cooling_device_ops *ops)
> +{
> + return ERR_PTR(-ENODEV);
> +}
> #endif
>
> int for_each_thermal_trip(struct thermal_zone_device *tz,
> @@ -254,17 +280,11 @@ void thermal_zone_device_update(struct thermal_zone_device *,
>
> struct thermal_cooling_device *thermal_cooling_device_register(const char *,
> void *, const struct thermal_cooling_device_ops *);
> +
> struct thermal_cooling_device *
> devm_thermal_cooling_device_register(struct device *dev, const char *type, void *devdata,
> const struct thermal_cooling_device_ops *ops);
> -struct thermal_cooling_device *
> -thermal_of_cooling_device_register(struct device_node *np, const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops);
> -struct thermal_cooling_device *
> -devm_thermal_of_cooling_device_register(struct device *dev,
> - struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops);
> +
> void thermal_cooling_device_update(struct thermal_cooling_device *);
> void thermal_cooling_device_unregister(struct thermal_cooling_device *);
> struct thermal_zone_device *thermal_zone_get_zone_by_name(const char *name);
> @@ -310,18 +330,7 @@ thermal_cooling_device_register(const char *type, void *devdata,
> const struct thermal_cooling_device_ops *ops)
> { return ERR_PTR(-ENODEV); }
> static inline struct thermal_cooling_device *
> -thermal_of_cooling_device_register(struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> -{ return ERR_PTR(-ENODEV); }
> -static inline struct thermal_cooling_device *
> -devm_thermal_of_cooling_device_register(struct device *dev,
> - struct device_node *np,
> - const char *type, void *devdata,
> - const struct thermal_cooling_device_ops *ops)
> -{
> - return ERR_PTR(-ENODEV);
> -}
> +
> static inline void thermal_cooling_device_unregister(
> struct thermal_cooling_device *cdev)
> { }
I would change the order of patch 04/10 and this one.
Other than that:
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF
2026-05-26 14:08 ` [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF Daniel Lezcano
@ 2026-05-29 13:27 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 13:27 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> The device node pointer stored in struct thermal_cooling_device is
> only used by the OF-specific thermal code to associate cooling devices
> with thermal zones defined in device tree.
>
> Now that OF and non-OF registration paths are separated and non-OF
> users no longer rely on devm_thermal_of_cooling_device_register() with
> a NULL device node, the np field is no longer required for non-OF
> configurations.
>
> Make this field conditional on CONFIG_THERMAL_OF to reduce memory
> footprint and better reflect its usage.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> include/linux/thermal.h | 4 +++-
> 1 file changed, 3 insertions(+), 1 deletion(-)
>
> diff --git a/include/linux/thermal.h b/include/linux/thermal.h
> index fc3f4a098370..60e596e7d7ae 100644
> --- a/include/linux/thermal.h
> +++ b/include/linux/thermal.h
> @@ -125,7 +125,6 @@ struct thermal_cooling_device {
> const char *type;
> unsigned long max_state;
> struct device device;
> - struct device_node *np;
> void *devdata;
> void *stats;
> const struct thermal_cooling_device_ops *ops;
> @@ -133,6 +132,9 @@ struct thermal_cooling_device {
> struct mutex lock; /* protect thermal_instances list */
> struct list_head thermal_instances;
> struct list_head node;
> +#ifdef CONFIG_THERMAL_OF
> + struct device_node *np;
> +#endif
> #ifdef CONFIG_THERMAL_DEBUGFS
> struct thermal_debugfs *debugfs;
> #endif
I've done compilation w/o THERMAL_OF set because it
was a bit odd...
It triggers an issue in the thermal_core.c at:
cdev->np which is left. This might break some bisect
in the suture if that would be the case.
drivers/thermal/thermal_core.c: In function
‘thermal_of_cooling_device_register’:
drivers/thermal/thermal_core.c:1121:13: error: ‘struct
thermal_cooling_device’ has no member named ‘np’
1121 | cdev->np = np;
| ^~
make[4]: *** [scripts/Makefile.build:289:
drivers/thermal/thermal_core.o] Error 1
make[3]: *** [scripts/Makefile.build:548: drivers/thermal] Error 2
make[3]: *** Waiting for unfinished jobs....
Let's maybe change the order with patch 05/10 ?
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function
2026-05-26 14:08 ` [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function Daniel Lezcano
@ 2026-05-29 15:17 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:17 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon, Krzysztof Kozlowski,
Thierry Reding, Nathan Chancellor, Nick Desaulniers,
Bill Wendling, Justin Stitt, Ingo Molnar, Thomas Gleixner,
Jiri Slaby (SUSE),
Mikko Perttunen, Svyatoslav Ryhel,
moderated list:ARM/ASPEED MACHINE SUPPORT,
moderated list:ARM/ASPEED MACHINE SUPPORT,
moderated list:ARM/NUVOTON NPCM ARCHITECTURE,
open list:TEGRA ARCHITECTURE SUPPORT,
open list:ARM/QUALCOMM MAILING LIST,
open list:KHADAS MCU MFD DRIVER,
open list:CLANG/LLVM BUILD SUPPORT
On 5/26/26 15:08, Daniel Lezcano wrote:
> To clarify that the function operates on child nodes, rename:
>
> devm_thermal_of_cooling_device_register()
> |
> v
> devm_thermal_of_child_cooling_device_register()
>
> Used the command:
>
> find . -type f -name '*.[ch]' -exec \
> sed -i 's/devm_thermal_of_cooling_device_register/\
> devm_thermal_of_child_cooling_device_register/g' {} \;
>
> Did not used clang-format-diff because it does not indent correctly
> and checkpatch complained. Manually reindented to make checkpatch
> happy
>
> This prepares for upcoming support of cooling devices identified by
> an ID rather than device tree child nodes.
>
> No functional change.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/hwmon/amc6821.c | 2 +-
> drivers/hwmon/aspeed-pwm-tacho.c | 5 +++--
> drivers/hwmon/emc2305.c | 6 +++---
> drivers/hwmon/gpio-fan.c | 6 ++++--
> drivers/hwmon/max6650.c | 6 +++---
> drivers/hwmon/npcm750-pwm-fan.c | 6 ++++--
> drivers/hwmon/pwm-fan.c | 5 +++--
> drivers/hwmon/qnap-mcu-hwmon.c | 6 +++---
> drivers/hwmon/tc654.c | 5 +++--
> drivers/memory/tegra/tegra210-emc-core.c | 4 ++--
> drivers/soc/qcom/qcom_aoss.c | 2 +-
> drivers/thermal/khadas_mcu_fan.c | 7 ++++---
> drivers/thermal/tegra/soctherm.c | 6 +++---
> drivers/thermal/thermal_of.c | 15 +++++++++------
> include/linux/thermal.h | 16 ++++++++--------
> 15 files changed, 54 insertions(+), 43 deletions(-)
>
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 07/10] thermal/of: Add cooling device ID support
2026-05-26 14:08 ` [PATCH v4 07/10] thermal/of: Add cooling device ID support Daniel Lezcano
@ 2026-05-29 15:18 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:18 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon,
moderated list:DRM DRIVERS FOR VIVANTE GPU IP,
open list:DRM DRIVERS FOR VIVANTE GPU IP
On 5/26/26 15:08, Daniel Lezcano wrote:
> Introduce an identifier (cdev_id) for cooling devices registered from
> device tree.
>
> This prepares support for a new DT binding where cooling devices are
> identified by a tuple (device node, ID), instead of relying on child
> nodes.
>
> Existing users are updated to pass a default ID of 0, preserving the
> current behavior.
>
> Future changes will extend the cooling map parsing to match cooling
> devices based on both the device node and the ID.
>
> No functional change intended.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/gpu/drm/etnaviv/etnaviv_gpu.c | 5 +++--
> drivers/thermal/cpufreq_cooling.c | 2 +-
> drivers/thermal/cpuidle_cooling.c | 2 +-
> drivers/thermal/devfreq_cooling.c | 2 +-
> drivers/thermal/thermal_of.c | 14 ++++++++------
> include/linux/thermal.h | 6 ++++--
> 6 files changed, 18 insertions(+), 13 deletions(-)
>
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper
2026-05-26 14:08 ` [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper Daniel Lezcano
@ 2026-05-29 15:21 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:21 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> Extend the OF cooling device registration to support an explicit
> cooling device identifier (cdev_id), preparing for upcoming DT
> bindings where cooling devices are identified by a tuple (device node,
> id) instead of relying on child nodes.
>
> Introduce a new helper:
>
> devm_thermal_of_cooling_device_register()
>
> which registers a cooling device using the device's of_node and an
> explicit cdev_id. This complements the existing
> devm_thermal_of_child_cooling_device_register() helper, which
> remains dedicated to the legacy child-node based bindings.
>
> Internally, factorize the devm registration logic into a common
> helper to avoid code duplication.
>
> Existing users are unaffected, as the child-based helper continues
> to pass a default cdev_id of 0, preserving current behavior.
>
> This change is a preparatory step for supporting indexed cooling
> devices in thermal OF bindings.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/thermal/thermal_of.c | 58 ++++++++++++++++++++++++++++--------
> include/linux/thermal.h | 13 ++++++++
> 2 files changed, 59 insertions(+), 12 deletions(-)
>
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec
2026-05-26 14:08 ` [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec Daniel Lezcano
@ 2026-05-29 15:25 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:25 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/26/26 15:08, Daniel Lezcano wrote:
> Extend the cooling device specifier parsing to support an optional
> cooling device identifier (cdev_id).
>
> Two formats are now supported:
>
> - Legacy format:
> <&cdev lower upper>
>
> - Indexed format:
> <&cdev cdev_id lower upper>
>
> When the indexed format is used, both the device node and the
> cdev_id must match in order to bind a cooling device to a thermal
> zone. The legacy format continues to match on the device node only,
> preserving backward compatibility.
>
> Update the parsing logic accordingly to handle both formats and
> extract the mitigation limits from the appropriate arguments.
>
> This is a preparatory step for upcoming DT bindings describing
> cooling devices using (device node, id) tuples instead of child
> nodes.
>
> No functional change for existing device trees.
>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> ---
> drivers/thermal/thermal_of.c | 26 ++++++++++++++++++++++----
> 1 file changed, 22 insertions(+), 4 deletions(-)
>
> diff --git a/drivers/thermal/thermal_of.c b/drivers/thermal/thermal_of.c
> index 3584024b76f5..100fd8a0c8ce 100644
> --- a/drivers/thermal/thermal_of.c
> +++ b/drivers/thermal/thermal_of.c
> @@ -259,16 +259,34 @@ static bool thermal_of_get_cooling_spec(struct device_node *map_np, int index,
>
> of_node_put(cooling_spec.np);
>
> - if (cooling_spec.args_count < 2) {
> - pr_err("wrong reference to cooling device, missing limits\n");
> + /*
> + * There are two formats:
> + * - Legacy format : <&cdev lower upper>
> + * - New format : <&cdev cdev_id lower upper>
> + *
> + * With the new format, along with the device node pointer,
> + * the cdev_id must match with the cooling device cdev_id in
> + * order to bind
> + */
> + if (cooling_spec.args_count < 2 || cooling_spec.args_count > 3) {
> + pr_err("Invalid number of cooling device parameters\n");
> return false;
> }
>
> if (cooling_spec.np != cdev->np)
> return false;
>
> - c->lower = cooling_spec.args[0];
> - c->upper = cooling_spec.args[1];
> + if (cooling_spec.args_count == 3 &&
> + cooling_spec.args[0] != cdev->cdev_id)
> + return false;
> +
> + if (cooling_spec.args_count != 3) {
A bit odd to read the negation format while still having 'else'.
> + c->lower = cooling_spec.args[0];
> + c->upper = cooling_spec.args[1];
> + } else {
> + c->lower = cooling_spec.args[1];
> + c->upper = cooling_spec.args[2];
> + }
> c->weight = weight;
>
> return true;
Just a minor comment, which can be ignored, fill free to do so
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device
2026-05-26 14:08 ` [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device Daniel Lezcano
@ 2026-05-29 15:26 ` Lukasz Luba
0 siblings, 0 replies; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:26 UTC (permalink / raw)
To: Daniel Lezcano, rafael, daniel.lezcano
Cc: Zhang Rui, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
Lucas Stach, Russell King, Christian Gmeiner, David Airlie,
Simona Vetter, Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon, Gaurav Kohli,
Krzysztof Kozlowski,
open list:OPEN FIRMWARE AND FLATTENED DEVICE TREE BINDINGS
On 5/26/26 15:08, Daniel Lezcano wrote:
> From: Gaurav Kohli <gaurav.kohli@oss.qualcomm.com>
>
> Extend the thermal cooling device binding to support a 3 cells specifier
> along with the 2 cells format.
>
> Update #cooling-cells property to enum to support both 2 and 3 arguments.
>
> Fix pwm-fan.yaml to restrict the number of cells to 'const: 2'
>
> Signed-off-by: Gaurav Kohli <gaurav.kohli@oss.qualcomm.com>
> Signed-off-by: Daniel Lezcano <daniel.lezcano@oss.qualcomm.com>
> Reviewed-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
> ---
> Documentation/devicetree/bindings/hwmon/pwm-fan.yaml | 3 ++-
> .../bindings/thermal/thermal-cooling-devices.yaml | 8 ++++++--
> .../devicetree/bindings/thermal/thermal-zones.yaml | 3 ++-
> 3 files changed, 10 insertions(+), 4 deletions(-)
>
> diff --git a/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml b/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
> index a84cc3a4cfdc..6a24851fd80d 100644
> --- a/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
> +++ b/Documentation/devicetree/bindings/hwmon/pwm-fan.yaml
> @@ -63,7 +63,8 @@ properties:
> description: The PWM that is used to control the fan.
> maxItems: 1
>
> - "#cooling-cells": true
> + "#cooling-cells":
> + const: 2
>
> required:
> - compatible
> diff --git a/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml b/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
> index b9022f1613d8..28f5818f1e60 100644
> --- a/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
> +++ b/Documentation/devicetree/bindings/thermal/thermal-cooling-devices.yaml
> @@ -44,10 +44,14 @@ select: true
> properties:
> "#cooling-cells":
> description:
> - Must be 2, in order to specify minimum and maximum cooling state used in
> + Must be 2 or 3. If 2, specifies minimum and maximum cooling state used in
> the cooling-maps reference. The first cell is the minimum cooling state
> and the second cell is the maximum cooling state requested.
> - const: 2
> + If 3, the first cell specifies the thermal mitigation device specifier
> + index for devices that support multiple thermal mitigation mechanisms.
> + The two other cells are respectively the minimum cooling state and the
> + maximum cooling state.
> + enum: [2, 3]
>
> additionalProperties: true
>
> diff --git a/Documentation/devicetree/bindings/thermal/thermal-zones.yaml b/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
> index 07d9f576ffe7..999ad40a20d5 100644
> --- a/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
> +++ b/Documentation/devicetree/bindings/thermal/thermal-zones.yaml
> @@ -211,7 +211,8 @@ patternProperties:
> device. Using the THERMAL_NO_LIMIT (-1UL) constant in the
> cooling-device phandle limit specifier lets the framework
> use the minimum and maximum cooling state for that cooling
> - device automatically.
> + device automatically. If three arguments are specified,
> + the first argument is the cooling device specifier.
>
> contribution:
> $ref: /schemas/types.yaml#/definitions/uint32
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-29 12:41 ` Daniel Lezcano
@ 2026-05-29 15:29 ` Lukasz Luba
2026-05-29 15:31 ` Daniel Lezcano
0 siblings, 1 reply; 28+ messages in thread
From: Lukasz Luba @ 2026-05-29 15:29 UTC (permalink / raw)
To: Daniel Lezcano, Rafael J. Wysocki
Cc: daniel.lezcano, Zhang Rui, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
Hi Rafael and Daniel,
On 5/29/26 13:41, Daniel Lezcano wrote:
> On 5/29/26 14:35, Rafael J. Wysocki wrote:
>> Hi Daniel,
>>
>> On Fri, May 29, 2026 at 10:35 AM Daniel Lezcano
>> <daniel.lezcano@oss.qualcomm.com> wrote:
>>>
>>>
>>> Hi Rafael,
>>>
>>> On 5/26/26 16:08, Daniel Lezcano wrote:
>>>
>>> [ ... ]
>>>
>>>> ---
>>>> Changelog:
>>>> - V4
>>>> - Reworked splitted functions to register a cooling device and
>>>> merged separately
>>>
>>> Are you fine with the thermal core changes in this series ?
>>
>> Generally, yes, I am, but let me have one more look at it.
>>
>>> Is it ok if I pick the series in my branch (and may be send a early
>>> PR) ?
>>
>> I have no comments, I'll respond with an Acked-by to it later today.
>>
>> Thanks!
>
> Thanks
I have re-ordered the patch 4 <-> 5 and the compilation issue goes away.
If you decide to do that feel free to add my tag to the current patch
04/10:
Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
Regards,
Lukasz
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-29 15:29 ` Lukasz Luba
@ 2026-05-29 15:31 ` Daniel Lezcano
2026-05-29 17:34 ` Rafael J. Wysocki
0 siblings, 1 reply; 28+ messages in thread
From: Daniel Lezcano @ 2026-05-29 15:31 UTC (permalink / raw)
To: Lukasz Luba, Rafael J. Wysocki
Cc: daniel.lezcano, Zhang Rui, Rob Herring, Krzysztof Kozlowski,
Conor Dooley, Lucas Stach, Russell King, Christian Gmeiner,
David Airlie, Simona Vetter, Guenter Roeck, Joel Stanley,
Andrew Jeffery, Thomas Weißschuh, Benson Leung,
Pali Rohár, Avi Fishman, Tomer Maimon, Tali Perry,
Patrick Venture, Nancy Yuen, Benjamin Fair, Heiko Stuebner,
Thierry Reding, Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On 5/29/26 17:29, Lukasz Luba wrote:
> Hi Rafael and Daniel,
>
> On 5/29/26 13:41, Daniel Lezcano wrote:
>> On 5/29/26 14:35, Rafael J. Wysocki wrote:
>>> Hi Daniel,
>>>
>>> On Fri, May 29, 2026 at 10:35 AM Daniel Lezcano
>>> <daniel.lezcano@oss.qualcomm.com> wrote:
>>>>
>>>>
>>>> Hi Rafael,
>>>>
>>>> On 5/26/26 16:08, Daniel Lezcano wrote:
>>>>
>>>> [ ... ]
>>>>
>>>>> ---
>>>>> Changelog:
>>>>> - V4
>>>>> - Reworked splitted functions to register a cooling device and
>>>>> merged separately
>>>>
>>>> Are you fine with the thermal core changes in this series ?
>>>
>>> Generally, yes, I am, but let me have one more look at it.
>>>
>>>> Is it ok if I pick the series in my branch (and may be send a early
>>>> PR) ?
>>>
>>> I have no comments, I'll respond with an Acked-by to it later today.
>>>
>>> Thanks!
>>
>> Thanks
>
> I have re-ordered the patch 4 <-> 5 and the compilation issue goes away.
> If you decide to do that feel free to add my tag to the current patch
> 04/10:
>
> Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
Thanks Lukasz !
^ permalink raw reply [flat|nested] 28+ messages in thread
* Re: [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF
2026-05-29 15:31 ` Daniel Lezcano
@ 2026-05-29 17:34 ` Rafael J. Wysocki
0 siblings, 0 replies; 28+ messages in thread
From: Rafael J. Wysocki @ 2026-05-29 17:34 UTC (permalink / raw)
To: Daniel Lezcano
Cc: Lukasz Luba, Rafael J. Wysocki, daniel.lezcano, Zhang Rui,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, Lucas Stach,
Russell King, Christian Gmeiner, David Airlie, Simona Vetter,
Guenter Roeck, Joel Stanley, Andrew Jeffery,
Thomas Weißschuh, Benson Leung, Pali Rohár,
Avi Fishman, Tomer Maimon, Tali Perry, Patrick Venture,
Nancy Yuen, Benjamin Fair, Heiko Stuebner, Thierry Reding,
Jonathan Hunter, Bjorn Andersson, Konrad Dybcio,
Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong, Amit Kucheria,
linux-pm, linux-kernel, linux-hwmon
On Fri, May 29, 2026 at 5:31 PM Daniel Lezcano
<daniel.lezcano@oss.qualcomm.com> wrote:
>
> On 5/29/26 17:29, Lukasz Luba wrote:
> > Hi Rafael and Daniel,
> >
> > On 5/29/26 13:41, Daniel Lezcano wrote:
> >> On 5/29/26 14:35, Rafael J. Wysocki wrote:
> >>> Hi Daniel,
> >>>
> >>> On Fri, May 29, 2026 at 10:35 AM Daniel Lezcano
> >>> <daniel.lezcano@oss.qualcomm.com> wrote:
> >>>>
> >>>>
> >>>> Hi Rafael,
> >>>>
> >>>> On 5/26/26 16:08, Daniel Lezcano wrote:
> >>>>
> >>>> [ ... ]
> >>>>
> >>>>> ---
> >>>>> Changelog:
> >>>>> - V4
> >>>>> - Reworked splitted functions to register a cooling device and
> >>>>> merged separately
> >>>>
> >>>> Are you fine with the thermal core changes in this series ?
> >>>
> >>> Generally, yes, I am, but let me have one more look at it.
> >>>
> >>>> Is it ok if I pick the series in my branch (and may be send a early
> >>>> PR) ?
> >>>
> >>> I have no comments, I'll respond with an Acked-by to it later today.
> >>>
> >>> Thanks!
> >>
> >> Thanks
> >
> > I have re-ordered the patch 4 <-> 5 and the compilation issue goes away.
> > If you decide to do that feel free to add my tag to the current patch
> > 04/10:
> >
> > Reviewed-by: Lukasz Luba <lukasz.luba@arm.com>
>
> Thanks Lukasz !
So with the change mentioned above by Lukasz, please feel free to add
Acked-by: Rafael J. Wysocki (Intel) <rafael@kernel.org>
to the series and take it into your branch.
And yes, an early PR would be welcome.
^ permalink raw reply [flat|nested] 28+ messages in thread
* [PATCH v3 00/11] Support cooling device with ID in the OF
@ 2026-04-29 16:14 Daniel Lezcano
0 siblings, 0 replies; 28+ messages in thread
From: Daniel Lezcano @ 2026-04-29 16:14 UTC (permalink / raw)
To: rafael, daniel.lezcano
Cc: gaurav.kohli, Zhang Rui, Lukasz Luba, Rob Herring,
Krzysztof Kozlowski, Conor Dooley, Lucas Stach, Russell King,
Christian Gmeiner, David Airlie, Simona Vetter, Guenter Roeck,
Joel Stanley, Andrew Jeffery, Thomas Weißschuh,
Benson Leung, Pali Rohár, Avi Fishman, Tomer Maimon,
Tali Perry, Patrick Venture, Nancy Yuen, Benjamin Fair,
Heiko Stuebner, Thierry Reding, Jonathan Hunter, Bjorn Andersson,
Konrad Dybcio, Amit Daniel Kachhap, Viresh Kumar, Neil Armstrong,
Amit Kucheria, linux-pm, linux-kernel, linux-hwmon
Ultra short description. Dt Cooling device description:
Old: <&mycdev min max>
New: <&mycdev min max> OR/AND <&mycdev id min max>
Depends on series:
https://lore.kernel.org/all/20260424160019.41710-1-daniel.lezcano@oss.qualcomm.com/
A cooling device can be a single cooling device or a cooling device
controller with multiple cooling devices attached to it.
The thermal framework builds a connection between a cooling device and
a thermal zone when there is a trip point to be mitigated by the
cooling device. In the Linux kernel thermal semantic, the action of
connecting the cooling device and the thermal zone is called a
binding.
The description of the aforementioned connection depends on the
firmware definition and in our case it is through the device tree. The
cooling map describes this connection.
How is it done ?
For a single cooling device, the DT describes:
* A cooling device:
mycooling_device {
...
};
* A cooling map in a thermal zone
mythermal_zone {
...
cooling-maps {
map0 {
...
cooling-device = <&mycooling_device min max>;
...
};
}
...
};
For a cooling device controller with multiple cooling devices
attached, the DT describes:
* A cooling device controller:
mycooling_device_ctrl {
mycooling_device1 {
...
};
mycooling_device2 {
...
};
...
mycooling_deviceN {
...
};
};
* A cooling map in a thermal zone
mythermal_zone {
...
cooling-maps {
map0 {
...
cooling-device = <&mycooling_device1 min max>;
...
};
}
...
};
When the cooling device "mycooling_device" is registered, then the
binding function will browse all the cooling maps and matches the node
device pointer to do the association (the pĥandle in the cooling map
vs the cooling device node).
That is how the connection between the cooling device and the thermal
zone is done.
DT maintainers consider the above description with child nodes is
incorrect if a child node doesn't have its own bindings as explained
in the documentation [1].
Gaurav Kohli posted a series to support the QMI TMD (Qualcomm
Messaging Interface based Thermal Mitigation Devices) [2]. This device
is a dedicated, centralized cooling device controller managing a set
of cooling devices.
Because of the above restrictions with child nodes there is no DT
bindings allowing to do the connection between the cooling device
inside the cooling device controller and a thermal zone.
A QMI TMD is not a standalone cooling device neither a multiple
cooling devices with their own DT description.
For this reason, the proposed changes with child nodes has been
rejected [3].
As a solution, it has been proposed to fold all these child nodes into
an array and add an id in the cooling maps to identify the cooling
device entry in the controller node [4].
Given the thermal zone has the same mechanism [5], that is a phandle
to a sensor node and an sensor specifier. The proposed approach makes
sense as it is consistent with the thermal zone description.
This series provides a cleanup around the usage of the OF code which
is interleaved with non-OF code. The OF and the non-OF code are
separated and remain self-encapsulated.
Then the function to register a cooling device is renamed to reflect
the legacy usage and a new function is introduced with the id
parameter.
Finally, the DT bindings is updated with the new format and the
thermal OF is changed to handle the new DT bindings.
Given the trivial changes impacting the files outside of the thermal
framework, this series is designed to have all changes going through
the thermal tree.
Thanks!
[1] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/devicetree/bindings/writing-bindings.rst
[2] https://lore.kernel.org/all/20260127155722.2797783-1-gaurav.kohli@oss.qualcomm.com/
[3] https://lore.kernel.org/all/546faeda-d896-403c-a449-5c9b0cd7159e@kernel.org/
[4] https://lore.kernel.org/all/74f59ef0-ead7-483f-a80e-a3da2f6ebcdb@oss.qualcomm.com/
[5] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/devicetree/bindings/thermal/thermal-zones.yaml#n99
---
Changelog:
- V3
- Reordered and reworked the patches to be git bisect safe
- Reworked devm usage by using a more adequate function doing the
same as the group of calls to devm*
- Pass an init callback instead of moving
thermal_cooling_device_init_complete() out of the function and
calling it in different places
- Sent separetely changes to the tegra soctherm driver
- V2
- Added stubs for OF functions in order to prevent to break the git
bisectability compilation
- Added missing call to thermal_cooling_device_init_complete() in
devm_thermal_of_cooling_device_register()
- Fixed assymetry in devm_ calls for the tegra/soctherm() driver
- Fixed kernel documentation for API changes
- Added missing static inline for a API stub
- Hardened the test with two or three arguments in the cooling spec
- Narrowed const: 2 strict in pwm-fan
---
Daniel Lezcano (10):
thermal/core: Use devm_add_action_or_reset() when registering a
cooling device
Add a non-OF registering funciton
thermal/of: Move the node pointer assignation in the OF code file
hwmon:: Use non-OF thermal cooling device register function
thermal/core: Put of_node field cooling device structure under Kconfig
option
thermal/of: Move OF code where it belongs to
thermal/of: Rename the devm_thermal_of_cooling_device_register()
function
thermal/of: Introduce cooling device of_index
thermal/of: Pass the of_index and add a function to register with an
index
thermal/of: Process cooling device index in cooling-spec
Gaurav Kohli (1):
dt-bindings: thermal: cooling-devices: Update support for 3 cells
cooling device
.../devicetree/bindings/hwmon/pwm-fan.yaml | 3 +-
.../thermal/thermal-cooling-devices.yaml | 8 +-
.../bindings/thermal/thermal-zones.yaml | 3 +-
drivers/gpu/drm/etnaviv/etnaviv_gpu.c | 5 +-
drivers/hwmon/amc6821.c | 2 +-
drivers/hwmon/aspeed-pwm-tacho.c | 5 +-
drivers/hwmon/cros_ec_hwmon.c | 4 +-
drivers/hwmon/dell-smm-hwmon.c | 4 +-
drivers/hwmon/emc2305.c | 6 +-
drivers/hwmon/gpio-fan.c | 6 +-
drivers/hwmon/max6650.c | 6 +-
drivers/hwmon/mlxreg-fan.c | 4 +-
drivers/hwmon/npcm750-pwm-fan.c | 6 +-
drivers/hwmon/pwm-fan.c | 5 +-
drivers/hwmon/qnap-mcu-hwmon.c | 6 +-
drivers/hwmon/tc654.c | 5 +-
drivers/memory/tegra/tegra210-emc-core.c | 4 +-
drivers/soc/qcom/qcom_aoss.c | 2 +-
drivers/thermal/cpufreq_cooling.c | 2 +-
drivers/thermal/cpuidle_cooling.c | 2 +-
drivers/thermal/devfreq_cooling.c | 2 +-
drivers/thermal/khadas_mcu_fan.c | 7 +-
drivers/thermal/tegra/soctherm.c | 6 +-
drivers/thermal/thermal_core.c | 106 ++++--------
drivers/thermal/thermal_core.h | 6 +
drivers/thermal/thermal_of.c | 157 +++++++++++++++++-
include/linux/thermal.h | 71 ++++++--
27 files changed, 303 insertions(+), 140 deletions(-)
--
2.43.0
^ permalink raw reply [flat|nested] 28+ messages in thread
end of thread, other threads:[~2026-05-29 17:34 UTC | newest]
Thread overview: 28+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-05-26 14:08 [PATCH v3 00/11] Support cooling device with ID in the OF Daniel Lezcano
2026-05-26 14:08 ` [PATCH v4 01/10] thermal/core: Introduce non-OF thermal_cooling_device_register() Daniel Lezcano
2026-05-29 9:47 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 02/10] thermal/core: Add devm_thermal_cooling_device_register() Daniel Lezcano
2026-05-29 12:55 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 03/10] hwmon: Use non-OF thermal cooling device registration API Daniel Lezcano
2026-05-29 12:55 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 04/10] thermal/core: Make cooling device OF node conditional on CONFIG_THERMAL_OF Daniel Lezcano
2026-05-29 13:27 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 05/10] thermal/of: Move cooling device OF helpers out of thermal core Daniel Lezcano
2026-05-29 13:26 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 06/10] thermal/of: Rename the devm_thermal_of_cooling_device_register() function Daniel Lezcano
2026-05-29 15:17 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 07/10] thermal/of: Add cooling device ID support Daniel Lezcano
2026-05-29 15:18 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 08/10] thermal/of: Pass cdev_id and introduce devm registration helper Daniel Lezcano
2026-05-29 15:21 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 09/10] thermal/of: Support cooling device ID in cooling-spec Daniel Lezcano
2026-05-29 15:25 ` Lukasz Luba
2026-05-26 14:08 ` [PATCH v4 10/10] dt-bindings: thermal: cooling-devices: Update support for 3 cells cooling device Daniel Lezcano
2026-05-29 15:26 ` Lukasz Luba
2026-05-29 8:35 ` [PATCH vs/3/4/ 00/11] Support cooling device with ID in the OF Daniel Lezcano
2026-05-29 12:35 ` Rafael J. Wysocki
2026-05-29 12:41 ` Daniel Lezcano
2026-05-29 15:29 ` Lukasz Luba
2026-05-29 15:31 ` Daniel Lezcano
2026-05-29 17:34 ` Rafael J. Wysocki
-- strict thread matches above, loose matches on Subject: below --
2026-04-29 16:14 [PATCH v3 " Daniel Lezcano
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Powered by JetHome