Hi, On Wed, Mar 04, 2026 at 11:33:01PM +0530, Shivendra Pratap wrote: > Devres APIs are intended for use in drivers, where the managed lifetime > of resources is tied directly to the driver attach/detach cycle. In > shared subsystem code, there is no guarantee that the subsystem > functions will only be called after a driver has been attached, nor that > they will not be referenced after the managed resources have been > released during driver detach. > > To ensure correct lifetime handling, avoid using devres-based > allocations in the reboot-mode and explicitly handle allocation and > cleanup of resources. > > Fixes: 4fcd504edbf7 ("power: reset: add reboot mode driver") > Signed-off-by: Shivendra Pratap > --- Reviewed-by: Sebastian Reichel The patch does not apply, though. -- Sebastian > drivers/power/reset/reboot-mode.c | 33 ++++++++++++++++++++------------- > 1 file changed, 20 insertions(+), 13 deletions(-) > > diff --git a/drivers/power/reset/reboot-mode.c b/drivers/power/reset/reboot-mode.c > index fba53f638da04655e756b5f8b7d2d666d1379535..d033043f5250a4de152a7786ef37e88a0ace3bbb 100644 > --- a/drivers/power/reset/reboot-mode.c > +++ b/drivers/power/reset/reboot-mode.c > @@ -3,13 +3,17 @@ > * Copyright (c) 2016, Fuzhou Rockchip Electronics Co., Ltd > */ > > +#define pr_fmt(fmt) "reboot-mode: " fmt > + > #include > #include > #include > #include > #include > +#include > #include > #include > +#include > > #define PREFIX "mode-" > > @@ -74,6 +78,7 @@ int reboot_mode_register(struct reboot_mode_driver *reboot) > struct property *prop; > struct device_node *np = reboot->dev->of_node; > size_t len = strlen(PREFIX); > + u32 magic; > int ret; > > INIT_LIST_HEAD(&reboot->head); > @@ -82,19 +87,18 @@ int reboot_mode_register(struct reboot_mode_driver *reboot) > if (strncmp(prop->name, PREFIX, len)) > continue; > > - info = devm_kzalloc(reboot->dev, sizeof(*info), GFP_KERNEL); > + if (device_property_read_u32(reboot->dev, prop->name, &magic)) { > + pr_debug("reboot mode %s without magic number\n", prop->name); > + continue; > + } > + > + info = kzalloc(sizeof(*info), GFP_KERNEL); > if (!info) { > ret = -ENOMEM; > goto error; > } > > - if (of_property_read_u32(np, prop->name, &info->magic)) { > - dev_err(reboot->dev, "reboot mode %s without magic number\n", > - info->mode); > - devm_kfree(reboot->dev, info); > - continue; > - } > - > + info->magic = magic; > info->mode = kstrdup_const(prop->name + len, GFP_KERNEL); > if (!info->mode) { > ret = -ENOMEM; > @@ -102,8 +106,7 @@ int reboot_mode_register(struct reboot_mode_driver *reboot) > } else if (info->mode[0] == '\0') { > kfree_const(info->mode); > ret = -EINVAL; > - dev_err(reboot->dev, "invalid mode name(%s): too short!\n", > - prop->name); > + pr_err("invalid mode name(%s): too short!\n", prop->name); > goto error; > } > > @@ -116,8 +119,8 @@ int reboot_mode_register(struct reboot_mode_driver *reboot) > return 0; > > error: > - list_for_each_entry(info, &reboot->head, list) > - kfree_const(info->mode); > + kfree(info); > + reboot_mode_unregister(reboot); > > return ret; > } > @@ -130,11 +133,15 @@ EXPORT_SYMBOL_GPL(reboot_mode_register); > int reboot_mode_unregister(struct reboot_mode_driver *reboot) > { > struct mode_info *info; > + struct mode_info *next; > > unregister_reboot_notifier(&reboot->reboot_notifier); > > - list_for_each_entry(info, &reboot->head, list) > + list_for_each_entry_safe(info, next, &reboot->head, list) { > + list_del(&info->list); > kfree_const(info->mode); > + kfree(info); > + } > > return 0; > } > > -- > 2.34.1 >