Devfreq framework can change the device status in the background. To
mitigate this situation make a copy of the status structure and use it
for internal calculations.

Signed-off-by: Lukasz Luba <lukasz.l...@arm.com>
---
 drivers/thermal/devfreq_cooling.c | 14 ++++++++++----
 1 file changed, 10 insertions(+), 4 deletions(-)

diff --git a/drivers/thermal/devfreq_cooling.c 
b/drivers/thermal/devfreq_cooling.c
index 396f16bb6566..36ec6a48606c 100644
--- a/drivers/thermal/devfreq_cooling.c
+++ b/drivers/thermal/devfreq_cooling.c
@@ -348,14 +348,20 @@ static int devfreq_cooling_power2state(struct 
thermal_cooling_device *cdev,
 {
        struct devfreq_cooling_device *dfc = cdev->devdata;
        struct devfreq *df = dfc->devfreq;
-       struct devfreq_dev_status *status = &df->last_status;
-       unsigned long freq = status->current_frequency;
+       struct devfreq_dev_status status;
        unsigned long busy_time;
+       unsigned long freq;
        s32 dyn_power;
        u32 static_power;
        s32 est_power;
        int i;
 
+       mutex_lock(&df->lock);
+       status = df->last_status;
+       mutex_unlock(&df->lock);
+
+       freq = status.current_frequency;
+
        if (dfc->power_ops->get_real_power) {
                /* Scale for resource utilization */
                est_power = power * dfc->res_util;
@@ -367,8 +373,8 @@ static int devfreq_cooling_power2state(struct 
thermal_cooling_device *cdev,
                dyn_power = dyn_power > 0 ? dyn_power : 0;
 
                /* Scale dynamic power for utilization */
-               busy_time = status->busy_time ?: 1;
-               est_power = (dyn_power * status->total_time) / busy_time;
+               busy_time = status.busy_time ?: 1;
+               est_power = (dyn_power * status.total_time) / busy_time;
        }
 
        /*
-- 
2.17.1

_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

Reply via email to