aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRafael J. Wysocki <rafael.j.wysocki@intel.com>2014-11-19 01:44:11 +0100
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>2014-11-20 01:24:16 +0100
commit78579b7c7eb45f0e7ec5e9437087ed21749f9a9c (patch)
tree079b23f3867daa6d02c5f5d3e5081b869fd3ca39
parentfc14f9c1272f62c3e8d01300f52467c0d9af50f9 (diff)
ACPI / PM: Ignore wakeup setting if the ACPI companion can't wake uppm+acpi-3.18-rc6
As reported by Dmitry, on some Chromebooks there are devices with corresponding ACPI objects and with unusual system wakeup configuration. Namely, they technically are wakeup-capable, but the wakeup is handled via a platform-specific out-of-band mechanism and the ACPI PM layer has no information on the wakeup capability. As a result, device_may_wakeup(dev) called from acpi_dev_suspend_late() returns 'true' for those devices, but the wakeup.flags.valid flag is unset for the corresponding ACPI device objects, so acpi_device_wakeup() reproducibly fails for them causing acpi_dev_suspend_late() to return an error code. The entire system suspend is then aborted and the machines in question cannot suspend at all. Address the problem by ignoring the device_may_wakeup(dev) return value in acpi_dev_suspend_late() if the ACPI companion of the device being handled has wakeup.flags.valid unset (in which case it is clear that the wakeup is supposed to be handled by other means). This fixes a regression introduced by commit a76e9bd89ae7 (i2c: attach/detach I2C client device to the ACPI power domain) as the affected systems could suspend and resume successfully before that commit. Fixes: a76e9bd89ae7 (i2c: attach/detach I2C client device to the ACPI power domain) Reported-by: Dmitry Torokhov <dtor@chromium.org> Reviewed-by: Dmitry Torokhov <dtor@chromium.org> Cc: 3.13+ <stable@vger.kernel.org> # 3.13+ Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
-rw-r--r--drivers/acpi/device_pm.c2
1 files changed, 1 insertions, 1 deletions
diff --git a/drivers/acpi/device_pm.c b/drivers/acpi/device_pm.c
index 143ec6ea1468..7db193160766 100644
--- a/drivers/acpi/device_pm.c
+++ b/drivers/acpi/device_pm.c
@@ -878,7 +878,7 @@ int acpi_dev_suspend_late(struct device *dev)
return 0;
target_state = acpi_target_system_state();
- wakeup = device_may_wakeup(dev);
+ wakeup = device_may_wakeup(dev) && acpi_device_can_wakeup(adev);
error = acpi_device_wakeup(adev, target_state, wakeup);
if (wakeup && error)
return error;