This is a note to let you know that I've just added the patch titled thermal/debugfs: Prevent use-after-free from occurring after cdev removal to the 6.8-stable tree which can be found at: http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary The filename of the patch is: thermal-debugfs-prevent-use-after-free-from-occurrin.patch and it can be found in the queue-6.8 subdirectory. If you, or anyone else, feels it should not be added to the stable tree, please let <stable@xxxxxxxxxxxxxxx> know about it. commit aacf37a6d9231d0968c5cd5beafc8d42aa820265 Author: Rafael J. Wysocki <rafael.j.wysocki@xxxxxxxxx> Date: Fri Apr 26 11:10:10 2024 +0200 thermal/debugfs: Prevent use-after-free from occurring after cdev removal [ Upstream commit d351eb0ab04c3e8109895fc33250cebbce9c11da ] Since thermal_debug_cdev_remove() does not run under cdev->lock, it can run in parallel with thermal_debug_cdev_state_update() and it may free the struct thermal_debugfs object used by the latter after it has been checked against NULL. If that happens, thermal_debug_cdev_state_update() will access memory that has been freed already causing the kernel to crash. Address this by using cdev->lock in thermal_debug_cdev_remove() around the cdev->debugfs value check (in case the same cdev is removed at the same time in two different threads) and its reset to NULL. Fixes: 755113d76786 ("thermal/debugfs: Add thermal cooling device debugfs information") Cc :6.8+ <stable@xxxxxxxxxxxxxxx> # 6.8+ Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@xxxxxxxxx> Reviewed-by: Lukasz Luba <lukasz.luba@xxxxxxx> Signed-off-by: Sasha Levin <sashal@xxxxxxxxxx> diff --git a/drivers/thermal/thermal_debugfs.c b/drivers/thermal/thermal_debugfs.c index 1fe2914a8853b..5693cc8b231aa 100644 --- a/drivers/thermal/thermal_debugfs.c +++ b/drivers/thermal/thermal_debugfs.c @@ -505,15 +505,23 @@ void thermal_debug_cdev_add(struct thermal_cooling_device *cdev) */ void thermal_debug_cdev_remove(struct thermal_cooling_device *cdev) { - struct thermal_debugfs *thermal_dbg = cdev->debugfs; + struct thermal_debugfs *thermal_dbg; - if (!thermal_dbg) + mutex_lock(&cdev->lock); + + thermal_dbg = cdev->debugfs; + if (!thermal_dbg) { + mutex_unlock(&cdev->lock); return; + } + + cdev->debugfs = NULL; + + mutex_unlock(&cdev->lock); mutex_lock(&thermal_dbg->lock); thermal_debugfs_cdev_clear(&thermal_dbg->cdev_dbg); - cdev->debugfs = NULL; mutex_unlock(&thermal_dbg->lock);