diff options
-rw-r--r-- | TODO | 3 | ||||
-rw-r--r-- | kernel.spec | 12 | ||||
-rw-r--r-- | linux-2.6-enable-more-pci-autosuspend.patch | 452 | ||||
-rw-r--r-- | linux-2.6-usb-pci-autosuspend.patch | 22 | ||||
-rw-r--r-- | runtime_pm_fixups.patch | 138 |
5 files changed, 0 insertions, 627 deletions
@@ -43,9 +43,6 @@ One half of the remaining exec-shield diff. davej bugged Ingo again on Jun 17 2011 about upstreaming. -* runtime_pm_fixups.patch -* linux-2.6-usb-pci-autosuspend.patch -* linux-2.6-enable-more-pci-autosuspend.patch * linux-2.6-acpi-debug-infinite-loop.patch Responsible: mjg59 diff --git a/kernel.spec b/kernel.spec index 60498bcb9..fae86736a 100644 --- a/kernel.spec +++ b/kernel.spec @@ -718,12 +718,6 @@ Patch12027: usb-add-quirk-for-logitech-webcams.patch Patch12029: crypto-register-cryptd-first.patch Patch12030: fix-intel-duplicate-backlight.patch - -# Runtime power management -Patch12203: linux-2.6-usb-pci-autosuspend.patch -Patch12204: linux-2.6-enable-more-pci-autosuspend.patch -Patch12205: runtime_pm_fixups.patch - Patch12303: dmar-disable-when-ricoh-multifunction.patch Patch13003: efi-dont-map-boot-services-on-32bit.patch @@ -1345,12 +1339,6 @@ ApplyPatch usb-add-quirk-for-logitech-webcams.patch ApplyPatch crypto-register-cryptd-first.patch ApplyPatch fix-intel-duplicate-backlight.patch -# Runtime PM -#ApplyPatch linux-2.6-usb-pci-autosuspend.patch -### Broken by implicit notify support & ACPICA rebase -###ApplyPatch linux-2.6-enable-more-pci-autosuspend.patch -#ApplyPatch runtime_pm_fixups.patch - # rhbz#605888 ApplyPatch dmar-disable-when-ricoh-multifunction.patch diff --git a/linux-2.6-enable-more-pci-autosuspend.patch b/linux-2.6-enable-more-pci-autosuspend.patch deleted file mode 100644 index 666ded640..000000000 --- a/linux-2.6-enable-more-pci-autosuspend.patch +++ /dev/null @@ -1,452 +0,0 @@ - drivers/acpi/acpica/aclocal.h | 7 +-- - drivers/acpi/acpica/evgpe.c | 75 +++++++++++++++----------------- - drivers/acpi/acpica/evgpeinit.c | 11 +---- - drivers/acpi/acpica/evgpeutil.c | 5 +- - drivers/acpi/acpica/evxface.c | 23 +++++----- - drivers/acpi/ec.c | 2 +- - drivers/acpi/pci_bind.c | 86 ++++++++++++++++++++++++++++++++++++++ - drivers/acpi/sleep.c | 2 +- - drivers/char/ipmi/ipmi_si_intf.c | 2 +- - include/acpi/acpixf.h | 3 +- - 10 files changed, 143 insertions(+), 73 deletions(-) - -diff --git a/drivers/acpi/acpica/aclocal.h b/drivers/acpi/acpica/aclocal.h -index 2ceb0c0..3663362 100644 ---- a/drivers/acpi/acpica/aclocal.h -+++ b/drivers/acpi/acpica/aclocal.h -@@ -406,17 +406,16 @@ struct acpi_predefined_data { - * - ****************************************************************************/ - --/* Dispatch info for each GPE -- either a method or handler, cannot be both */ -+/* Dispatch info for each GPE */ - - struct acpi_handler_info { - acpi_event_handler address; /* Address of handler, if any */ - void *context; /* Context to be passed to handler */ -- struct acpi_namespace_node *method_node; /* Method node for this GPE level (saved) */ - u8 orig_flags; /* Original misc info about this GPE */ - u8 orig_enabled; /* Set if the GPE was originally enabled */ - }; - --union acpi_gpe_dispatch_info { -+struct acpi_gpe_dispatch_info { - struct acpi_namespace_node *method_node; /* Method node for this GPE level */ - struct acpi_handler_info *handler; - }; -@@ -426,7 +425,7 @@ union acpi_gpe_dispatch_info { - * NOTE: Important to keep this struct as small as possible. - */ - struct acpi_gpe_event_info { -- union acpi_gpe_dispatch_info dispatch; /* Either Method or Handler */ -+ struct acpi_gpe_dispatch_info dispatch; - struct acpi_gpe_register_info *register_info; /* Backpointer to register info */ - u8 flags; /* Misc info about this GPE */ - u8 gpe_number; /* This GPE */ -diff --git a/drivers/acpi/acpica/evgpe.c b/drivers/acpi/acpica/evgpe.c -index f226eac..c4b1c4c 100644 ---- a/drivers/acpi/acpica/evgpe.c -+++ b/drivers/acpi/acpica/evgpe.c -@@ -474,9 +474,7 @@ static void ACPI_SYSTEM_XFACE acpi_ev_asynch_execute_gpe_method(void *context) - * Must check for control method type dispatch one more time to avoid a - * race with ev_gpe_install_handler - */ -- if ((local_gpe_event_info.flags & ACPI_GPE_DISPATCH_MASK) == -- ACPI_GPE_DISPATCH_METHOD) { -- -+ if (local_gpe_event_info.flags & ACPI_GPE_DISPATCH_METHOD) { - /* Allocate the evaluation information block */ - - info = ACPI_ALLOCATE_ZEROED(sizeof(struct acpi_evaluate_info)); -@@ -575,41 +573,15 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) - } - - /* -- * Dispatch the GPE to either an installed handler, or the control method -- * associated with this GPE (_Lxx or _Exx). If a handler exists, we invoke -- * it and do not attempt to run the method. If there is neither a handler -- * nor a method, we disable this GPE to prevent further such pointless -- * events from firing. -+ * Dispatch the GPE to either any installed handler or control -+ * method associated with this GPE (_Lxx or _Exx). We invoke -+ * the method first in case it has side effects that would be -+ * interfered with if the handler has already altered hardware -+ * state. If there is neither a handler nor a method, we -+ * disable this GPE to prevent further such pointless events -+ * from firing. - */ -- switch (gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) { -- case ACPI_GPE_DISPATCH_HANDLER: -- -- /* -- * Invoke the installed handler (at interrupt level) -- * Ignore return status for now. -- * TBD: leave GPE disabled on error? -- */ -- (void)gpe_event_info->dispatch.handler->address(gpe_event_info-> -- dispatch. -- handler-> -- context); -- -- /* It is now safe to clear level-triggered events. */ -- -- if ((gpe_event_info->flags & ACPI_GPE_XRUPT_TYPE_MASK) == -- ACPI_GPE_LEVEL_TRIGGERED) { -- status = acpi_hw_clear_gpe(gpe_event_info); -- if (ACPI_FAILURE(status)) { -- ACPI_EXCEPTION((AE_INFO, status, -- "Unable to clear GPE[0x%2X]", -- gpe_number)); -- return_UINT32(ACPI_INTERRUPT_NOT_HANDLED); -- } -- } -- break; -- -- case ACPI_GPE_DISPATCH_METHOD: -- -+ if (gpe_event_info->flags & ACPI_GPE_DISPATCH_METHOD) { - /* - * Disable the GPE, so it doesn't keep firing before the method has a - * chance to run (it runs asynchronously with interrupts enabled). -@@ -634,10 +606,34 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) - "Unable to queue handler for GPE[0x%2X] - event disabled", - gpe_number)); - } -- break; -+ } - -- default: -+ if (gpe_event_info->flags & ACPI_GPE_DISPATCH_HANDLER) { -+ /* -+ * Invoke the installed handler (at interrupt level) -+ * Ignore return status for now. -+ * TBD: leave GPE disabled on error? -+ */ -+ (void)gpe_event_info->dispatch.handler->address(gpe_event_info-> -+ dispatch. -+ handler-> -+ context); - -+ /* It is now safe to clear level-triggered events. */ -+ -+ if ((gpe_event_info->flags & ACPI_GPE_XRUPT_TYPE_MASK) == -+ ACPI_GPE_LEVEL_TRIGGERED) { -+ status = acpi_hw_clear_gpe(gpe_event_info); -+ if (ACPI_FAILURE(status)) { -+ ACPI_EXCEPTION((AE_INFO, status, -+ "Unable to clear GPE[0x%2X]", -+ gpe_number)); -+ return_UINT32(ACPI_INTERRUPT_NOT_HANDLED); -+ } -+ } -+ } -+ -+ if (!(gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK)) { - /* - * No handler or method to run! - * 03/2010: This case should no longer be possible. We will not allow -@@ -658,7 +654,6 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) - gpe_number)); - return_UINT32(ACPI_INTERRUPT_NOT_HANDLED); - } -- break; - } - - return_UINT32(ACPI_INTERRUPT_HANDLED); -diff --git a/drivers/acpi/acpica/evgpeinit.c b/drivers/acpi/acpica/evgpeinit.c -index 2c7def9..9915b52 100644 ---- a/drivers/acpi/acpica/evgpeinit.c -+++ b/drivers/acpi/acpica/evgpeinit.c -@@ -386,16 +386,7 @@ acpi_ev_match_gpe_method(acpi_handle obj_handle, - return_ACPI_STATUS(AE_OK); - } - -- if ((gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) == -- ACPI_GPE_DISPATCH_HANDLER) { -- -- /* If there is already a handler, ignore this GPE method */ -- -- return_ACPI_STATUS(AE_OK); -- } -- -- if ((gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) == -- ACPI_GPE_DISPATCH_METHOD) { -+ if (gpe_event_info->flags & ACPI_GPE_DISPATCH_METHOD) { - /* - * If there is already a method, ignore this method. But check - * for a type mismatch (if both the _Lxx AND _Exx exist) -diff --git a/drivers/acpi/acpica/evgpeutil.c b/drivers/acpi/acpica/evgpeutil.c -index 19a0e51..434ad1b 100644 ---- a/drivers/acpi/acpica/evgpeutil.c -+++ b/drivers/acpi/acpica/evgpeutil.c -@@ -323,12 +323,11 @@ acpi_ev_delete_gpe_handlers(struct acpi_gpe_xrupt_info *gpe_xrupt_info, - ACPI_GPE_REGISTER_WIDTH) - + j]; - -- if ((gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) == -- ACPI_GPE_DISPATCH_HANDLER) { -+ if (gpe_event_info->flags & ACPI_GPE_DISPATCH_HANDLER) { - ACPI_FREE(gpe_event_info->dispatch.handler); - gpe_event_info->dispatch.handler = NULL; - gpe_event_info->flags &= -- ~ACPI_GPE_DISPATCH_MASK; -+ ~ACPI_GPE_DISPATCH_HANDLER; - } - } - } -diff --git a/drivers/acpi/acpica/evxface.c b/drivers/acpi/acpica/evxface.c -index 36af222..b097136 100644 ---- a/drivers/acpi/acpica/evxface.c -+++ b/drivers/acpi/acpica/evxface.c -@@ -662,6 +662,8 @@ ACPI_EXPORT_SYMBOL(acpi_remove_notify_handler) - * edge- or level-triggered interrupt. - * Address - Address of the handler - * Context - Value passed to the handler on each GPE -+ * keep_method - Whether the existing method should be -+ * displaced or kept - * - * RETURN: Status - * -@@ -671,7 +673,8 @@ ACPI_EXPORT_SYMBOL(acpi_remove_notify_handler) - acpi_status - acpi_install_gpe_handler(acpi_handle gpe_device, - u32 gpe_number, -- u32 type, acpi_event_handler address, void *context) -+ u32 type, acpi_event_handler address, void *context, -+ bool keep_method) - { - struct acpi_gpe_event_info *gpe_event_info; - struct acpi_handler_info *handler; -@@ -711,8 +714,7 @@ acpi_install_gpe_handler(acpi_handle gpe_device, - - /* Make sure that there isn't a handler there already */ - -- if ((gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) == -- ACPI_GPE_DISPATCH_HANDLER) { -+ if (gpe_event_info->flags & ACPI_GPE_DISPATCH_HANDLER) { - status = AE_ALREADY_EXISTS; - goto free_and_exit; - } -@@ -721,7 +723,6 @@ acpi_install_gpe_handler(acpi_handle gpe_device, - - handler->address = address; - handler->context = context; -- handler->method_node = gpe_event_info->dispatch.method_node; - handler->orig_flags = gpe_event_info->flags & - (ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); - -@@ -732,7 +733,7 @@ acpi_install_gpe_handler(acpi_handle gpe_device, - */ - - if ((handler->orig_flags & ACPI_GPE_DISPATCH_METHOD) -- && gpe_event_info->runtime_count) { -+ && gpe_event_info->runtime_count && !keep_method) { - handler->orig_enabled = 1; - (void)acpi_raw_disable_gpe(gpe_event_info); - } -@@ -741,10 +742,10 @@ acpi_install_gpe_handler(acpi_handle gpe_device, - - gpe_event_info->dispatch.handler = handler; - -- /* Setup up dispatch flags to indicate handler (vs. method) */ -+ if (!keep_method) -+ gpe_event_info->flags &= -+ ~(ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); - -- gpe_event_info->flags &= -- ~(ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); - gpe_event_info->flags |= (u8) (type | ACPI_GPE_DISPATCH_HANDLER); - - acpi_os_release_lock(acpi_gbl_gpe_lock, flags); -@@ -813,8 +814,7 @@ acpi_remove_gpe_handler(acpi_handle gpe_device, - - /* Make sure that a handler is indeed installed */ - -- if ((gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) != -- ACPI_GPE_DISPATCH_HANDLER) { -+ if (!(gpe_event_info->flags & ACPI_GPE_DISPATCH_HANDLER)) { - status = AE_NOT_EXIST; - goto unlock_and_exit; - } -@@ -830,9 +830,8 @@ acpi_remove_gpe_handler(acpi_handle gpe_device, - - handler = gpe_event_info->dispatch.handler; - -- /* Restore Method node (if any), set dispatch flags */ -+ /* Set dispatch flags */ - -- gpe_event_info->dispatch.method_node = handler->method_node; - gpe_event_info->flags &= - ~(ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); - gpe_event_info->flags |= handler->orig_flags; -diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c -index 372ff80..9a39f82 100644 ---- a/drivers/acpi/ec.c -+++ b/drivers/acpi/ec.c -@@ -740,7 +740,7 @@ static int ec_install_handlers(struct acpi_ec *ec) - return 0; - status = acpi_install_gpe_handler(NULL, ec->gpe, - ACPI_GPE_EDGE_TRIGGERED, -- &acpi_ec_gpe_handler, ec); -+ &acpi_ec_gpe_handler, ec, false); - if (ACPI_FAILURE(status)) - return -ENODEV; - -diff --git a/drivers/acpi/pci_bind.c b/drivers/acpi/pci_bind.c -index 2ef0409..8b3cc6a 100644 ---- a/drivers/acpi/pci_bind.c -+++ b/drivers/acpi/pci_bind.c -@@ -28,6 +28,7 @@ - #include <linux/pci.h> - #include <linux/pci-acpi.h> - #include <linux/acpi.h> -+#include <linux/list.h> - #include <linux/pm_runtime.h> - #include <acpi/acpi_bus.h> - #include <acpi/acpi_drivers.h> -@@ -35,6 +36,43 @@ - #define _COMPONENT ACPI_PCI_COMPONENT - ACPI_MODULE_NAME("pci_bind"); - -+static LIST_HEAD(acpi_pci_gpe_devs); -+ -+struct pci_gpe_dev { -+ struct list_head node; -+ struct pci_dev *dev; -+ acpi_handle gpe_device; -+ int gpe_number; -+ struct work_struct work; -+}; -+ -+static void acpi_pci_wake_handler_work(struct work_struct *work) -+{ -+ struct pci_gpe_dev *gpe_dev = container_of(work, struct pci_gpe_dev, -+ work); -+ -+ pci_check_pme_status(gpe_dev->dev); -+ pm_runtime_resume(&gpe_dev->dev->dev); -+ pci_wakeup_event(gpe_dev->dev); -+ if (gpe_dev->dev->subordinate) -+ pci_pme_wakeup_bus(gpe_dev->dev->subordinate); -+} -+ -+static u32 acpi_pci_wake_handler(void *data) -+{ -+ long gpe_number = (long) data; -+ struct pci_gpe_dev *gpe_dev; -+ -+ list_for_each_entry(gpe_dev, &acpi_pci_gpe_devs, node) { -+ if (gpe_number != gpe_dev->gpe_number) -+ continue; -+ -+ schedule_work(&gpe_dev->work); -+ } -+ -+ return ACPI_INTERRUPT_HANDLED; -+} -+ - static int acpi_pci_unbind(struct acpi_device *device) - { - struct pci_dev *dev; -@@ -43,6 +81,30 @@ static int acpi_pci_unbind(struct acpi_device *device) - if (!dev) - goto out; - -+ if (device->wakeup.flags.valid) { -+ struct pci_gpe_dev *gpe_dev; -+ struct pci_gpe_dev *tmp; -+ int gpe_count = 0; -+ int gpe_number = device->wakeup.gpe_number; -+ acpi_handle gpe_device = device->wakeup.gpe_device; -+ -+ list_for_each_entry_safe(gpe_dev, tmp, &acpi_pci_gpe_devs, node) { -+ if (gpe_dev->dev == dev) { -+ flush_work(&gpe_dev->work); -+ list_del(&gpe_dev->node); -+ kfree(gpe_dev); -+ } else if (gpe_dev->gpe_number == gpe_number && -+ gpe_dev->gpe_device == gpe_device) { -+ gpe_count++; -+ } -+ } -+ -+ if (gpe_count == 0) { -+ acpi_remove_gpe_handler(gpe_device, gpe_number, -+ &acpi_pci_wake_handler); -+ } -+ } -+ - device_set_run_wake(&dev->dev, false); - pci_acpi_remove_pm_notifier(device); - -@@ -71,6 +133,30 @@ static int acpi_pci_bind(struct acpi_device *device) - return 0; - - pci_acpi_add_pm_notifier(device, dev); -+ if (device->wakeup.flags.valid) { -+ struct pci_gpe_dev *gpe_dev; -+ acpi_handle gpe_device = device->wakeup.gpe_device; -+ long gpe_number = device->wakeup.gpe_number; -+ -+ gpe_dev = kmalloc(sizeof(struct pci_gpe_dev), GFP_KERNEL); -+ if (gpe_dev) { -+ gpe_dev->dev = dev; -+ gpe_dev->gpe_device = gpe_device; -+ gpe_dev->gpe_number = gpe_number; -+ INIT_WORK(&gpe_dev->work, acpi_pci_wake_handler_work); -+ -+ acpi_install_gpe_handler(gpe_device, gpe_number, -+ ACPI_GPE_LEVEL_TRIGGERED, -+ &acpi_pci_wake_handler, -+ (void *)gpe_number, -+ true); -+ acpi_gpe_can_wake(device->wakeup.gpe_device, -+ device->wakeup.gpe_number); -+ device->wakeup.flags.run_wake = 1; -+ list_add_tail(&gpe_dev->node, &acpi_pci_gpe_devs); -+ } -+ } -+ - if (device->wakeup.flags.run_wake) - device_set_run_wake(&dev->dev, true); - -diff --git a/drivers/acpi/sleep.c b/drivers/acpi/sleep.c -index 721d93b..b0ddef6 100644 ---- a/drivers/acpi/sleep.c -+++ b/drivers/acpi/sleep.c -@@ -643,7 +643,7 @@ int acpi_pm_device_sleep_state(struct device *dev, int *d_min_p) - if (acpi_target_sleep_state != ACPI_STATE_S0 || - status != AE_NOT_FOUND) - d_max = d_min; -- } else if (d_max < d_min) { -+ } else if (ACPI_SUCCESS(status) && d_max < d_min) { - /* Warn the user of the broken DSDT */ - printk(KERN_WARNING "ACPI: Wrong value from %s\n", - acpi_method); -diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c -index 035da9e..62a48b2 100644 ---- a/drivers/char/ipmi/ipmi_si_intf.c -+++ b/drivers/char/ipmi/ipmi_si_intf.c -@@ -1970,7 +1970,7 @@ static int acpi_gpe_irq_setup(struct smi_info *info) - info->irq, - ACPI_GPE_LEVEL_TRIGGERED, - &ipmi_acpi_gpe, -- info); -+ info, false); - if (status != AE_OK) { - dev_warn(info->dev, "%s unable to claim ACPI GPE %d," - " running polled\n", DEVICE_NAME, info->irq); -diff --git a/include/acpi/acpixf.h b/include/acpi/acpixf.h -index 53b7cfd..740eb7e 100644 ---- a/include/acpi/acpixf.h -+++ b/include/acpi/acpixf.h -@@ -258,7 +258,8 @@ acpi_remove_address_space_handler(acpi_handle device, - acpi_status - acpi_install_gpe_handler(acpi_handle gpe_device, - u32 gpe_number, -- u32 type, acpi_event_handler address, void *context); -+ u32 type, acpi_event_handler address, void *context, -+ bool keep_method); - - acpi_status - acpi_remove_gpe_handler(acpi_handle gpe_device, diff --git a/linux-2.6-usb-pci-autosuspend.patch b/linux-2.6-usb-pci-autosuspend.patch deleted file mode 100644 index 610a7654d..000000000 --- a/linux-2.6-usb-pci-autosuspend.patch +++ /dev/null @@ -1,22 +0,0 @@ -commit 15d89120d03116adbbf3226a85fbd2fff0b12576 -Author: Matthew Garrett <mjg@redhat.com> -Date: Fri Sep 17 11:09:12 2010 -0400 - - Enable USB PCI autosuspend by default - -diff --git a/drivers/usb/core/hcd-pci.c b/drivers/usb/core/hcd-pci.c -index c3f9854..3c020e6 100644 ---- a/drivers/usb/core/hcd-pci.c -+++ b/drivers/usb/core/hcd-pci.c -@@ -248,8 +248,10 @@ int usb_hcd_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) - goto err4; - set_hs_companion(dev, hcd); - -- if (pci_dev_run_wake(dev)) -+ if (pci_dev_run_wake(dev)) { - pm_runtime_put_noidle(&dev->dev); -+ pm_runtime_allow(&dev->dev); -+ } - return retval; - - err4: diff --git a/runtime_pm_fixups.patch b/runtime_pm_fixups.patch deleted file mode 100644 index 1be6149d6..000000000 --- a/runtime_pm_fixups.patch +++ /dev/null @@ -1,138 +0,0 @@ -From 141d0d01ab292d4ea3a6d5e96b4048e10e68c1d3 Mon Sep 17 00:00:00 2001 -From: Kyle McMartin <kyle@mcmartin.ca> -Date: Mon, 24 Jan 2011 13:01:57 -0500 -Subject: [PATCH] runtime_pm_fixups - ---- - drivers/acpi/bus.c | 3 ++- - drivers/acpi/pci_bind.c | 6 ++++++ - drivers/acpi/power.c | 5 ++++- - drivers/acpi/sleep.c | 2 +- - drivers/acpi/wakeup.c | 2 +- - drivers/pci/pci-acpi.c | 2 +- - include/acpi/acpi_bus.h | 2 +- - 7 files changed, 16 insertions(+), 6 deletions(-) - -diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c -index 7ced61f..e4e0114 100644 ---- a/drivers/acpi/bus.c -+++ b/drivers/acpi/bus.c -@@ -256,7 +256,8 @@ static int __acpi_bus_set_power(struct acpi_device *device, int state) - * a lower-powered state. - */ - if (state < device->power.state) { -- if (device->power.flags.power_resources) { -+ if (device->power.flags.power_resources && -+ !device->wakeup.run_wake_count) { - result = acpi_power_transition(device, state); - if (result) - goto end; -diff --git a/drivers/acpi/pci_bind.c b/drivers/acpi/pci_bind.c -index 2ef0409..4b0bb68 100644 ---- a/drivers/acpi/pci_bind.c -+++ b/drivers/acpi/pci_bind.c -@@ -32,6 +32,8 @@ - #include <acpi/acpi_bus.h> - #include <acpi/acpi_drivers.h> - -+#include "internal.h" -+ - #define _COMPONENT ACPI_PCI_COMPONENT - ACPI_MODULE_NAME("pci_bind"); - -@@ -65,6 +67,7 @@ static int acpi_pci_bind(struct acpi_device *device) - acpi_handle handle; - struct pci_bus *bus; - struct pci_dev *dev; -+ int state; - - dev = acpi_get_pci_dev(device->handle); - if (!dev) -@@ -87,6 +90,9 @@ static int acpi_pci_bind(struct acpi_device *device) - device->ops.unbind = acpi_pci_unbind; - } - -+ acpi_power_get_inferred_state(device, &state); -+ acpi_power_transition(device, state); -+ - /* - * Evaluate and parse _PRT, if exists. This code allows parsing of - * _PRT objects within the scope of non-bridge devices. Note that -diff --git a/drivers/acpi/power.c b/drivers/acpi/power.c -index 9ac2a9f..cd6a8df 100644 ---- a/drivers/acpi/power.c -+++ b/drivers/acpi/power.c -@@ -412,7 +412,7 @@ int acpi_enable_wakeup_device_power(struct acpi_device *dev, int sleep_state) - * State Wake) for the device, if present - * 2. Shutdown down the power resources - */ --int acpi_disable_wakeup_device_power(struct acpi_device *dev) -+int acpi_disable_wakeup_device_power(struct acpi_device *dev, int sleep_state) - { - int i, err = 0; - -@@ -435,6 +435,9 @@ int acpi_disable_wakeup_device_power(struct acpi_device *dev) - if (err) - goto out; - -+ if (sleep_state == ACPI_STATE_S0) -+ goto out; -+ - /* Close power resource */ - for (i = 0; i < dev->wakeup.resources.count; i++) { - int ret = acpi_power_off(dev->wakeup.resources.handles[i]); -diff --git a/drivers/acpi/sleep.c b/drivers/acpi/sleep.c -index d6a8cd1..5d68dc0 100644 ---- a/drivers/acpi/sleep.c -+++ b/drivers/acpi/sleep.c -@@ -697,7 +697,7 @@ int acpi_pm_device_sleep_wake(struct device *dev, bool enable) - - error = enable ? - acpi_enable_wakeup_device_power(adev, acpi_target_sleep_state) : -- acpi_disable_wakeup_device_power(adev); -+ acpi_disable_wakeup_device_power(adev, acpi_target_sleep_state); - if (!error) - dev_info(dev, "wake-up capability %s by ACPI\n", - enable ? "enabled" : "disabled"); -diff --git a/drivers/acpi/wakeup.c b/drivers/acpi/wakeup.c -index ed65014..a0cabc3 100644 ---- a/drivers/acpi/wakeup.c -+++ b/drivers/acpi/wakeup.c -@@ -73,7 +73,7 @@ void acpi_disable_wakeup_devices(u8 sleep_state) - ACPI_GPE_DISABLE); - - if (device_may_wakeup(&dev->dev)) -- acpi_disable_wakeup_device_power(dev); -+ acpi_disable_wakeup_device_power(dev, sleep_state); - } - } - -diff --git a/drivers/pci/pci-acpi.c b/drivers/pci/pci-acpi.c -index 6fe0772..819fa7a 100644 ---- a/drivers/pci/pci-acpi.c -+++ b/drivers/pci/pci-acpi.c -@@ -302,7 +302,7 @@ static int acpi_dev_run_wake(struct device *phys_dev, bool enable) - if (!--dev->wakeup.run_wake_count) { - acpi_disable_gpe(dev->wakeup.gpe_device, - dev->wakeup.gpe_number); -- acpi_disable_wakeup_device_power(dev); -+ acpi_disable_wakeup_device_power(dev, ACPI_STATE_S0); - } - } else { - error = -EALREADY; -diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h -index 78ca429..92d6e86 100644 ---- a/include/acpi/acpi_bus.h -+++ b/include/acpi/acpi_bus.h -@@ -379,7 +379,7 @@ struct acpi_pci_root *acpi_pci_find_root(acpi_handle handle); - #define DEVICE_ACPI_HANDLE(dev) ((acpi_handle)((dev)->archdata.acpi_handle)) - - int acpi_enable_wakeup_device_power(struct acpi_device *dev, int state); --int acpi_disable_wakeup_device_power(struct acpi_device *dev); -+int acpi_disable_wakeup_device_power(struct acpi_device *dev, int state); - - #ifdef CONFIG_PM_OPS - int acpi_pm_device_sleep_state(struct device *, int *); --- -1.7.3.5 - |