Re: [PATCH v2 4/5] thermal: stm32: improve temperature resolution

From: Daniel Lezcano
Date: Thu Dec 05 2019 - 06:03:18 EST


On 04/11/2019 14:30, Pascal Paillet wrote:
> Currently, the temperature is rounded by 1 or 2 degrees.
> Change the way of computing to avoid rounds.
> Also simplify the sampling time management.

Give more details about the changes in order to let us understand them.

> Signed-off-by: Pascal Paillet <p.paillet@xxxxxx>
> ---
> drivers/thermal/st/stm_thermal.c | 58 ++++++++------------------------
> 1 file changed, 14 insertions(+), 44 deletions(-)
>
> diff --git a/drivers/thermal/st/stm_thermal.c b/drivers/thermal/st/stm_thermal.c
> index cb72252f2800..9986716b17c1 100644
> --- a/drivers/thermal/st/stm_thermal.c
> +++ b/drivers/thermal/st/stm_thermal.c
> @@ -59,7 +59,6 @@
>
> /* Less significant bit position definitions */
> #define TS1_T0_POS 16
> -#define TS1_SMP_TIME_POS 16
> #define TS1_HITTHD_POS 16
> #define TS1_LITTHD_POS 0
> #define HSREF_CLK_DIV_POS 24
> @@ -83,15 +82,10 @@
> #define ONE_MHZ 1000000
> #define POLL_TIMEOUT 5000
> #define STARTUP_TIME 40
> -#define TS1_T0_VAL0 30
> -#define TS1_T0_VAL1 130
> +#define TS1_T0_VAL0 30000 /* 30 celsius */
> +#define TS1_T0_VAL1 130000 /* 130 celsius */
> #define NO_HW_TRIG 0
> -
> -/* The Thermal Framework expects millidegrees */
> -#define mcelsius(temp) ((temp) * 1000)
> -
> -/* The Sensor expects oC degrees */
> -#define celsius(temp) ((temp) / 1000)
> +#define SAMPLING_TIME 15
>
> struct stm_thermal_sensor {
> struct device *dev;
> @@ -259,27 +253,17 @@ static int stm_thermal_calculate_threshold(struct stm_thermal_sensor *sensor,
> int temp, u32 *th)
> {
> int freqM;
> - u32 sampling_time;
> -
> - /* Retrieve the number of periods to sample */
> - sampling_time = (readl_relaxed(sensor->base + DTS_CFGR1_OFFSET) &
> - TS1_SMP_TIME_MASK) >> TS1_SMP_TIME_POS;
>
> /* Figure out the CLK_PTAT frequency for a given temperature */
> - freqM = ((temp - sensor->t0) * sensor->ramp_coeff)
> - + sensor->fmt0;
> -
> - dev_dbg(sensor->dev, "%s: freqM for threshold = %d Hz",
> - __func__, freqM);
> + freqM = ((temp - sensor->t0) * sensor->ramp_coeff) / 1000 +
> + sensor->fmt0;
>
> /* Figure out the threshold sample number */
> - *th = clk_get_rate(sensor->clk);
> + *th = clk_get_rate(sensor->clk) * SAMPLING_TIME / freqM;
> if (!*th)
> return -EINVAL;
>
> - *th = *th / freqM;
> -
> - *th *= sampling_time;
> + dev_dbg(sensor->dev, "freqM=%d Hz, threshold=0x%x", freqM, *th);
>
> return 0;
> }
> @@ -371,40 +355,26 @@ static int stm_thermal_set_trips(void *data, int low, int high)
> static int stm_thermal_get_temp(void *data, int *temp)
> {
> struct stm_thermal_sensor *sensor = data;
> - u32 sampling_time;
> + u32 periods;
> int freqM, ret;
>
> if (sensor->mode != THERMAL_DEVICE_ENABLED)
> return -EAGAIN;
>
> - /* Retrieve the number of samples */
> - ret = readl_poll_timeout(sensor->base + DTS_DR_OFFSET, freqM,
> - (freqM & TS1_MFREQ_MASK), STARTUP_TIME,
> - POLL_TIMEOUT);
> -
> + /* Retrieve the number of periods sampled */
> + ret = readl_relaxed_poll_timeout(sensor->base + DTS_DR_OFFSET, periods,
> + (periods & TS1_MFREQ_MASK),
> + STARTUP_TIME, POLL_TIMEOUT);
> if (ret)
> return ret;
>
> - if (!freqM)
> - return -ENODATA;
> -
> - /* Retrieve the number of periods sampled */
> - sampling_time = (readl_relaxed(sensor->base + DTS_CFGR1_OFFSET) &
> - TS1_SMP_TIME_MASK) >> TS1_SMP_TIME_POS;
> -
> - /* Figure out the number of samples per period */
> - freqM /= sampling_time;
> -
> /* Figure out the CLK_PTAT frequency */
> - freqM = clk_get_rate(sensor->clk) / freqM;
> + freqM = (clk_get_rate(sensor->clk) * SAMPLING_TIME) / periods;
> if (!freqM)
> return -EINVAL;
>
> - dev_dbg(sensor->dev, "%s: freqM=%d\n", __func__, freqM);
> -
> /* Figure out the temperature in mili celsius */
> - *temp = mcelsius(sensor->t0 + ((freqM - sensor->fmt0) /
> - sensor->ramp_coeff));
> + *temp = (freqM - sensor->fmt0) * 1000 / sensor->ramp_coeff + sensor->t0;
>
> return 0;
> }
>


--
<http://www.linaro.org/> Linaro.org â Open source software for ARM SoCs

Follow Linaro: <http://www.facebook.com/pages/Linaro> Facebook |
<http://twitter.com/#!/linaroorg> Twitter |
<http://www.linaro.org/linaro-blog/> Blog