Commit 62b01247 authored by Rafael J. Wysocki's avatar Rafael J. Wysocki

PM: Warn if interrupts are enabled during suspend-resume of sysdevs

Sysdevs have to be suspended and resumed with interrupts disabled and
things usually break in a way that's difficult to debug if one of
sysdev drivers enables interrupts by mistake during suspend or
resume.  Add extra checks that will generate warnings in such cases.
Signed-off-by: default avatarRafael J. Wysocki <rjw@sisk.pl>
parent ce4b3c55
...@@ -343,11 +343,15 @@ static void __sysdev_resume(struct sys_device *dev) ...@@ -343,11 +343,15 @@ static void __sysdev_resume(struct sys_device *dev)
/* First, call the class-specific one */ /* First, call the class-specific one */
if (cls->resume) if (cls->resume)
cls->resume(dev); cls->resume(dev);
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled after %pF\n", cls->resume);
/* Call auxillary drivers next. */ /* Call auxillary drivers next. */
list_for_each_entry(drv, &cls->drivers, entry) { list_for_each_entry(drv, &cls->drivers, entry) {
if (drv->resume) if (drv->resume)
drv->resume(dev); drv->resume(dev);
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled after %pF\n", drv->resume);
} }
} }
...@@ -377,6 +381,9 @@ int sysdev_suspend(pm_message_t state) ...@@ -377,6 +381,9 @@ int sysdev_suspend(pm_message_t state)
if (ret) if (ret)
return ret; return ret;
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled while suspending system devices\n");
pr_debug("Suspending System Devices\n"); pr_debug("Suspending System Devices\n");
list_for_each_entry_reverse(cls, &system_kset->list, kset.kobj.entry) { list_for_each_entry_reverse(cls, &system_kset->list, kset.kobj.entry) {
...@@ -393,6 +400,9 @@ int sysdev_suspend(pm_message_t state) ...@@ -393,6 +400,9 @@ int sysdev_suspend(pm_message_t state)
if (ret) if (ret)
goto aux_driver; goto aux_driver;
} }
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled after %pF\n",
drv->suspend);
} }
/* Now call the generic one */ /* Now call the generic one */
...@@ -400,6 +410,9 @@ int sysdev_suspend(pm_message_t state) ...@@ -400,6 +410,9 @@ int sysdev_suspend(pm_message_t state)
ret = cls->suspend(sysdev, state); ret = cls->suspend(sysdev, state);
if (ret) if (ret)
goto cls_driver; goto cls_driver;
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled after %pF\n",
cls->suspend);
} }
} }
} }
...@@ -452,6 +465,9 @@ int sysdev_resume(void) ...@@ -452,6 +465,9 @@ int sysdev_resume(void)
{ {
struct sysdev_class *cls; struct sysdev_class *cls;
WARN_ONCE(!irqs_disabled(),
"Interrupts enabled while resuming system devices\n");
pr_debug("Resuming System Devices\n"); pr_debug("Resuming System Devices\n");
list_for_each_entry(cls, &system_kset->list, kset.kobj.entry) { list_for_each_entry(cls, &system_kset->list, kset.kobj.entry) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment