All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] PM / Domains: Use subsystem runtime suspend/resume callbacks by default
@ 2012-05-20 22:37 Rafael J. Wysocki
  0 siblings, 0 replies; only message in thread
From: Rafael J. Wysocki @ 2012-05-20 22:37 UTC (permalink / raw)
  To: Linux PM list; +Cc: LKML

From: Rafael J. Wysocki <rjw@sisk.pl>

Currently, the default "save state" and "restore state" routines
for generic PM domains, pm_genpd_default_save_state() and
pm_genpd_default_restore_state(), respectively, only use runtime PM
callbacks provided by device drivers, but in general those callbacks
need not provide the entire necessary functionality.  Namely, in
general it may be necessary to execute subsystem (i.e. device type,
device class or bus type) callbacks that will carry out all of the
necessary operations.

For this reason, modify pm_genpd_default_save_state() and
pm_genpd_default_restore_state() to execute subsystem callbacks,
if they are provided, and fall back to driver callbacks otherwise.

Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl>
---
 drivers/base/power/domain.c |   32 ++++++++++++++++++++++++--------
 1 file changed, 24 insertions(+), 8 deletions(-)

Index: linux/drivers/base/power/domain.c
===================================================================
--- linux.orig/drivers/base/power/domain.c
+++ linux/drivers/base/power/domain.c
@@ -1738,16 +1738,24 @@ int genpd_detach_cpuidle(struct generic_
 static int pm_genpd_default_save_state(struct device *dev)
 {
 	int (*cb)(struct device *__dev);
-	struct device_driver *drv = dev->driver;
 
 	cb = dev_gpd_data(dev)->ops.save_state;
 	if (cb)
 		return cb(dev);
 
-	if (drv && drv->pm && drv->pm->runtime_suspend)
-		return drv->pm->runtime_suspend(dev);
+	if (dev->type && dev->type->pm)
+		cb = dev->type->pm->runtime_suspend;
+	else if (dev->class && dev->class->pm)
+		cb = dev->class->pm->runtime_suspend;
+	else if (dev->bus && dev->bus->pm)
+		cb = dev->bus->pm->runtime_suspend;
+	else
+		cb = NULL;
 
-	return 0;
+	if (!cb && dev->driver && dev->driver->pm)
+		cb = dev->driver->pm->runtime_suspend;
+
+	return cb ? cb(dev) : 0;
 }
 
 /**
@@ -1757,16 +1765,24 @@ static int pm_genpd_default_save_state(s
 static int pm_genpd_default_restore_state(struct device *dev)
 {
 	int (*cb)(struct device *__dev);
-	struct device_driver *drv = dev->driver;
 
 	cb = dev_gpd_data(dev)->ops.restore_state;
 	if (cb)
 		return cb(dev);
 
-	if (drv && drv->pm && drv->pm->runtime_resume)
-		return drv->pm->runtime_resume(dev);
+	if (dev->type && dev->type->pm)
+		cb = dev->type->pm->runtime_resume;
+	else if (dev->class && dev->class->pm)
+		cb = dev->class->pm->runtime_resume;
+	else if (dev->bus && dev->bus->pm)
+		cb = dev->bus->pm->runtime_resume;
+	else
+		cb = NULL;
+
+	if (!cb && dev->driver && dev->driver->pm)
+		cb = dev->driver->pm->runtime_resume;
 
-	return 0;
+	return cb ? cb(dev) : 0;
 }
 
 #ifdef CONFIG_PM_SLEEP

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2012-05-20 22:32 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2012-05-20 22:37 [PATCH] PM / Domains: Use subsystem runtime suspend/resume callbacks by default Rafael J. Wysocki

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.