[prev in list] [next in list] [prev in thread] [next in thread]
List: linux-pm
Subject: Re: [PATCH v2 4/4] PM / core: Print warn if device gets enabled as wakeup source during sleep
From: "Rafael J. Wysocki" <rafael () kernel ! org>
Date: 2017-12-30 0:58:07
Message-ID: CAJZ5v0jWjvfQAttj6uhOhc_Hs1oT=sz3yEGnWGJaCMvJ7HJf8Q () mail ! gmail ! com
[Download RAW message or body]
On Fri, Dec 29, 2017 at 12:37 PM, Ulf Hansson <ulf.hansson@linaro.org> wrote:
> In general, wakeup settings are not supposed to be changed during any of
> the system wide PM phases. The reason is simply that it would break
> guarantees provided by the PM core, to properly act on active wakeup
> sources.
>
> However, there are exceptions to when, in particular, disabling a device as
> wakeup source makes sense. For example, in cases when a driver realizes
> that its device is dead during system suspend. For these scenarios, we
> don't need to care about acting on the wakeup source correctly, because a
> dead device shouldn't deliver wakeup signals.
>
> To this reasoning and to help users to properly manage wakeup settings,
> let's print a warning in cases someone calls device_wakeup_enable() during
> system sleep.
>
> Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
> ---
> drivers/base/power/main.c | 4 ++++
> drivers/base/power/wakeup.c | 4 ++++
> include/linux/pm.h | 1 +
> 3 files changed, 9 insertions(+)
>
> diff --git a/drivers/base/power/main.c b/drivers/base/power/main.c
> index 1327726..6b0d312 100644
> --- a/drivers/base/power/main.c
> +++ b/drivers/base/power/main.c
> @@ -1030,6 +1030,8 @@ static void device_complete(struct device *dev, pm_message_t state)
> callback(dev);
> }
>
> + dev->power.may_set_wakeup = dev->power.can_wakeup;
> +
> device_unlock(dev);
>
> pm_runtime_put(dev);
> @@ -1747,6 +1749,7 @@ static int device_prepare(struct device *dev, pm_message_t state)
>
> device_lock(dev);
>
> + dev->power.may_set_wakeup = false;
> dev->power.wakeup_path = false;
>
> if (dev->power.no_pm_callbacks) {
> @@ -1775,6 +1778,7 @@ static int device_prepare(struct device *dev, pm_message_t state)
> if (ret < 0) {
> suspend_report_result(callback, ret);
> pm_runtime_put(dev);
> + dev->power.may_set_wakeup = dev->power.can_wakeup;
> return ret;
> }
> /*
> diff --git a/drivers/base/power/wakeup.c b/drivers/base/power/wakeup.c
> index cb72965..5445bea 100644
> --- a/drivers/base/power/wakeup.c
> +++ b/drivers/base/power/wakeup.c
> @@ -268,6 +268,9 @@ int device_wakeup_enable(struct device *dev)
> if (!dev || !dev->power.can_wakeup)
> return -EINVAL;
>
> + if (!dev->power.may_set_wakeup)
> + dev_warn(dev, "don't enable as wakup source during sleep!\n");
> +
> ws = wakeup_source_register(dev_name(dev));
> if (!ws)
> return -ENOMEM;
> @@ -413,6 +416,7 @@ void device_set_wakeup_capable(struct device *dev, bool capable)
> return;
>
> dev->power.can_wakeup = capable;
> + dev->power.may_set_wakeup = capable;
> if (device_is_registered(dev) && !list_empty(&dev->power.entry)) {
> if (capable) {
> int ret = wakeup_sysfs_add(dev);
> diff --git a/include/linux/pm.h b/include/linux/pm.h
> index ebc6ef8..106fb15 100644
> --- a/include/linux/pm.h
> +++ b/include/linux/pm.h
> @@ -606,6 +606,7 @@ struct dev_pm_info {
> struct list_head entry;
> struct completion completion;
> struct wakeup_source *wakeup;
> + bool may_set_wakeup:1;
> bool wakeup_path:1;
> bool syscore:1;
> bool no_pm_callbacks:1; /* Owned by the PM core */
> --
I didn't mean anything so complicated. :-)
Just a warning message if (pm_suspend_target_state != PM_SUSPEND_ON)
in device_wakeup_enable() (or equivalent) should be sufficient.
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic