#include <linux/interrupt.h>
#include <linux/sched.h>
#include <linux/async.h>
-#include <linux/timer.h>
#include "../base.h"
#include "power.h"
static DEFINE_MUTEX(dpm_list_mtx);
static pm_message_t pm_transition;
-static void dpm_drv_timeout(unsigned long data);
-struct dpm_drv_wd_data {
- struct device *dev;
- struct task_struct *tsk;
-};
-
/*
* Set once the preparation of devices for a PM transition has started, reset
* before starting to resume devices. Protected by dpm_list_mtx.
TRACE_DEVICE(dev);
TRACE_RESUME(0);
- if (dev->parent && (dev->parent->power.status >= DPM_OFF ||
- dev->parent->power.status == DPM_RESUMING))
- dpm_wait(dev->parent, async);
+ dpm_wait(dev->parent, async);
device_lock(dev);
dev->power.status = DPM_RESUMING;
&& !pm_trace_is_enabled();
}
-/**
- * dpm_drv_timeout - Driver suspend / resume watchdog handler
- * @data: struct device which timed out
- *
- * Called when a driver has timed out suspending or resuming.
- * There's not much we can do here to recover so
- * BUG() out for a crash-dump
- *
- */
-static void dpm_drv_timeout(unsigned long data)
-{
- struct dpm_drv_wd_data *wd_data = (void *)data;
- struct device *dev = wd_data->dev;
- struct task_struct *tsk = wd_data->tsk;
-
- printk(KERN_EMERG "**** DPM device timeout: %s (%s)\n", dev_name(dev),
- (dev->driver ? dev->driver->name : "no driver"));
-
- printk(KERN_EMERG "dpm suspend stack:\n");
- show_stack(tsk, NULL);
-
- BUG();
-}
-
/**
* dpm_resume - Execute "resume" callbacks for non-sysdev devices.
* @state: PM transition of the system being carried out.
static int __device_suspend(struct device *dev, pm_message_t state, bool async)
{
int error = 0;
- struct timer_list timer;
- struct dpm_drv_wd_data data;
dpm_wait_for_children(dev, async);
-
- data.dev = dev;
- data.tsk = get_current();
- init_timer_on_stack(&timer);
- timer.expires = jiffies + HZ * 12;
- timer.function = dpm_drv_timeout;
- timer.data = (unsigned long)&data;
- add_timer(&timer);
-
device_lock(dev);
if (async_error)
End:
device_unlock(dev);
-
- del_timer_sync(&timer);
- destroy_timer_on_stack(&timer);
-
complete_all(&dev->power.completion);
return error;