diff --git a/Documentation/driver-model/devres.txt b/Documentation/driver-model/devres.txt index b0d775d28e97bebe4875385530a26f0335f90b29..b1ff0b7edb450b3b00506a344671f023c6323dda 100644 --- a/Documentation/driver-model/devres.txt +++ b/Documentation/driver-model/devres.txt @@ -342,6 +342,10 @@ PINCTRL devm_pinctrl_register() devm_pinctrl_unregister() +POWER + devm_reboot_mode_register() + devm_reboot_mode_unregister() + PWM devm_pwm_get() devm_pwm_put() diff --git a/drivers/power/reset/reboot-mode.c b/drivers/power/reset/reboot-mode.c index 2dfbbce0f8174dca4a50a8b9dd29e657bad8af78..fb512183ace3ed818004e10f072a2d4ebc45a184 100644 --- a/drivers/power/reset/reboot-mode.c +++ b/drivers/power/reset/reboot-mode.c @@ -135,6 +135,65 @@ int reboot_mode_unregister(struct reboot_mode_driver *reboot) } EXPORT_SYMBOL_GPL(reboot_mode_unregister); +static void devm_reboot_mode_release(struct device *dev, void *res) +{ + reboot_mode_unregister(*(struct reboot_mode_driver **)res); +} + +/** + * devm_reboot_mode_register() - resource managed reboot_mode_register() + * @dev: device to associate this resource with + * @reboot: reboot mode driver + * + * Returns: 0 on success or a negative error code on failure. + */ +int devm_reboot_mode_register(struct device *dev, + struct reboot_mode_driver *reboot) +{ + struct reboot_mode_driver **dr; + int rc; + + dr = devres_alloc(devm_reboot_mode_release, sizeof(*dr), GFP_KERNEL); + if (!dr) + return -ENOMEM; + + rc = reboot_mode_register(reboot); + if (rc) { + devres_free(dr); + return rc; + } + + *dr = reboot; + devres_add(dev, dr); + + return 0; +} +EXPORT_SYMBOL_GPL(devm_reboot_mode_register); + +static int devm_reboot_mode_match(struct device *dev, void *res, void *data) +{ + struct reboot_mode_driver **p = res; + + if (WARN_ON(!p || !*p)) + return 0; + + return *p == data; +} + +/** + * devm_reboot_mode_unregister() - resource managed reboot_mode_unregister() + * @dev: device to associate this resource with + * @reboot: reboot mode driver + */ +void devm_reboot_mode_unregister(struct device *dev, + struct reboot_mode_driver *reboot) +{ + WARN_ON(devres_release(dev, + devm_reboot_mode_release, + devm_reboot_mode_match, reboot)); +} +EXPORT_SYMBOL_GPL(devm_reboot_mode_unregister); + MODULE_AUTHOR("Andy Yan