aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Brown <broonie@opensource.wolfsonmicro.com>2013-01-26 23:07:32 -0500
committerSamuel Ortiz <sameo@linux.intel.com>2013-02-13 18:22:47 -0500
commitdc781d0e10fca29123ddde45429d777725c0fde5 (patch)
tree8c4d350002cb2427e3495eb1c746802748e34a9d
parent595e5bf75cea0664eeb63d8df20716f66f4aa459 (diff)
mfd: arizona: Disable interrupts during resume
Runtime power management does not function during system suspend but the Arizona devices need to use runtime power management to power up the device in order to handle interrupts. Try to avoid interrupts firing during resume by disabling the primary IRQ before interrupts are reenabled on resume and only reenabling it again during main resume. The goal is to avoid issues in the situation where an interrupt is asserted during resume (eg, due to it being the wake source) and the interrupt handling gets scheduled prior to the device being able to handle runtime PM. Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com> Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
-rw-r--r--drivers/mfd/arizona-core.c26
1 files changed, 26 insertions, 0 deletions
diff --git a/drivers/mfd/arizona-core.c b/drivers/mfd/arizona-core.c
index 1ab02a7d2b05..9c994b69b063 100644
--- a/drivers/mfd/arizona-core.c
+++ b/drivers/mfd/arizona-core.c
@@ -263,10 +263,36 @@ static int arizona_runtime_suspend(struct device *dev)
263} 263}
264#endif 264#endif
265 265
266#ifdef CONFIG_PM_SLEEP
267static int arizona_resume_noirq(struct device *dev)
268{
269 struct arizona *arizona = dev_get_drvdata(dev);
270
271 dev_dbg(arizona->dev, "Early resume, disabling IRQ\n");
272 disable_irq(arizona->irq);
273
274 return 0;
275}
276
277static int arizona_resume(struct device *dev)
278{
279 struct arizona *arizona = dev_get_drvdata(dev);
280
281 dev_dbg(arizona->dev, "Late resume, reenabling IRQ\n");
282 enable_irq(arizona->irq);
283
284 return 0;
285}
286#endif
287
266const struct dev_pm_ops arizona_pm_ops = { 288const struct dev_pm_ops arizona_pm_ops = {
267 SET_RUNTIME_PM_OPS(arizona_runtime_suspend, 289 SET_RUNTIME_PM_OPS(arizona_runtime_suspend,
268 arizona_runtime_resume, 290 arizona_runtime_resume,
269 NULL) 291 NULL)
292 SET_SYSTEM_SLEEP_PM_OPS(NULL, arizona_resume)
293#ifdef CONFIG_PM_SLEEP
294 .resume_noirq = arizona_resume_noirq,
295#endif
270}; 296};
271EXPORT_SYMBOL_GPL(arizona_pm_ops); 297EXPORT_SYMBOL_GPL(arizona_pm_ops);
272 298