Commit add74a2b authored by Patrick Mochel's avatar Patrick Mochel

[power] Fix device suspend handling

- Handle -EAGAIN in device_suspend() properly: keep going, with error reset
  to 0. 

- Call dpm_resume() if we got a real error, instead of device_resume(), which
  would deadlock.
parent 6cf73674
...@@ -58,7 +58,8 @@ extern void dpm_sysfs_remove(struct device *); ...@@ -58,7 +58,8 @@ extern void dpm_sysfs_remove(struct device *);
/* /*
* resume.c * resume.c
*/ */
extern int dpm_resume(void);
extern void dpm_resume(void);
extern void dpm_power_up(void); extern void dpm_power_up(void);
extern int resume_device(struct device *); extern int resume_device(struct device *);
......
...@@ -28,6 +28,19 @@ int resume_device(struct device * dev) ...@@ -28,6 +28,19 @@ int resume_device(struct device * dev)
} }
void dpm_resume(void)
{
while(!list_empty(&dpm_off)) {
struct list_head * entry = dpm_off.next;
struct device * dev = to_device(entry);
list_del_init(entry);
resume_device(dev);
list_add_tail(entry,&dpm_active);
}
}
/** /**
* device_resume - Restore state of each device in system. * device_resume - Restore state of each device in system.
* *
...@@ -38,13 +51,7 @@ int resume_device(struct device * dev) ...@@ -38,13 +51,7 @@ int resume_device(struct device * dev)
void device_resume(void) void device_resume(void)
{ {
down(&dpm_sem); down(&dpm_sem);
while(!list_empty(&dpm_off)) { dpm_resume();
struct list_head * entry = dpm_off.next;
struct device * dev = to_device(entry);
list_del_init(entry);
resume_device(dev);
list_add_tail(entry,&dpm_active);
}
up(&dpm_sem); up(&dpm_sem);
} }
......
...@@ -81,14 +81,18 @@ int device_suspend(u32 state) ...@@ -81,14 +81,18 @@ int device_suspend(u32 state)
while(!list_empty(&dpm_active)) { while(!list_empty(&dpm_active)) {
struct list_head * entry = dpm_active.prev; struct list_head * entry = dpm_active.prev;
struct device * dev = to_device(entry); struct device * dev = to_device(entry);
if ((error = suspend_device(dev,state))) if ((error = suspend_device(dev,state))) {
goto Error; if (error != -EAGAIN)
goto Error;
else
error = 0;
}
} }
Done: Done:
up(&dpm_sem); up(&dpm_sem);
return error; return error;
Error: Error:
device_resume(); dpm_resume();
goto Done; goto Done;
} }
......
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