linux/drivers/acpi
Rafael J. Wysocki 5c7dd710f6 ACPI / PCI / PM: Fix device PM regression related to D3hot/D3cold
Commit 1cc0c998fd ("ACPI: Fix D3hot v D3cold confusion") introduced a
bug in __acpi_bus_set_power() and changed the behavior of
acpi_pci_set_power_state() in such a way that it generally doesn't work
as expected if PCI_D3hot is passed to it as the second argument.

First off, if ACPI_STATE_D3 (equal to ACPI_STATE_D3_COLD) is passed to
__acpi_bus_set_power() and the explicit_set flag is set for the D3cold
state, the function will try to execute AML method called "_PS4", which
doesn't exist.

Fix this by adding a check to ensure that the name of the AML method
to execute for transitions to ACPI_STATE_D3_COLD is correct in
__acpi_bus_set_power().  Also make sure that the explicit_set flag
for ACPI_STATE_D3_COLD will be set if _PS3 is present and modify
acpi_power_transition() to avoid accessing power resources for
ACPI_STATE_D3_COLD, because they don't exist.

Second, if PCI_D3hot is passed to acpi_pci_set_power_state() as the
target state, the function will request a transition to
ACPI_STATE_D3_HOT instead of ACPI_STATE_D3.  However,
ACPI_STATE_D3_HOT is now only marked as supported if the _PR3 AML
method is defined for the given device, which is rare.  This causes
problems to happen on systems where devices were successfully put
into ACPI D3 by pci_set_power_state(PCI_D3hot) which doesn't work
now.  In particular, some unused graphics adapters are not turned
off as a result.

To fix this issue restore the old behavior of
acpi_pci_set_power_state(), which is to request a transition to
ACPI_STATE_D3 (equal to ACPI_STATE_D3_COLD) if either PCI_D3hot or
PCI_D3cold is passed to it as the argument.

This approach is not ideal, because generally power should not
be removed from devices if PCI_D3hot is the target power state,
but since this behavior is relied on, we have no choice but to
restore it at the moment and spend more time on designing a
better solution in the future.

