Commit a8460ba5 authored by Rafael J. Wysocki's avatar Rafael J. Wysocki

Merge tag 'thermal-v6.5-rc1' of...

Merge tag 'thermal-v6.5-rc1' of ssh://gitolite.kernel.org/pub/scm/linux/kernel/git/thermal/linux into thermal

Pull thermal control updates for 6.5-rc1 from Daniel Lezcano:

"- Add DT bindings for SM6375, MSM8226 and QCM2290 Qcom platforms (Konrad
   Dybcio)

 - Add DT bindings and support for QCom MSM8226 (Matti Lehtimäki)

 - Add DT bindings for QCom ipq9574 (Praveenkumar I)

 - Convert bcm2835 DT bindings to the yaml schema (Stefan Wahren)

 - Allow selecting the bang-bang governor as default (Thierry Reding)

 - Refactor and prepare the code to set the scene for RCar Gen4
   (Wolfram Sang)

 - Cleanup and fixes for the QCom tsens drivers. Add DT bindings and
   calibration for the MSM8909 platform (Stephan Gerhold)

 - Revert a patch introducing a wrong usage of devm_of_iomap() on the
   Mediatek platform (Ricardo Cañuelo)

 - Fix the clock vs reset ordering in order to conform to the
   documentation on the sun8i (Christophe JAILLET)

 - Prevent setting up undocumented registers, enable the only described
   sensors and add the version 2.1 on the Qoriq sensor (Peng Fan)

 - Add DT bindings and support for the Armada AP807 (Alex Leibovich)

 - Update the mlx5 driver with the recent thermal changes (Daniel
   Lezcano)

 - Convert to platform remove callback returning void on STM32 (Uwe
   Kleine-König)

 - Add an error information printing for devm_thermal_add_hwmon_sysfs()
   and remove the error from the Sun8i, Amlogic, i.MX, TI, K3, Tegra,
   Qoriq, Mediateka and QCom (Yangtao Li)

 - Register as hwmon sensor for the Generic ADC (Chen-Yu Tsai)

 - Use the dev_err_probe() function in the QCom tsens alarm driver
   (Luca Weiss)"

* tag 'thermal-v6.5-rc1' of ssh://gitolite.kernel.org/pub/scm/linux/kernel/git/thermal/linux: (38 commits)
  thermal/drivers/qcom/temp-alarm: Use dev_err_probe
  thermal/drivers/generic-adc: Register thermal zones as hwmon sensors
  thermal/drivers/mediatek/lvts_thermal: Remove redundant msg in lvts_ctrl_start()
  thermal/drivers/qcom: Remove redundant msg at probe time
  thermal/drivers/ti-soc: Remove redundant msg in ti_thermal_expose_sensor()
  thermal/drivers/qoriq: Remove redundant msg in qoriq_tmu_register_tmu_zone()
  thermal/drivers/tegra: Remove redundant msg in tegra_tsensor_register_channel()
  drivers/thermal/k3: Remove redundant msg in k3_bandgap_probe()
  thermal/drivers/imx: Remove redundant msg in imx8mm_tmu_probe() and imx_sc_thermal_probe()
  thermal/drivers/amlogic: Remove redundant msg in amlogic_thermal_probe()
  thermal/drivers/sun8i: Remove redundant msg in sun8i_ths_register()
  thermal/hwmon: Add error information printing for devm_thermal_add_hwmon_sysfs()
  thermal/drivers/stm32: Convert to platform remove callback returning void
  net/mlx5: Update the driver with the recent thermal changes
  thermal/drivers/armada: Add support for AP807 thermal data
  dt-bindings: armada-thermal: Add armada-ap807-thermal compatible
  thermal/drivers/qoriq: Support version 2.1
  thermal/drivers/qoriq: Only enable supported sensors
  thermal/drivers/qoriq: No need to program site adjustment register
  thermal/drivers/mediatek/lvts_thermal: Register thermal zones as hwmon sensors
  ...