References: https://bugzilla.kernel.org/show_bug.cgi?id=43228
Reported-by: rocko <rockorequin@hotmail.com>
Reported-by: Cristian Rodríguez <crrodriguez@opensuse.org>
Reported-and-tested-by: Peter <lekensteyn@gmail.com>
Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
2012-05-17 16:16:16 -07:00
..
acpica Revert "ACPI: ignore FADT reset-reg-sup flag" 2012-04-20 11:19:35 -07:00
apei Merge branch 'apei' into release 2012-03-30 16:14:02 -04:00
ac.c treewide: fix potentially dangerous trailing ';' in #defined values/expressions 2011-07-21 14:10:00 +02:00
acpi_ipmi.c IPMI/ACPI: Add the IPMI opregion driver to enable ACPI to access BMC controller 2010-12-14 00:22:14 -05:00
acpi_memhotplug.c include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h 2010-03-30 22:02:32 +09:00
acpi_pad.c ACPI: minor printk format change in acpi_pad 2011-03-23 01:36:45 -04:00
battery.c switch procfs to umode_t use 2012-01-03 22:54:56 -05:00
bgrt.c ACPI: Add support for exposing BGRT data 2012-03-30 04:09:24 -04:00
blacklist.c acpi: delete module.h include from files explicitly not needing it 2011-10-31 19:30:33 -04:00
bus.c ACPI / PCI / PM: Fix device PM regression related to D3hot/D3cold 2012-05-17 16:16:16 -07:00
button.c ACPI button: remove unused procfs I/F 2011-03-22 23:20:35 -04:00
cm_sbs.c ACPI: Move definition of PREFIX from acpi_bus.h to internal..h 2009-08-28 19:57:27 -04:00
container.c include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h 2010-03-30 22:02:32 +09:00
custom_method.c ACPI: Split out custom_method functionality into an own driver 2011-05-29 01:50:40 -04:00
debugfs.c acpi: add export.h to files using THIS_MODULE/EXPORT_SYMBOL 2011-10-31 19:30:34 -04:00
dock.c module_param: make bool parameters really bool (drivers & misc) 2012-01-13 09:32:20 +10:30
ec_sys.c simple_open: automatically convert to simple_open() 2012-04-05 15:25:50 -07:00
ec.c Merge branch 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux 2012-03-30 16:45:39 -07:00
event.c acpi: add export.h to files using THIS_MODULE/EXPORT_SYMBOL 2011-10-31 19:30:34 -04:00
fan.c ACPI: constify ops structs 2011-07-16 18:36:17 -04:00
glue.c acpi: add export.h to files using THIS_MODULE/EXPORT_SYMBOL 2011-10-31 19:30:34 -04:00
hed.c ACPI Hardware Error Device (PNP0C33) support 2010-05-19 22:40:24 -04:00
internal.h ACPI: Cleanup custom_method debug stuff 2011-05-29 01:50:04 -04:00
Kconfig ACPI: Add support for exposing BGRT data 2012-03-30 04:09:24 -04:00
Makefile ACPI: Add support for exposing BGRT data 2012-03-30 04:09:24 -04:00
numa.c ACPI: Store SRAT table revision 2012-01-17 04:19:04 -05:00
nvs.c ACPI / PM: print physical addresses consistently with other parts of kernel 2012-03-30 02:46:57 -04:00
osl.c Revert "ACPI: Make ACPI interrupt threaded" 2012-04-18 10:16:27 -07:00
pci_bind.c PCI / ACPI / PM: Platform support for PCI PME wake-up 2010-02-22 16:21:02 -08:00
pci_irq.c PCI/PM/Runtime: make PCI traces quieter 2012-01-06 12:11:16 -08:00
pci_link.c ACPI: Use syscore_ops instead of sysdev class and sysdev 2011-03-18 18:22:21 -04:00
pci_root.c PCI: Rework ASPM disable code 2012-01-06 12:10:26 -08:00
pci_slot.c module_param: make bool parameters really bool (drivers & misc) 2012-01-13 09:32:20 +10:30
power.c ACPI / PCI / PM: Fix device PM regression related to D3hot/D3cold 2012-05-17 16:16:16 -07:00
proc.c acpi: add export.h to files using THIS_MODULE/EXPORT_SYMBOL 2011-10-31 19:30:34 -04:00
processor_core.c ACPI: processor: fix acpi_get_cpuid for UP processor 2012-01-17 05:25:08 -05:00
processor_driver.c Merge branch 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux 2012-03-30 16:45:39 -07:00
processor_idle.c Merge branches 'idle-fix' and 'misc' into release 2012-04-06 21:48:59 -04:00
processor_perflib.c ACPI: Load acpi-cpufreq from processor driver automatically 2012-01-26 16:48:12 -08:00
processor_thermal.c ACPI: Do cpufreq clamping for throttling per package v2 2012-03-22 02:16:14 -04:00
processor_throttling.c ACPI throttling: fix endian bug in acpi_read_throttling_status() 2012-03-30 16:06:12 -04:00
reboot.c Revert "ACPI: ignore FADT reset-reg-sup flag" 2012-04-20 11:19:35 -07:00
sbs.c Merge branch 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6 2011-08-02 21:17:02 -10:00
sbshc.c acpi: add module.h to files implicitly using/relying on it. 2011-10-31 19:30:32 -04:00
sbshc.h
scan.c ACPI / PCI / PM: Fix device PM regression related to D3hot/D3cold 2012-05-17 16:16:16 -07:00
sleep.c ACPI: Convert wake_sleep_flags to a value instead of function 2012-04-23 13:29:07 -07:00
sleep.h ACPI: static sleep_states[] and acpi_gts_bfs_check 2010-10-19 13:44:37 -04:00
sysfs.c ACPI: Export FADT pm_profile integer value to userspace 2011-11-06 20:48:42 -05:00
tables.c ACPI: delete the "acpi=ht" boot option 2010-03-14 20:58:38 -04:00
thermal.c ACPI: Evaluate thermal trip points before reading temperature 2012-03-30 02:38:31 -04:00
utils.c include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h 2010-03-30 22:02:32 +09:00
video_detect.c platform/x86: drop deprecated asus_acpi driver 2012-03-20 12:02:18 -04:00
video.c ACPI video: Don't start video device until its associated input device has been allocated 2012-03-30 15:47:52 -04:00
wakeup.c ACPI / Wakeup: Enable button GPEs unconditionally during initialization 2011-02-12 01:39:53 +01:00