parents f46117bf 57c9eaa4
...@@ -8,6 +8,7 @@ Required properties: ...@@ -8,6 +8,7 @@ Required properties:
* marvell,armada380-thermal * marvell,armada380-thermal
* marvell,armadaxp-thermal * marvell,armadaxp-thermal
* marvell,armada-ap806-thermal * marvell,armada-ap806-thermal
* marvell,armada-ap807-thermal
* marvell,armada-cp110-thermal * marvell,armada-cp110-thermal
Note: these bindings are deprecated for AP806/CP110 and should instead Note: these bindings are deprecated for AP806/CP110 and should instead
......
Binding for Thermal Sensor driver for BCM2835 SoCs.
Required parameters:
-------------------
compatible: should be one of: "brcm,bcm2835-thermal",
"brcm,bcm2836-thermal" or "brcm,bcm2837-thermal"
reg: Address range of the thermal registers.
clocks: Phandle of the clock used by the thermal sensor.
#thermal-sensor-cells: should be 0 (see Documentation/devicetree/bindings/thermal/thermal-sensor.yaml)
Example:
thermal-zones {
cpu_thermal: cpu-thermal {
polling-delay-passive = <0>;
polling-delay = <1000>;
thermal-sensors = <&thermal>;
trips {
cpu-crit {
temperature = <80000>;
hysteresis = <0>;
type = "critical";
};
};
coefficients = <(-538) 407000>;
cooling-maps {
};
};
};
thermal: thermal@7e212000 {
compatible = "brcm,bcm2835-thermal";
reg = <0x7e212000 0x8>;
clocks = <&clocks BCM2835_CLOCK_TSENS>;
#thermal-sensor-cells = <0>;
};
# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
%YAML 1.2
---
$id: http://devicetree.org/schemas/thermal/brcm,bcm2835-thermal.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: Broadcom BCM2835 thermal sensor
maintainers:
- Stefan Wahren <stefan.wahren@i2se.com>
allOf:
- $ref: thermal-sensor.yaml#
properties:
compatible:
enum:
- brcm,bcm2835-thermal
- brcm,bcm2836-thermal
- brcm,bcm2837-thermal
reg:
maxItems: 1
clocks:
maxItems: 1
"#thermal-sensor-cells":
const: 0
unevaluatedProperties: false
required:
- compatible
- reg
- clocks
- '#thermal-sensor-cells'
examples:
- |
#include <dt-bindings/clock/bcm2835.h>
thermal@7e212000 {
compatible = "brcm,bcm2835-thermal";
reg = <0x7e212000 0x8>;
clocks = <&clocks BCM2835_CLOCK_TSENS>;
#thermal-sensor-cells = <0>;
};
...@@ -29,6 +29,8 @@ properties: ...@@ -29,6 +29,8 @@ properties:
items: items:
- enum: - enum:
- qcom,mdm9607-tsens - qcom,mdm9607-tsens
- qcom,msm8226-tsens
- qcom,msm8909-tsens
- qcom,msm8916-tsens - qcom,msm8916-tsens
- qcom,msm8939-tsens - qcom,msm8939-tsens
- qcom,msm8974-tsens - qcom,msm8974-tsens
...@@ -48,6 +50,7 @@ properties: ...@@ -48,6 +50,7 @@ properties:
- qcom,msm8953-tsens - qcom,msm8953-tsens
- qcom,msm8996-tsens - qcom,msm8996-tsens
- qcom,msm8998-tsens - qcom,msm8998-tsens
- qcom,qcm2290-tsens
- qcom,sc7180-tsens - qcom,sc7180-tsens
- qcom,sc7280-tsens - qcom,sc7280-tsens
- qcom,sc8180x-tsens - qcom,sc8180x-tsens
...@@ -56,6 +59,7 @@ properties: ...@@ -56,6 +59,7 @@ properties:
- qcom,sdm845-tsens - qcom,sdm845-tsens
- qcom,sm6115-tsens - qcom,sm6115-tsens
- qcom,sm6350-tsens - qcom,sm6350-tsens
- qcom,sm6375-tsens
- qcom,sm8150-tsens - qcom,sm8150-tsens
- qcom,sm8250-tsens - qcom,sm8250-tsens
- qcom,sm8350-tsens - qcom,sm8350-tsens
...@@ -67,6 +71,12 @@ properties: ...@@ -67,6 +71,12 @@ properties:
enum: enum:
- qcom,ipq8074-tsens - qcom,ipq8074-tsens
- description: v2 of TSENS with combined interrupt
items:
- enum:
- qcom,ipq9574-tsens
- const: qcom,ipq8074-tsens
reg: reg:
items: items:
- description: TM registers - description: TM registers
...@@ -223,12 +233,7 @@ allOf: ...@@ -223,12 +233,7 @@ allOf:
contains: contains:
enum: enum:
- qcom,ipq8064-tsens - qcom,ipq8064-tsens
- qcom,mdm9607-tsens
- qcom,msm8916-tsens
- qcom,msm8960-tsens - qcom,msm8960-tsens
- qcom,msm8974-tsens
- qcom,msm8976-tsens
- qcom,qcs404-tsens
- qcom,tsens-v0_1 - qcom,tsens-v0_1
- qcom,tsens-v1 - qcom,tsens-v1
then: then:
...@@ -244,22 +249,7 @@ allOf: ...@@ -244,22 +249,7 @@ allOf:
properties: properties:
compatible: compatible:
contains: contains:
enum: const: qcom,tsens-v2
- qcom,msm8953-tsens
- qcom,msm8996-tsens
- qcom,msm8998-tsens
- qcom,sc7180-tsens
- qcom,sc7280-tsens
- qcom,sc8180x-tsens
- qcom,sc8280xp-tsens
- qcom,sdm630-tsens
- qcom,sdm845-tsens
- qcom,sm6350-tsens
- qcom,sm8150-tsens
- qcom,sm8250-tsens
- qcom,sm8350-tsens
- qcom,sm8450-tsens
- qcom,tsens-v2
then: then:
properties: properties:
interrupts: interrupts:
......
...@@ -45,7 +45,7 @@ static int mlx5_thermal_get_mtmp_temp(struct mlx5_core_dev *mdev, u32 id, int *p ...@@ -45,7 +45,7 @@ static int mlx5_thermal_get_mtmp_temp(struct mlx5_core_dev *mdev, u32 id, int *p
static int mlx5_thermal_get_temp(struct thermal_zone_device *tzdev, static int mlx5_thermal_get_temp(struct thermal_zone_device *tzdev,
int *p_temp) int *p_temp)
{ {
struct mlx5_thermal *thermal = tzdev->devdata; struct mlx5_thermal *thermal = thermal_zone_device_priv(tzdev);
struct mlx5_core_dev *mdev = thermal->mdev; struct mlx5_core_dev *mdev = thermal->mdev;
int err; int err;
...@@ -81,12 +81,13 @@ int mlx5_thermal_init(struct mlx5_core_dev *mdev) ...@@ -81,12 +81,13 @@ int mlx5_thermal_init(struct mlx5_core_dev *mdev)
return -ENOMEM; return -ENOMEM;
thermal->mdev = mdev; thermal->mdev = mdev;
thermal->tzdev = thermal_zone_device_register(data, thermal->tzdev = thermal_zone_device_register_with_trips(data,
MLX5_THERMAL_NUM_TRIPS, NULL,
MLX5_THERMAL_TRIP_MASK, MLX5_THERMAL_NUM_TRIPS,
thermal, MLX5_THERMAL_TRIP_MASK,
&mlx5_thermal_ops, thermal,
NULL, 0, MLX5_THERMAL_POLL_INT_MSEC); &mlx5_thermal_ops,
NULL, 0, MLX5_THERMAL_POLL_INT_MSEC);
if (IS_ERR(thermal->tzdev)) { if (IS_ERR(thermal->tzdev)) {
dev_err(mdev->device, "Failed to register thermal zone device (%s) %ld\n", dev_err(mdev->device, "Failed to register thermal zone device (%s) %ld\n",
data, PTR_ERR(thermal->tzdev)); data, PTR_ERR(thermal->tzdev));
......
...@@ -130,6 +130,14 @@ config THERMAL_DEFAULT_GOV_POWER_ALLOCATOR ...@@ -130,6 +130,14 @@ config THERMAL_DEFAULT_GOV_POWER_ALLOCATOR
system and device power allocation. This governor can only system and device power allocation. This governor can only
operate on cooling devices that implement the power API. operate on cooling devices that implement the power API.
config THERMAL_DEFAULT_GOV_BANG_BANG
bool "bang_bang"
depends on THERMAL_GOV_BANG_BANG
help
Use the bang_bang governor as default. This throttles the
devices one step at the time, taking into account the trip
point hysteresis.
endchoice endchoice
config THERMAL_GOV_FAIR_SHARE config THERMAL_GOV_FAIR_SHARE
......
...@@ -282,8 +282,7 @@ static int amlogic_thermal_probe(struct platform_device *pdev) ...@@ -282,8 +282,7 @@ static int amlogic_thermal_probe(struct platform_device *pdev)
return ret; return ret;
} }
if (devm_thermal_add_hwmon_sysfs(&pdev->dev, pdata->tzd)) devm_thermal_add_hwmon_sysfs(&pdev->dev, pdata->tzd);
dev_warn(&pdev->dev, "Failed to add hwmon sysfs attributes\n");
ret = amlogic_thermal_initialize(pdata); ret = amlogic_thermal_initialize(pdata);
if (ret) if (ret)
......
...@@ -231,7 +231,7 @@ static void armada380_init(struct platform_device *pdev, ...@@ -231,7 +231,7 @@ static void armada380_init(struct platform_device *pdev,
regmap_write(priv->syscon, data->syscon_control0_off, reg); regmap_write(priv->syscon, data->syscon_control0_off, reg);
} }
static void armada_ap806_init(struct platform_device *pdev, static void armada_ap80x_init(struct platform_device *pdev,
struct armada_thermal_priv *priv) struct armada_thermal_priv *priv)
{ {
struct armada_thermal_data *data = priv->data; struct armada_thermal_data *data = priv->data;
...@@ -614,7 +614,7 @@ static const struct armada_thermal_data armada380_data = { ...@@ -614,7 +614,7 @@ static const struct armada_thermal_data armada380_data = {
}; };
static const struct armada_thermal_data armada_ap806_data = { static const struct armada_thermal_data armada_ap806_data = {
.init = armada_ap806_init, .init = armada_ap80x_init,
.is_valid_bit = BIT(16), .is_valid_bit = BIT(16),
.temp_shift = 0, .temp_shift = 0,
.temp_mask = 0x3ff, .temp_mask = 0x3ff,
...@@ -637,6 +637,30 @@ static const struct armada_thermal_data armada_ap806_data = { ...@@ -637,6 +637,30 @@ static const struct armada_thermal_data armada_ap806_data = {
.cpu_nr = 4, .cpu_nr = 4,
}; };
static const struct armada_thermal_data armada_ap807_data = {
.init = armada_ap80x_init,
.is_valid_bit = BIT(16),
.temp_shift = 0,
.temp_mask = 0x3ff,
.thresh_shift = 3,
.hyst_shift = 19,
.hyst_mask = 0x3,
.coef_b = -128900LL,
.coef_m = 394ULL,
.coef_div = 1,
.inverted = true,
.signed_sample = true,
.syscon_control0_off = 0x84,
.syscon_control1_off = 0x88,
.syscon_status_off = 0x8C,
.dfx_irq_cause_off = 0x108,
.dfx_irq_mask_off = 0x10C,
.dfx_overheat_irq = BIT(22),
.dfx_server_irq_mask_off = 0x104,
.dfx_server_irq_en = BIT(1),
.cpu_nr = 4,
};
static const struct armada_thermal_data armada_cp110_data = { static const struct armada_thermal_data armada_cp110_data = {
.init = armada_cp110_init, .init = armada_cp110_init,
.is_valid_bit = BIT(10), .is_valid_bit = BIT(10),
...@@ -680,6 +704,10 @@ static const struct of_device_id armada_thermal_id_table[] = { ...@@ -680,6 +704,10 @@ static const struct of_device_id armada_thermal_id_table[] = {
.compatible = "marvell,armada-ap806-thermal", .compatible = "marvell,armada-ap806-thermal",
.data = &armada_ap806_data, .data = &armada_ap806_data,
}, },
{
.compatible = "marvell,armada-ap807-thermal",
.data = &armada_ap807_data,
},
{ {
.compatible = "marvell,armada-cp110-thermal", .compatible = "marvell,armada-cp110-thermal",
.data = &armada_cp110_data, .data = &armada_cp110_data,
......
...@@ -343,8 +343,7 @@ static int imx8mm_tmu_probe(struct platform_device *pdev) ...@@ -343,8 +343,7 @@ static int imx8mm_tmu_probe(struct platform_device *pdev)
} }
tmu->sensors[i].hw_id = i; tmu->sensors[i].hw_id = i;
if (devm_thermal_add_hwmon_sysfs(&pdev->dev, tmu->sensors[i].tzd)) devm_thermal_add_hwmon_sysfs(&pdev->dev, tmu->sensors[i].tzd);
dev_warn(&pdev->dev, "failed to add hwmon sysfs attributes\n");
} }
platform_set_drvdata(pdev, tmu); platform_set_drvdata(pdev, tmu);
......
...@@ -116,8 +116,7 @@ static int imx_sc_thermal_probe(struct platform_device *pdev) ...@@ -116,8 +116,7 @@ static int imx_sc_thermal_probe(struct platform_device *pdev)
return ret; return ret;
} }
if (devm_thermal_add_hwmon_sysfs(&pdev->dev, sensor->tzd)) devm_thermal_add_hwmon_sysfs(&pdev->dev, sensor->tzd);
dev_warn(&pdev->dev, "failed to add hwmon sysfs attributes\n");
} }
return 0; return 0;
......
...@@ -222,8 +222,7 @@ static int k3_bandgap_probe(struct platform_device *pdev) ...@@ -222,8 +222,7 @@ static int k3_bandgap_probe(struct platform_device *pdev)
goto err_alloc; goto err_alloc;
} }
if (devm_thermal_add_hwmon_sysfs(dev, data[id].tzd)) devm_thermal_add_hwmon_sysfs(dev, data[id].tzd);
dev_warn(dev, "Failed to add hwmon sysfs attributes\n");
} }
platform_set_drvdata(pdev, bgp); platform_set_drvdata(pdev, bgp);
......
...@@ -1222,12 +1222,7 @@ static int mtk_thermal_probe(struct platform_device *pdev) ...@@ -1222,12 +1222,7 @@ static int mtk_thermal_probe(struct platform_device *pdev)
return -ENODEV; return -ENODEV;
} }
auxadc_base = devm_of_iomap(&pdev->dev, auxadc, 0, NULL); auxadc_base = of_iomap(auxadc, 0);
if (IS_ERR(auxadc_base)) {
of_node_put(auxadc);
return PTR_ERR(auxadc_base);
}
auxadc_phys_base = of_get_phys_base(auxadc); auxadc_phys_base = of_get_phys_base(auxadc);
of_node_put(auxadc); of_node_put(auxadc);
...@@ -1243,12 +1238,7 @@ static int mtk_thermal_probe(struct platform_device *pdev) ...@@ -1243,12 +1238,7 @@ static int mtk_thermal_probe(struct platform_device *pdev)
return -ENODEV; return -ENODEV;
} }
apmixed_base = devm_of_iomap(&pdev->dev, apmixedsys, 0, NULL); apmixed_base = of_iomap(apmixedsys, 0);
if (IS_ERR(apmixed_base)) {
of_node_put(apmixedsys);
return PTR_ERR(apmixed_base);
}
apmixed_phys_base = of_get_phys_base(apmixedsys); apmixed_phys_base = of_get_phys_base(apmixedsys);
of_node_put(apmixedsys); of_node_put(apmixedsys);
......
...@@ -19,6 +19,8 @@ ...@@ -19,6 +19,8 @@
#include <linux/thermal.h> #include <linux/thermal.h>
#include <dt-bindings/thermal/mediatek,lvts-thermal.h> #include <dt-bindings/thermal/mediatek,lvts-thermal.h>
#include "../thermal_hwmon.h"
#define LVTS_MONCTL0(__base) (__base + 0x0000) #define LVTS_MONCTL0(__base) (__base + 0x0000)
#define LVTS_MONCTL1(__base) (__base + 0x0004) #define LVTS_MONCTL1(__base) (__base + 0x0004)
#define LVTS_MONCTL2(__base) (__base + 0x0008) #define LVTS_MONCTL2(__base) (__base + 0x0008)
...@@ -996,6 +998,8 @@ static int lvts_ctrl_start(struct device *dev, struct lvts_ctrl *lvts_ctrl) ...@@ -996,6 +998,8 @@ static int lvts_ctrl_start(struct device *dev, struct lvts_ctrl *lvts_ctrl)
return PTR_ERR(tz); return PTR_ERR(tz);
} }
devm_thermal_add_hwmon_sysfs(dev, tz);
/* /*
* The thermal zone pointer will be needed in the * The thermal zone pointer will be needed in the
* interrupt handler, we store it in the sensor * interrupt handler, we store it in the sensor
......
...@@ -689,9 +689,7 @@ static int adc_tm5_register_tzd(struct adc_tm5_chip *adc_tm) ...@@ -689,9 +689,7 @@ static int adc_tm5_register_tzd(struct adc_tm5_chip *adc_tm)
return PTR_ERR(tzd); return PTR_ERR(tzd);
} }
adc_tm->channels[i].tzd = tzd; adc_tm->channels[i].tzd = tzd;
if (devm_thermal_add_hwmon_sysfs(adc_tm->dev, tzd)) devm_thermal_add_hwmon_sysfs(adc_tm->dev, tzd);
dev_warn(adc_tm->dev,
"Failed to add hwmon sysfs attributes\n");
} }
return 0; return 0;
......
...@@ -411,22 +411,19 @@ static int qpnp_tm_probe(struct platform_device *pdev) ...@@ -411,22 +411,19 @@ static int qpnp_tm_probe(struct platform_device *pdev)
chip->base = res; chip->base = res;
ret = qpnp_tm_read(chip, QPNP_TM_REG_TYPE, &type); ret = qpnp_tm_read(chip, QPNP_TM_REG_TYPE, &type);
if (ret < 0) { if (ret < 0)
dev_err(&pdev->dev, "could not read type\n"); return dev_err_probe(&pdev->dev, ret,
return ret; "could not read type\n");
}
ret = qpnp_tm_read(chip, QPNP_TM_REG_SUBTYPE, &subtype); ret = qpnp_tm_read(chip, QPNP_TM_REG_SUBTYPE, &subtype);
if (ret < 0) { if (ret < 0)
dev_err(&pdev->dev, "could not read subtype\n"); return dev_err_probe(&pdev->dev, ret,
return ret; "could not read subtype\n");
}
ret = qpnp_tm_read(chip, QPNP_TM_REG_DIG_MAJOR, &dig_major); ret = qpnp_tm_read(chip, QPNP_TM_REG_DIG_MAJOR, &dig_major);
if (ret < 0) { if (ret < 0)
dev_err(&pdev->dev, "could not read dig_major\n"); return dev_err_probe(&pdev->dev, ret,
return ret; "could not read dig_major\n");
}
if (type != QPNP_TM_TYPE || (subtype != QPNP_TM_SUBTYPE_GEN1 if (type != QPNP_TM_TYPE || (subtype != QPNP_TM_SUBTYPE_GEN1
&& subtype != QPNP_TM_SUBTYPE_GEN2)) { && subtype != QPNP_TM_SUBTYPE_GEN2)) {
...@@ -448,20 +445,15 @@ static int qpnp_tm_probe(struct platform_device *pdev) ...@@ -448,20 +445,15 @@ static int qpnp_tm_probe(struct platform_device *pdev)
*/ */
chip->tz_dev = devm_thermal_of_zone_register( chip->tz_dev = devm_thermal_of_zone_register(
&pdev->dev, 0, chip, &qpnp_tm_sensor_ops); &pdev->dev, 0, chip, &qpnp_tm_sensor_ops);
if (IS_ERR(chip->tz_dev)) { if (IS_ERR(chip->tz_dev))
dev_err(&pdev->dev, "failed to register sensor\n"); return dev_err_probe(&pdev->dev, PTR_ERR(chip->tz_dev),
return PTR_ERR(chip->tz_dev); "failed to register sensor\n");
}
ret = qpnp_tm_init(chip); ret = qpnp_tm_init(chip);
if (ret < 0) { if (ret < 0)
dev_err(&pdev->dev, "init failed\n"); return dev_err_probe(&pdev->dev, ret, "init failed\n");
return ret;
}
if (devm_thermal_add_hwmon_sysfs(&pdev->dev, chip->tz_dev)) devm_thermal_add_hwmon_sysfs(&pdev->dev, chip->tz_dev);
dev_warn(&pdev->dev,
"Failed to add hwmon sysfs attributes\n");
ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, qpnp_tm_isr, ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, qpnp_tm_isr,
IRQF_ONESHOT, node->name, chip); IRQF_ONESHOT, node->name, chip);
......
...@@ -39,26 +39,6 @@ struct tsens_legacy_calibration_format tsens_8916_nvmem = { ...@@ -39,26 +39,6 @@ struct tsens_legacy_calibration_format tsens_8916_nvmem = {
}, },
}; };
struct tsens_legacy_calibration_format tsens_8939_nvmem = {
.base_len = 8,
.base_shift = 2,
.sp_len = 6,
.mode = { 12, 0 },
.invalid = { 12, 2 },
.base = { { 0, 0 }, { 1, 24 } },
.sp = {
{ { 12, 3 }, { 12, 9 } },
{ { 12, 15 }, { 12, 21 } },
{ { 12, 27 }, { 13, 1 } },
{ { 13, 7 }, { 13, 13 } },
{ { 13, 19 }, { 13, 25 } },
{ { 0, 8 }, { 0, 14 } },
{ { 0, 20 }, { 0, 26 } },
{ { 1, 0 }, { 1, 6 } },
{ { 1, 12 }, { 1, 18 } },
},
};
struct tsens_legacy_calibration_format tsens_8974_nvmem = { struct tsens_legacy_calibration_format tsens_8974_nvmem = {
.base_len = 8, .base_len = 8,
.base_shift = 2, .base_shift = 2,
...@@ -103,22 +83,6 @@ struct tsens_legacy_calibration_format tsens_8974_backup_nvmem = { ...@@ -103,22 +83,6 @@ struct tsens_legacy_calibration_format tsens_8974_backup_nvmem = {
}, },
}; };
struct tsens_legacy_calibration_format tsens_9607_nvmem = {
.base_len = 8,
.base_shift = 2,
.sp_len = 6,
.mode = { 2, 20 },
.invalid = { 2, 22 },
.base = { { 0, 0 }, { 2, 12 } },
.sp = {
{ { 0, 8 }, { 0, 14 } },
{ { 0, 20 }, { 0, 26 } },
{ { 1, 0 }, { 1, 6 } },
{ { 1, 12 }, { 1, 18 } },
{ { 2, 0 }, { 2, 6 } },
},
};
static int calibrate_8916(struct tsens_priv *priv) static int calibrate_8916(struct tsens_priv *priv)
{ {
u32 p1[5], p2[5]; u32 p1[5], p2[5];
...@@ -243,6 +207,39 @@ static int calibrate_8974(struct tsens_priv *priv) ...@@ -243,6 +207,39 @@ static int calibrate_8974(struct tsens_priv *priv)
return 0; return 0;
} }
static int __init init_8226(struct tsens_priv *priv)
{
priv->sensor[0].slope = 2901;
priv->sensor[1].slope = 2846;
priv->sensor[2].slope = 3038;
priv->sensor[3].slope = 2955;
priv->sensor[4].slope = 2901;
priv->sensor[5].slope = 2846;
return init_common(priv);
}
static int __init init_8909(struct tsens_priv *priv)
{
int i;
for (i = 0; i < priv->num_sensors; ++i)
priv->sensor[i].slope = 3000;
priv->sensor[0].p1_calib_offset = 0;
priv->sensor[0].p2_calib_offset = 0;
priv->sensor[1].p1_calib_offset = -10;
priv->sensor[1].p2_calib_offset = -6;
priv->sensor[2].p1_calib_offset = 0;
priv->sensor[2].p2_calib_offset = 0;
priv->sensor[3].p1_calib_offset = -9;
priv->sensor[3].p2_calib_offset = -9;
priv->sensor[4].p1_calib_offset = -8;
priv->sensor[4].p2_calib_offset = -10;
return init_common(priv);
}
static int __init init_8939(struct tsens_priv *priv) { static int __init init_8939(struct tsens_priv *priv) {
priv->sensor[0].slope = 2911; priv->sensor[0].slope = 2911;
priv->sensor[1].slope = 2789; priv->sensor[1].slope = 2789;
...@@ -258,7 +255,28 @@ static int __init init_8939(struct tsens_priv *priv) { ...@@ -258,7 +255,28 @@ static int __init init_8939(struct tsens_priv *priv) {
return init_common(priv); return init_common(priv);
} }
/* v0.1: 8916, 8939, 8974, 9607 */ static int __init init_9607(struct tsens_priv *priv)
{
int i;
for (i = 0; i < priv->num_sensors; ++i)
priv->sensor[i].slope = 3000;
priv->sensor[0].p1_calib_offset = 1;
priv->sensor[0].p2_calib_offset = 1;
priv->sensor[1].p1_calib_offset = -4;
priv->sensor[1].p2_calib_offset = -2;
priv->sensor[2].p1_calib_offset = 4;
priv->sensor[2].p2_calib_offset = 8;
priv->sensor[3].p1_calib_offset = -3;
priv->sensor[3].p2_calib_offset = -5;
priv->sensor[4].p1_calib_offset = -4;
priv->sensor[4].p2_calib_offset = -4;
return init_common(priv);
}
/* v0.1: 8226, 8909, 8916, 8939, 8974, 9607 */
static struct tsens_features tsens_v0_1_feat = { static struct tsens_features tsens_v0_1_feat = {
.ver_major = VER_0_1, .ver_major = VER_0_1,
...@@ -313,6 +331,32 @@ static const struct tsens_ops ops_v0_1 = { ...@@ -313,6 +331,32 @@ static const struct tsens_ops ops_v0_1 = {
.get_temp = get_temp_common, .get_temp = get_temp_common,
}; };
static const struct tsens_ops ops_8226 = {
.init = init_8226,
.calibrate = tsens_calibrate_common,
.get_temp = get_temp_common,
};
struct tsens_plat_data data_8226 = {
.num_sensors = 6,
.ops = &ops_8226,
.feat = &tsens_v0_1_feat,
.fields = tsens_v0_1_regfields,
};
static const struct tsens_ops ops_8909 = {
.init = init_8909,
.calibrate = tsens_calibrate_common,
.get_temp = get_temp_common,
};
struct tsens_plat_data data_8909 = {
.num_sensors = 5,
.ops = &ops_8909,
.feat = &tsens_v0_1_feat,
.fields = tsens_v0_1_regfields,
};
static const struct tsens_ops ops_8916 = { static const struct tsens_ops ops_8916 = {
.init = init_common, .init = init_common,
.calibrate = calibrate_8916, .calibrate = calibrate_8916,
...@@ -356,9 +400,15 @@ struct tsens_plat_data data_8974 = { ...@@ -356,9 +400,15 @@ struct tsens_plat_data data_8974 = {
.fields = tsens_v0_1_regfields, .fields = tsens_v0_1_regfields,
}; };
static const struct tsens_ops ops_9607 = {
.init = init_9607,
.calibrate = tsens_calibrate_common,
.get_temp = get_temp_common,
};
struct tsens_plat_data data_9607 = { struct tsens_plat_data data_9607 = {
.num_sensors = 5, .num_sensors = 5,
.ops = &ops_v0_1, .ops = &ops_9607,
.feat = &tsens_v0_1_feat, .feat = &tsens_v0_1_feat,
.fields = tsens_v0_1_regfields, .fields = tsens_v0_1_regfields,
}; };
...@@ -42,28 +42,6 @@ struct tsens_legacy_calibration_format tsens_qcs404_nvmem = { ...@@ -42,28 +42,6 @@ struct tsens_legacy_calibration_format tsens_qcs404_nvmem = {
}, },
}; };
struct tsens_legacy_calibration_format tsens_8976_nvmem = {
.base_len = 8,
.base_shift = 2,
.sp_len = 6,
.mode = { 4, 0 },
.invalid = { 4, 2 },
.base = { { 0, 0 }, { 2, 8 } },
.sp = {
{ { 0, 8 }, { 0, 14 } },
{ { 0, 20 }, { 0, 26 } },
{ { 1, 0 }, { 1, 6 } },
{ { 1, 12 }, { 1, 18 } },
{ { 2, 8 }, { 2, 14 } },
{ { 2, 20 }, { 2, 26 } },
{ { 3, 0 }, { 3, 6 } },
{ { 3, 12 }, { 3, 18 } },
{ { 4, 2 }, { 4, 9 } },
{ { 4, 14 }, { 4, 21 } },
{ { 4, 26 }, { 5, 1 } },
},
};
static int calibrate_v1(struct tsens_priv *priv) static int calibrate_v1(struct tsens_priv *priv)
{ {
u32 p1[10], p2[10]; u32 p1[10], p2[10];
......
...@@ -134,10 +134,12 @@ int tsens_read_calibration(struct tsens_priv *priv, int shift, u32 *p1, u32 *p2, ...@@ -134,10 +134,12 @@ int tsens_read_calibration(struct tsens_priv *priv, int shift, u32 *p1, u32 *p2,
p1[i] = p1[i] + (base1 << shift); p1[i] = p1[i] + (base1 << shift);
break; break;
case TWO_PT_CALIB: case TWO_PT_CALIB:
case TWO_PT_CALIB_NO_OFFSET:
for (i = 0; i < priv->num_sensors; i++) for (i = 0; i < priv->num_sensors; i++)
p2[i] = (p2[i] + base2) << shift; p2[i] = (p2[i] + base2) << shift;
fallthrough; fallthrough;
case ONE_PT_CALIB2: case ONE_PT_CALIB2:
case ONE_PT_CALIB2_NO_OFFSET:
for (i = 0; i < priv->num_sensors; i++) for (i = 0; i < priv->num_sensors; i++)
p1[i] = (p1[i] + base1) << shift; p1[i] = (p1[i] + base1) << shift;
break; break;
...@@ -149,6 +151,18 @@ int tsens_read_calibration(struct tsens_priv *priv, int shift, u32 *p1, u32 *p2, ...@@ -149,6 +151,18 @@ int tsens_read_calibration(struct tsens_priv *priv, int shift, u32 *p1, u32 *p2,
} }
} }
/* Apply calibration offset workaround except for _NO_OFFSET modes */
switch (mode) {
case TWO_PT_CALIB:
for (i = 0; i < priv->num_sensors; i++)
p2[i] += priv->sensor[i].p2_calib_offset;
fallthrough;
case ONE_PT_CALIB2:
for (i = 0; i < priv->num_sensors; i++)
p1[i] += priv->sensor[i].p1_calib_offset;
break;
}
return mode; return mode;
} }
...@@ -254,7 +268,7 @@ void compute_intercept_slope(struct tsens_priv *priv, u32 *p1, ...@@ -254,7 +268,7 @@ void compute_intercept_slope(struct tsens_priv *priv, u32 *p1,
if (!priv->sensor[i].slope) if (!priv->sensor[i].slope)
priv->sensor[i].slope = SLOPE_DEFAULT; priv->sensor[i].slope = SLOPE_DEFAULT;
if (mode == TWO_PT_CALIB) { if (mode == TWO_PT_CALIB || mode == TWO_PT_CALIB_NO_OFFSET) {
/* /*
* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ * slope (m) = adc_code2 - adc_code1 (y2 - y1)/
* temp_120_degc - temp_30_degc (x2 - x1) * temp_120_degc - temp_30_degc (x2 - x1)
...@@ -1095,6 +1109,12 @@ static const struct of_device_id tsens_table[] = { ...@@ -1095,6 +1109,12 @@ static const struct of_device_id tsens_table[] = {
}, { }, {
.compatible = "qcom,mdm9607-tsens", .compatible = "qcom,mdm9607-tsens",
.data = &data_9607, .data = &data_9607,
}, {
.compatible = "qcom,msm8226-tsens",
.data = &data_8226,
}, {
.compatible = "qcom,msm8909-tsens",
.data = &data_8909,
}, { }, {
.compatible = "qcom,msm8916-tsens", .compatible = "qcom,msm8916-tsens",
.data = &data_8916, .data = &data_8916,
...@@ -1189,9 +1209,7 @@ static int tsens_register(struct tsens_priv *priv) ...@@ -1189,9 +1209,7 @@ static int tsens_register(struct tsens_priv *priv)
if (priv->ops->enable) if (priv->ops->enable)
priv->ops->enable(priv, i); priv->ops->enable(priv, i);
if (devm_thermal_add_hwmon_sysfs(priv->dev, tzd)) devm_thermal_add_hwmon_sysfs(priv->dev, tzd);
dev_warn(priv->dev,
"Failed to add hwmon sysfs attributes\n");
} }
/* VER_0 require to set MIN and MAX THRESH /* VER_0 require to set MIN and MAX THRESH
......
...@@ -10,6 +10,8 @@ ...@@ -10,6 +10,8 @@
#define ONE_PT_CALIB 0x1 #define ONE_PT_CALIB 0x1
#define ONE_PT_CALIB2 0x2 #define ONE_PT_CALIB2 0x2
#define TWO_PT_CALIB 0x3 #define TWO_PT_CALIB 0x3
#define ONE_PT_CALIB2_NO_OFFSET 0x6
#define TWO_PT_CALIB_NO_OFFSET 0x7
#define CAL_DEGC_PT1 30 #define CAL_DEGC_PT1 30
#define CAL_DEGC_PT2 120 #define CAL_DEGC_PT2 120
#define SLOPE_FACTOR 1000 #define SLOPE_FACTOR 1000
...@@ -57,6 +59,8 @@ struct tsens_sensor { ...@@ -57,6 +59,8 @@ struct tsens_sensor {
unsigned int hw_id; unsigned int hw_id;
int slope; int slope;
u32 status; u32 status;
int p1_calib_offset;
int p2_calib_offset;
}; };
/** /**
...@@ -635,7 +639,7 @@ int get_temp_common(const struct tsens_sensor *s, int *temp); ...@@ -635,7 +639,7 @@ int get_temp_common(const struct tsens_sensor *s, int *temp);
extern struct tsens_plat_data data_8960; extern struct tsens_plat_data data_8960;
/* TSENS v0.1 targets */ /* TSENS v0.1 targets */
extern struct tsens_plat_data data_8916, data_8939, data_8974, data_9607; extern struct tsens_plat_data data_8226, data_8909, data_8916, data_8939, data_8974, data_9607;
/* TSENS v1 targets */ /* TSENS v1 targets */
extern struct tsens_plat_data data_tsens_v1, data_8976, data_8956; extern struct tsens_plat_data data_tsens_v1, data_8976, data_8956;
......
...@@ -31,7 +31,6 @@ ...@@ -31,7 +31,6 @@
#define TMR_DISABLE 0x0 #define TMR_DISABLE 0x0
#define TMR_ME 0x80000000 #define TMR_ME 0x80000000
#define TMR_ALPF 0x0c000000 #define TMR_ALPF 0x0c000000
#define TMR_MSITE_ALL GENMASK(15, 0)
#define REGS_TMTMIR 0x008 /* Temperature measurement interval Register */ #define REGS_TMTMIR 0x008 /* Temperature measurement interval Register */
#define TMTMIR_DEFAULT 0x0000000f #define TMTMIR_DEFAULT 0x0000000f
...@@ -51,6 +50,7 @@ ...@@ -51,6 +50,7 @@
* Site Register * Site Register
*/ */
#define TRITSR_V BIT(31) #define TRITSR_V BIT(31)
#define TRITSR_TP5 BIT(9)
#define REGS_V2_TMSAR(n) (0x304 + 16 * (n)) /* TMU monitoring #define REGS_V2_TMSAR(n) (0x304 + 16 * (n)) /* TMU monitoring
* site adjustment register * site adjustment register
*/ */
...@@ -105,6 +105,11 @@ static int tmu_get_temp(struct thermal_zone_device *tz, int *temp) ...@@ -105,6 +105,11 @@ static int tmu_get_temp(struct thermal_zone_device *tz, int *temp)
* within sensor range. TEMP is an 9 bit value representing * within sensor range. TEMP is an 9 bit value representing
* temperature in KelVin. * temperature in KelVin.
*/ */
regmap_read(qdata->regmap, REGS_TMR, &val);
if (!(val & TMR_ME))
return -EAGAIN;
if (regmap_read_poll_timeout(qdata->regmap, if (regmap_read_poll_timeout(qdata->regmap,
REGS_TRITSR(qsensor->id), REGS_TRITSR(qsensor->id),
val, val,
...@@ -113,10 +118,15 @@ static int tmu_get_temp(struct thermal_zone_device *tz, int *temp) ...@@ -113,10 +118,15 @@ static int tmu_get_temp(struct thermal_zone_device *tz, int *temp)
10 * USEC_PER_MSEC)) 10 * USEC_PER_MSEC))
return -ENODATA; return -ENODATA;
if (qdata->ver == TMU_VER1) if (qdata->ver == TMU_VER1) {
*temp = (val & GENMASK(7, 0)) * MILLIDEGREE_PER_DEGREE; *temp = (val & GENMASK(7, 0)) * MILLIDEGREE_PER_DEGREE;
else } else {
*temp = kelvin_to_millicelsius(val & GENMASK(8, 0)); if (val & TRITSR_TP5)
*temp = milli_kelvin_to_millicelsius((val & GENMASK(8, 0)) *
MILLIDEGREE_PER_DEGREE + 500);
else
*temp = kelvin_to_millicelsius(val & GENMASK(8, 0));
}
return 0; return 0;
} }
...@@ -128,15 +138,7 @@ static const struct thermal_zone_device_ops tmu_tz_ops = { ...@@ -128,15 +138,7 @@ static const struct thermal_zone_device_ops tmu_tz_ops = {
static int qoriq_tmu_register_tmu_zone(struct device *dev, static int qoriq_tmu_register_tmu_zone(struct device *dev,
struct qoriq_tmu_data *qdata) struct qoriq_tmu_data *qdata)
{ {
int id; int id, sites = 0;
if (qdata->ver == TMU_VER1) {
regmap_write(qdata->regmap, REGS_TMR,
TMR_MSITE_ALL | TMR_ME | TMR_ALPF);
} else {
regmap_write(qdata->regmap, REGS_V2_TMSR, TMR_MSITE_ALL);
regmap_write(qdata->regmap, REGS_TMR, TMR_ME | TMR_ALPF_V2);
}
for (id = 0; id < SITES_MAX; id++) { for (id = 0; id < SITES_MAX; id++) {
struct thermal_zone_device *tzd; struct thermal_zone_device *tzd;
...@@ -153,14 +155,24 @@ static int qoriq_tmu_register_tmu_zone(struct device *dev, ...@@ -153,14 +155,24 @@ static int qoriq_tmu_register_tmu_zone(struct device *dev,
if (ret == -ENODEV) if (ret == -ENODEV)
continue; continue;
regmap_write(qdata->regmap, REGS_TMR, TMR_DISABLE);
return ret; return ret;
} }
if (devm_thermal_add_hwmon_sysfs(dev, tzd)) if (qdata->ver == TMU_VER1)
dev_warn(dev, sites |= 0x1 << (15 - id);
"Failed to add hwmon sysfs attributes\n"); else
sites |= 0x1 << id;
devm_thermal_add_hwmon_sysfs(dev, tzd);
}
if (sites) {
if (qdata->ver == TMU_VER1) {
regmap_write(qdata->regmap, REGS_TMR, TMR_ME | TMR_ALPF | sites);
} else {
regmap_write(qdata->regmap, REGS_V2_TMSR, sites);
regmap_write(qdata->regmap, REGS_TMR, TMR_ME | TMR_ALPF_V2);
}
} }
return 0; return 0;
...@@ -208,8 +220,6 @@ static int qoriq_tmu_calibration(struct device *dev, ...@@ -208,8 +220,6 @@ static int qoriq_tmu_calibration(struct device *dev,
static void qoriq_tmu_init_device(struct qoriq_tmu_data *data) static void qoriq_tmu_init_device(struct qoriq_tmu_data *data)
{ {
int i;
/* Disable interrupt, using polling instead */ /* Disable interrupt, using polling instead */
regmap_write(data->regmap, REGS_TIER, TIER_DISABLE); regmap_write(data->regmap, REGS_TIER, TIER_DISABLE);
...@@ -220,8 +230,6 @@ static void qoriq_tmu_init_device(struct qoriq_tmu_data *data) ...@@ -220,8 +230,6 @@ static void qoriq_tmu_init_device(struct qoriq_tmu_data *data)
} else { } else {
regmap_write(data->regmap, REGS_V2_TMTMIR, TMTMIR_DEFAULT); regmap_write(data->regmap, REGS_V2_TMTMIR, TMTMIR_DEFAULT);
regmap_write(data->regmap, REGS_V2_TEUMR(0), TEUMR0_V2); regmap_write(data->regmap, REGS_V2_TEUMR(0), TEUMR0_V2);
for (i = 0; i < SITES_MAX; i++)
regmap_write(data->regmap, REGS_V2_TMSAR(i), TMSARA_V2);
} }
/* Disable monitoring */ /* Disable monitoring */
...@@ -230,7 +238,7 @@ static void qoriq_tmu_init_device(struct qoriq_tmu_data *data) ...@@ -230,7 +238,7 @@ static void qoriq_tmu_init_device(struct qoriq_tmu_data *data)
static const struct regmap_range qoriq_yes_ranges[] = { static const struct regmap_range qoriq_yes_ranges[] = {
regmap_reg_range(REGS_TMR, REGS_TSCFGR), regmap_reg_range(REGS_TMR, REGS_TSCFGR),
regmap_reg_range(REGS_TTRnCR(0), REGS_TTRnCR(3)), regmap_reg_range(REGS_TTRnCR(0), REGS_TTRnCR(15)),
regmap_reg_range(REGS_V2_TEUMR(0), REGS_V2_TEUMR(2)), regmap_reg_range(REGS_V2_TEUMR(0), REGS_V2_TEUMR(2)),
regmap_reg_range(REGS_V2_TMSAR(0), REGS_V2_TMSAR(15)), regmap_reg_range(REGS_V2_TMSAR(0), REGS_V2_TMSAR(15)),
regmap_reg_range(REGS_IPBRR(0), REGS_IPBRR(1)), regmap_reg_range(REGS_IPBRR(0), REGS_IPBRR(1)),
......
...@@ -35,6 +35,12 @@ ...@@ -35,6 +35,12 @@
#define REG_GEN3_PTAT2 0x60 #define REG_GEN3_PTAT2 0x60
#define REG_GEN3_PTAT3 0x64 #define REG_GEN3_PTAT3 0x64
#define REG_GEN3_THSCP 0x68 #define REG_GEN3_THSCP 0x68
#define REG_GEN4_THSFMON00 0x180
#define REG_GEN4_THSFMON01 0x184
#define REG_GEN4_THSFMON02 0x188
#define REG_GEN4_THSFMON15 0x1BC
#define REG_GEN4_THSFMON16 0x1C0
#define REG_GEN4_THSFMON17 0x1C4
/* IRQ{STR,MSK,EN} bits */ /* IRQ{STR,MSK,EN} bits */
#define IRQ_TEMP1 BIT(0) #define IRQ_TEMP1 BIT(0)
...@@ -55,6 +61,7 @@ ...@@ -55,6 +61,7 @@
#define MCELSIUS(temp) ((temp) * 1000) #define MCELSIUS(temp) ((temp) * 1000)
#define GEN3_FUSE_MASK 0xFFF #define GEN3_FUSE_MASK 0xFFF
#define GEN4_FUSE_MASK 0xFFF
#define TSC_MAX_NUM 5 #define TSC_MAX_NUM 5
...@@ -66,6 +73,13 @@ struct equation_coefs { ...@@ -66,6 +73,13 @@ struct equation_coefs {
int b2; int b2;
}; };
struct rcar_gen3_thermal_priv;
struct rcar_thermal_info {
int ths_tj_1;
void (*read_fuses)(struct rcar_gen3_thermal_priv *priv);
};
struct rcar_gen3_thermal_tsc { struct rcar_gen3_thermal_tsc {
void __iomem *base; void __iomem *base;
struct thermal_zone_device *zone; struct thermal_zone_device *zone;
...@@ -79,6 +93,7 @@ struct rcar_gen3_thermal_priv { ...@@ -79,6 +93,7 @@ struct rcar_gen3_thermal_priv {
struct thermal_zone_device_ops ops; struct thermal_zone_device_ops ops;
unsigned int num_tscs; unsigned int num_tscs;
int ptat[3]; int ptat[3];
const struct rcar_thermal_info *info;
}; };
static inline u32 rcar_gen3_thermal_read(struct rcar_gen3_thermal_tsc *tsc, static inline u32 rcar_gen3_thermal_read(struct rcar_gen3_thermal_tsc *tsc,
...@@ -236,6 +251,62 @@ static irqreturn_t rcar_gen3_thermal_irq(int irq, void *data) ...@@ -236,6 +251,62 @@ static irqreturn_t rcar_gen3_thermal_irq(int irq, void *data)
return IRQ_HANDLED; return IRQ_HANDLED;
} }
static void rcar_gen3_thermal_read_fuses_gen3(struct rcar_gen3_thermal_priv *priv)
{
unsigned int i;
/*
* Set the pseudo calibration points with fused values.
* PTAT is shared between all TSCs but only fused for the first
* TSC while THCODEs are fused for each TSC.
*/
priv->ptat[0] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT1) &
GEN3_FUSE_MASK;
priv->ptat[1] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT2) &
GEN3_FUSE_MASK;
priv->ptat[2] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT3) &
GEN3_FUSE_MASK;
for (i = 0; i < priv->num_tscs; i++) {
struct rcar_gen3_thermal_tsc *tsc = priv->tscs[i];
tsc->thcode[0] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE1) &
GEN3_FUSE_MASK;
tsc->thcode[1] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE2) &
GEN3_FUSE_MASK;
tsc->thcode[2] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE3) &
GEN3_FUSE_MASK;
}
}
static void rcar_gen3_thermal_read_fuses_gen4(struct rcar_gen3_thermal_priv *priv)
{
unsigned int i;
/*
* Set the pseudo calibration points with fused values.
* PTAT is shared between all TSCs but only fused for the first
* TSC while THCODEs are fused for each TSC.
*/
priv->ptat[0] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN4_THSFMON16) &
GEN4_FUSE_MASK;
priv->ptat[1] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN4_THSFMON17) &
GEN4_FUSE_MASK;
priv->ptat[2] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN4_THSFMON15) &
GEN4_FUSE_MASK;
for (i = 0; i < priv->num_tscs; i++) {
struct rcar_gen3_thermal_tsc *tsc = priv->tscs[i];
tsc->thcode[0] = rcar_gen3_thermal_read(tsc, REG_GEN4_THSFMON01) &
GEN4_FUSE_MASK;
tsc->thcode[1] = rcar_gen3_thermal_read(tsc, REG_GEN4_THSFMON02) &
GEN4_FUSE_MASK;
tsc->thcode[2] = rcar_gen3_thermal_read(tsc, REG_GEN4_THSFMON00) &
GEN4_FUSE_MASK;
}
}
static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv) static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv)
{ {
unsigned int i; unsigned int i;
...@@ -243,7 +314,8 @@ static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv) ...@@ -243,7 +314,8 @@ static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv)
/* If fuses are not set, fallback to pseudo values. */ /* If fuses are not set, fallback to pseudo values. */
thscp = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_THSCP); thscp = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_THSCP);
if ((thscp & THSCP_COR_PARA_VLD) != THSCP_COR_PARA_VLD) { if (!priv->info->read_fuses ||
(thscp & THSCP_COR_PARA_VLD) != THSCP_COR_PARA_VLD) {
/* Default THCODE values in case FUSEs are not set. */ /* Default THCODE values in case FUSEs are not set. */
static const int thcodes[TSC_MAX_NUM][3] = { static const int thcodes[TSC_MAX_NUM][3] = {
{ 3397, 2800, 2221 }, { 3397, 2800, 2221 },
...@@ -268,29 +340,7 @@ static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv) ...@@ -268,29 +340,7 @@ static bool rcar_gen3_thermal_read_fuses(struct rcar_gen3_thermal_priv *priv)
return false; return false;
} }
/* priv->info->read_fuses(priv);
* Set the pseudo calibration points with fused values.
* PTAT is shared between all TSCs but only fused for the first
* TSC while THCODEs are fused for each TSC.
*/
priv->ptat[0] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT1) &
GEN3_FUSE_MASK;
priv->ptat[1] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT2) &
GEN3_FUSE_MASK;
priv->ptat[2] = rcar_gen3_thermal_read(priv->tscs[0], REG_GEN3_PTAT3) &
GEN3_FUSE_MASK;
for (i = 0; i < priv->num_tscs; i++) {
struct rcar_gen3_thermal_tsc *tsc = priv->tscs[i];
tsc->thcode[0] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE1) &
GEN3_FUSE_MASK;
tsc->thcode[1] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE2) &
GEN3_FUSE_MASK;
tsc->thcode[2] = rcar_gen3_thermal_read(tsc, REG_GEN3_THCODE3) &
GEN3_FUSE_MASK;
}
return true; return true;
} }
...@@ -318,52 +368,65 @@ static void rcar_gen3_thermal_init(struct rcar_gen3_thermal_priv *priv, ...@@ -318,52 +368,65 @@ static void rcar_gen3_thermal_init(struct rcar_gen3_thermal_priv *priv,
usleep_range(1000, 2000); usleep_range(1000, 2000);
} }
static const int rcar_gen3_ths_tj_1 = 126; static const struct rcar_thermal_info rcar_m3w_thermal_info = {
static const int rcar_gen3_ths_tj_1_m3_w = 116; .ths_tj_1 = 116,
.read_fuses = rcar_gen3_thermal_read_fuses_gen3,
};
static const struct rcar_thermal_info rcar_gen3_thermal_info = {
.ths_tj_1 = 126,
.read_fuses = rcar_gen3_thermal_read_fuses_gen3,
};
static const struct rcar_thermal_info rcar_gen4_thermal_info = {
.ths_tj_1 = 126,
.read_fuses = rcar_gen3_thermal_read_fuses_gen4,
};
static const struct of_device_id rcar_gen3_thermal_dt_ids[] = { static const struct of_device_id rcar_gen3_thermal_dt_ids[] = {
{ {
.compatible = "renesas,r8a774a1-thermal", .compatible = "renesas,r8a774a1-thermal",
.data = &rcar_gen3_ths_tj_1_m3_w, .data = &rcar_m3w_thermal_info,
}, },
{ {
.compatible = "renesas,r8a774b1-thermal", .compatible = "renesas,r8a774b1-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a774e1-thermal", .compatible = "renesas,r8a774e1-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a7795-thermal", .compatible = "renesas,r8a7795-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a7796-thermal", .compatible = "renesas,r8a7796-thermal",
.data = &rcar_gen3_ths_tj_1_m3_w, .data = &rcar_m3w_thermal_info,
}, },
{ {
.compatible = "renesas,r8a77961-thermal", .compatible = "renesas,r8a77961-thermal",
.data = &rcar_gen3_ths_tj_1_m3_w, .data = &rcar_m3w_thermal_info,
}, },
{ {
.compatible = "renesas,r8a77965-thermal", .compatible = "renesas,r8a77965-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a77980-thermal", .compatible = "renesas,r8a77980-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a779a0-thermal", .compatible = "renesas,r8a779a0-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen3_thermal_info,
}, },
{ {
.compatible = "renesas,r8a779f0-thermal", .compatible = "renesas,r8a779f0-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen4_thermal_info,
}, },
{ {
.compatible = "renesas,r8a779g0-thermal", .compatible = "renesas,r8a779g0-thermal",
.data = &rcar_gen3_ths_tj_1, .data = &rcar_gen4_thermal_info,
}, },
{}, {},
}; };
...@@ -418,7 +481,6 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev) ...@@ -418,7 +481,6 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev)
{ {
struct rcar_gen3_thermal_priv *priv; struct rcar_gen3_thermal_priv *priv;
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
const int *ths_tj_1 = of_device_get_match_data(dev);
struct resource *res; struct resource *res;
struct thermal_zone_device *zone; struct thermal_zone_device *zone;
unsigned int i; unsigned int i;
...@@ -430,6 +492,7 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev) ...@@ -430,6 +492,7 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev)
priv->ops = rcar_gen3_tz_of_ops; priv->ops = rcar_gen3_tz_of_ops;
priv->info = of_device_get_match_data(dev);
platform_set_drvdata(pdev, priv); platform_set_drvdata(pdev, priv);
if (rcar_gen3_thermal_request_irqs(priv, pdev)) if (rcar_gen3_thermal_request_irqs(priv, pdev))
...@@ -469,7 +532,7 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev) ...@@ -469,7 +532,7 @@ static int rcar_gen3_thermal_probe(struct platform_device *pdev)
struct rcar_gen3_thermal_tsc *tsc = priv->tscs[i]; struct rcar_gen3_thermal_tsc *tsc = priv->tscs[i];
rcar_gen3_thermal_init(priv, tsc); rcar_gen3_thermal_init(priv, tsc);
rcar_gen3_thermal_calc_coefs(priv, tsc, *ths_tj_1); rcar_gen3_thermal_calc_coefs(priv, tsc, priv->info->ths_tj_1);
zone = devm_thermal_of_zone_register(dev, i, tsc, &priv->ops); zone = devm_thermal_of_zone_register(dev, i, tsc, &priv->ops);
if (IS_ERR(zone)) { if (IS_ERR(zone)) {
......
...@@ -227,14 +227,12 @@ int st_thermal_register(struct platform_device *pdev, ...@@ -227,14 +227,12 @@ int st_thermal_register(struct platform_device *pdev,
} }
EXPORT_SYMBOL_GPL(st_thermal_register); EXPORT_SYMBOL_GPL(st_thermal_register);
int st_thermal_unregister(struct platform_device *pdev) void st_thermal_unregister(struct platform_device *pdev)
{ {
struct st_thermal_sensor *sensor = platform_get_drvdata(pdev); struct st_thermal_sensor *sensor = platform_get_drvdata(pdev);
st_thermal_sensor_off(sensor); st_thermal_sensor_off(sensor);
thermal_zone_device_unregister(sensor->thermal_dev); thermal_zone_device_unregister(sensor->thermal_dev);
return 0;
} }
EXPORT_SYMBOL_GPL(st_thermal_unregister); EXPORT_SYMBOL_GPL(st_thermal_unregister);
......
...@@ -94,7 +94,7 @@ struct st_thermal_sensor { ...@@ -94,7 +94,7 @@ struct st_thermal_sensor {
extern int st_thermal_register(struct platform_device *pdev, extern int st_thermal_register(struct platform_device *pdev,
const struct of_device_id *st_thermal_of_match); const struct of_device_id *st_thermal_of_match);
extern int st_thermal_unregister(struct platform_device *pdev); extern void st_thermal_unregister(struct platform_device *pdev);
extern const struct dev_pm_ops st_thermal_pm_ops; extern const struct dev_pm_ops st_thermal_pm_ops;
#endif /* __STI_RESET_SYSCFG_H */ #endif /* __STI_RESET_SYSCFG_H */
...@@ -172,9 +172,9 @@ static int st_mmap_probe(struct platform_device *pdev) ...@@ -172,9 +172,9 @@ static int st_mmap_probe(struct platform_device *pdev)
return st_thermal_register(pdev, st_mmap_thermal_of_match); return st_thermal_register(pdev, st_mmap_thermal_of_match);
} }
static int st_mmap_remove(struct platform_device *pdev) static void st_mmap_remove(struct platform_device *pdev)
{ {
return st_thermal_unregister(pdev); st_thermal_unregister(pdev);
} }
static struct platform_driver st_mmap_thermal_driver = { static struct platform_driver st_mmap_thermal_driver = {
...@@ -184,7 +184,7 @@ static struct platform_driver st_mmap_thermal_driver = { ...@@ -184,7 +184,7 @@ static struct platform_driver st_mmap_thermal_driver = {
.of_match_table = st_mmap_thermal_of_match, .of_match_table = st_mmap_thermal_of_match,
}, },
.probe = st_mmap_probe, .probe = st_mmap_probe,
.remove = st_mmap_remove, .remove_new = st_mmap_remove,
}; };
module_platform_driver(st_mmap_thermal_driver); module_platform_driver(st_mmap_thermal_driver);
......
...@@ -319,6 +319,11 @@ static int sun8i_ths_calibrate(struct ths_device *tmdev) ...@@ -319,6 +319,11 @@ static int sun8i_ths_calibrate(struct ths_device *tmdev)
return ret; return ret;
} }
static void sun8i_ths_reset_control_assert(void *data)
{
reset_control_assert(data);
}
static int sun8i_ths_resource_init(struct ths_device *tmdev) static int sun8i_ths_resource_init(struct ths_device *tmdev)
{ {
struct device *dev = tmdev->dev; struct device *dev = tmdev->dev;
...@@ -339,47 +344,35 @@ static int sun8i_ths_resource_init(struct ths_device *tmdev) ...@@ -339,47 +344,35 @@ static int sun8i_ths_resource_init(struct ths_device *tmdev)
if (IS_ERR(tmdev->reset)) if (IS_ERR(tmdev->reset))
return PTR_ERR(tmdev->reset); return PTR_ERR(tmdev->reset);
tmdev->bus_clk = devm_clk_get(&pdev->dev, "bus"); ret = reset_control_deassert(tmdev->reset);
if (ret)
return ret;
ret = devm_add_action_or_reset(dev, sun8i_ths_reset_control_assert,
tmdev->reset);
if (ret)
return ret;
tmdev->bus_clk = devm_clk_get_enabled(&pdev->dev, "bus");
if (IS_ERR(tmdev->bus_clk)) if (IS_ERR(tmdev->bus_clk))
return PTR_ERR(tmdev->bus_clk); return PTR_ERR(tmdev->bus_clk);
} }
if (tmdev->chip->has_mod_clk) { if (tmdev->chip->has_mod_clk) {
tmdev->mod_clk = devm_clk_get(&pdev->dev, "mod"); tmdev->mod_clk = devm_clk_get_enabled(&pdev->dev, "mod");
if (IS_ERR(tmdev->mod_clk)) if (IS_ERR(tmdev->mod_clk))
return PTR_ERR(tmdev->mod_clk); return PTR_ERR(tmdev->mod_clk);
} }
ret = reset_control_deassert(tmdev->reset);
if (ret)
return ret;
ret = clk_prepare_enable(tmdev->bus_clk);
if (ret)
goto assert_reset;
ret = clk_set_rate(tmdev->mod_clk, 24000000); ret = clk_set_rate(tmdev->mod_clk, 24000000);
if (ret) if (ret)
goto bus_disable; return ret;
ret = clk_prepare_enable(tmdev->mod_clk);
if (ret)
goto bus_disable;
ret = sun8i_ths_calibrate(tmdev); ret = sun8i_ths_calibrate(tmdev);
if (ret) if (ret)
goto mod_disable; return ret;
return 0; return 0;
mod_disable:
clk_disable_unprepare(tmdev->mod_clk);
bus_disable:
clk_disable_unprepare(tmdev->bus_clk);
assert_reset:
reset_control_assert(tmdev->reset);
return ret;
} }
static int sun8i_h3_thermal_init(struct ths_device *tmdev) static int sun8i_h3_thermal_init(struct ths_device *tmdev)
...@@ -475,9 +468,7 @@ static int sun8i_ths_register(struct ths_device *tmdev) ...@@ -475,9 +468,7 @@ static int sun8i_ths_register(struct ths_device *tmdev)
if (IS_ERR(tmdev->sensor[i].tzd)) if (IS_ERR(tmdev->sensor[i].tzd))
return PTR_ERR(tmdev->sensor[i].tzd); return PTR_ERR(tmdev->sensor[i].tzd);
if (devm_thermal_add_hwmon_sysfs(tmdev->dev, tmdev->sensor[i].tzd)) devm_thermal_add_hwmon_sysfs(tmdev->dev, tmdev->sensor[i].tzd);
dev_warn(tmdev->dev,
"Failed to add hwmon sysfs attributes\n");
} }
return 0; return 0;
...@@ -530,17 +521,6 @@ static int sun8i_ths_probe(struct platform_device *pdev) ...@@ -530,17 +521,6 @@ static int sun8i_ths_probe(struct platform_device *pdev)
return 0; return 0;
} }
static int sun8i_ths_remove(struct platform_device *pdev)
{
struct ths_device *tmdev = platform_get_drvdata(pdev);
clk_disable_unprepare(tmdev->mod_clk);
clk_disable_unprepare(tmdev->bus_clk);
reset_control_assert(tmdev->reset);
return 0;
}
static const struct ths_thermal_chip sun8i_a83t_ths = { static const struct ths_thermal_chip sun8i_a83t_ths = {
.sensor_num = 3, .sensor_num = 3,
.scale = 705, .scale = 705,
...@@ -642,7 +622,6 @@ MODULE_DEVICE_TABLE(of, of_ths_match); ...@@ -642,7 +622,6 @@ MODULE_DEVICE_TABLE(of, of_ths_match);
static struct platform_driver ths_driver = { static struct platform_driver ths_driver = {
.probe = sun8i_ths_probe, .probe = sun8i_ths_probe,
.remove = sun8i_ths_remove,
.driver = { .driver = {
.name = "sun8i-thermal", .name = "sun8i-thermal",
.of_match_table = of_ths_match, .of_match_table = of_ths_match,
......
...@@ -523,8 +523,7 @@ static int tegra_tsensor_register_channel(struct tegra_tsensor *ts, ...@@ -523,8 +523,7 @@ static int tegra_tsensor_register_channel(struct tegra_tsensor *ts,
return 0; return 0;
} }
if (devm_thermal_add_hwmon_sysfs(ts->dev, tsc->tzd)) devm_thermal_add_hwmon_sysfs(ts->dev, tsc->tzd);
dev_warn(ts->dev, "failed to add hwmon sysfs attributes\n");
return 0; return 0;
} }
......
...@@ -13,6 +13,8 @@ ...@@ -13,6 +13,8 @@
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/thermal.h> #include <linux/thermal.h>
#include "thermal_hwmon.h"
struct gadc_thermal_info { struct gadc_thermal_info {
struct device *dev; struct device *dev;
struct thermal_zone_device *tz_dev; struct thermal_zone_device *tz_dev;
...@@ -153,6 +155,8 @@ static int gadc_thermal_probe(struct platform_device *pdev) ...@@ -153,6 +155,8 @@ static int gadc_thermal_probe(struct platform_device *pdev)
return ret; return ret;
} }
devm_thermal_add_hwmon_sysfs(&pdev->dev, gti->tz_dev);
return 0; return 0;
} }
......
...@@ -23,6 +23,8 @@ ...@@ -23,6 +23,8 @@
#define DEFAULT_THERMAL_GOVERNOR "user_space" #define DEFAULT_THERMAL_GOVERNOR "user_space"
#elif defined(CONFIG_THERMAL_DEFAULT_GOV_POWER_ALLOCATOR) #elif defined(CONFIG_THERMAL_DEFAULT_GOV_POWER_ALLOCATOR)
#define DEFAULT_THERMAL_GOVERNOR "power_allocator" #define DEFAULT_THERMAL_GOVERNOR "power_allocator"
#elif defined(CONFIG_THERMAL_DEFAULT_GOV_BANG_BANG)
#define DEFAULT_THERMAL_GOVERNOR "bang_bang"
#endif #endif
/* Initial state of a cooling device during binding */ /* Initial state of a cooling device during binding */
......
...@@ -271,11 +271,14 @@ int devm_thermal_add_hwmon_sysfs(struct device *dev, struct thermal_zone_device ...@@ -271,11 +271,14 @@ int devm_thermal_add_hwmon_sysfs(struct device *dev, struct thermal_zone_device
ptr = devres_alloc(devm_thermal_hwmon_release, sizeof(*ptr), ptr = devres_alloc(devm_thermal_hwmon_release, sizeof(*ptr),
GFP_KERNEL); GFP_KERNEL);
if (!ptr) if (!ptr) {
dev_warn(dev, "Failed to allocate device resource data\n");
return -ENOMEM; return -ENOMEM;
}
ret = thermal_add_hwmon_sysfs(tz); ret = thermal_add_hwmon_sysfs(tz);
if (ret) { if (ret) {
dev_warn(dev, "Failed to add hwmon sysfs attributes\n");
devres_free(ptr); devres_free(ptr);
return ret; return ret;
} }
......
...@@ -182,8 +182,7 @@ int ti_thermal_expose_sensor(struct ti_bandgap *bgp, int id, ...@@ -182,8 +182,7 @@ int ti_thermal_expose_sensor(struct ti_bandgap *bgp, int id,
ti_bandgap_write_update_interval(bgp, data->sensor_id, ti_bandgap_write_update_interval(bgp, data->sensor_id,
TI_BANDGAP_UPDATE_INTERVAL_MS); TI_BANDGAP_UPDATE_INTERVAL_MS);
if (devm_thermal_add_hwmon_sysfs(bgp->dev, data->ti_thermal)) devm_thermal_add_hwmon_sysfs(bgp->dev, data->ti_thermal);
dev_warn(bgp->dev, "failed to add hwmon sysfs attributes\n");
return 0; return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment