aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pci
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/pci')
-rw-r--r--drivers/pci/pci-acpi.c1
-rw-r--r--drivers/pci/pci.c20
-rw-r--r--drivers/pci/pci.h1
-rw-r--r--drivers/pci/pcie/pme/pcie_pme.c5
4 files changed, 25 insertions, 2 deletions
diff --git a/drivers/pci/pci-acpi.c b/drivers/pci/pci-acpi.c
index 2e7a3bf1382..1ab98bbe58d 100644
--- a/drivers/pci/pci-acpi.c
+++ b/drivers/pci/pci-acpi.c
@@ -48,6 +48,7 @@ static void pci_acpi_wake_dev(acpi_handle handle, u32 event, void *context)
48 if (event == ACPI_NOTIFY_DEVICE_WAKE && pci_dev) { 48 if (event == ACPI_NOTIFY_DEVICE_WAKE && pci_dev) {
49 pci_check_pme_status(pci_dev); 49 pci_check_pme_status(pci_dev);
50 pm_runtime_resume(&pci_dev->dev); 50 pm_runtime_resume(&pci_dev->dev);
51 pci_wakeup_event(pci_dev);
51 if (pci_dev->subordinate) 52 if (pci_dev->subordinate)
52 pci_pme_wakeup_bus(pci_dev->subordinate); 53 pci_pme_wakeup_bus(pci_dev->subordinate);
53 } 54 }
diff --git a/drivers/pci/pci.c b/drivers/pci/pci.c
index 740fb4ea966..130ed1daf0f 100644
--- a/drivers/pci/pci.c
+++ b/drivers/pci/pci.c
@@ -1275,6 +1275,22 @@ bool pci_check_pme_status(struct pci_dev *dev)
1275 return ret; 1275 return ret;
1276} 1276}
1277 1277
1278/*
1279 * Time to wait before the system can be put into a sleep state after reporting
1280 * a wakeup event signaled by a PCI device.
1281 */
1282#define PCI_WAKEUP_COOLDOWN 100
1283
1284/**
1285 * pci_wakeup_event - Report a wakeup event related to a given PCI device.
1286 * @dev: Device to report the wakeup event for.
1287 */
1288void pci_wakeup_event(struct pci_dev *dev)
1289{
1290 if (device_may_wakeup(&dev->dev))
1291 pm_wakeup_event(&dev->dev, PCI_WAKEUP_COOLDOWN);
1292}
1293
1278/** 1294/**
1279 * pci_pme_wakeup - Wake up a PCI device if its PME Status bit is set. 1295 * pci_pme_wakeup - Wake up a PCI device if its PME Status bit is set.
1280 * @dev: Device to handle. 1296 * @dev: Device to handle.
@@ -1285,8 +1301,10 @@ bool pci_check_pme_status(struct pci_dev *dev)
1285 */ 1301 */
1286static int pci_pme_wakeup(struct pci_dev *dev, void *ign) 1302static int pci_pme_wakeup(struct pci_dev *dev, void *ign)
1287{ 1303{
1288 if (pci_check_pme_status(dev)) 1304 if (pci_check_pme_status(dev)) {
1289 pm_request_resume(&dev->dev); 1305 pm_request_resume(&dev->dev);
1306 pci_wakeup_event(dev);
1307 }
1290 return 0; 1308 return 0;
1291} 1309}
1292 1310
diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h
index f8077b3c8c8..c8b7fd056cc 100644
--- a/drivers/pci/pci.h
+++ b/drivers/pci/pci.h
@@ -56,6 +56,7 @@ extern void pci_update_current_state(struct pci_dev *dev, pci_power_t state);
56extern void pci_disable_enabled_device(struct pci_dev *dev); 56extern void pci_disable_enabled_device(struct pci_dev *dev);
57extern bool pci_check_pme_status(struct pci_dev *dev); 57extern bool pci_check_pme_status(struct pci_dev *dev);
58extern int pci_finish_runtime_suspend(struct pci_dev *dev); 58extern int pci_finish_runtime_suspend(struct pci_dev *dev);
59extern void pci_wakeup_event(struct pci_dev *dev);
59extern int __pci_pme_wakeup(struct pci_dev *dev, void *ign); 60extern int __pci_pme_wakeup(struct pci_dev *dev, void *ign);
60extern void pci_pme_wakeup_bus(struct pci_bus *bus); 61extern void pci_pme_wakeup_bus(struct pci_bus *bus);
61extern void pci_pm_init(struct pci_dev *dev); 62extern void pci_pm_init(struct pci_dev *dev);
diff --git a/drivers/pci/pcie/pme/pcie_pme.c b/drivers/pci/pcie/pme/pcie_pme.c
index d672a0a6381..bbdea18693d 100644
--- a/drivers/pci/pcie/pme/pcie_pme.c
+++ b/drivers/pci/pcie/pme/pcie_pme.c
@@ -154,6 +154,7 @@ static bool pcie_pme_walk_bus(struct pci_bus *bus)
154 /* Skip PCIe devices in case we started from a root port. */ 154 /* Skip PCIe devices in case we started from a root port. */
155 if (!pci_is_pcie(dev) && pci_check_pme_status(dev)) { 155 if (!pci_is_pcie(dev) && pci_check_pme_status(dev)) {
156 pm_request_resume(&dev->dev); 156 pm_request_resume(&dev->dev);
157 pci_wakeup_event(dev);
157 ret = true; 158 ret = true;
158 } 159 }
159 160
@@ -254,8 +255,10 @@ static void pcie_pme_handle_request(struct pci_dev *port, u16 req_id)
254 if (found) { 255 if (found) {
255 /* The device is there, but we have to check its PME status. */ 256 /* The device is there, but we have to check its PME status. */
256 found = pci_check_pme_status(dev); 257 found = pci_check_pme_status(dev);
257 if (found) 258 if (found) {
258 pm_request_resume(&dev->dev); 259 pm_request_resume(&dev->dev);
260 pci_wakeup_event(dev);
261 }
259 pci_dev_put(dev); 262 pci_dev_put(dev);
260 } else if (devfn) { 263 } else if (devfn) {
261 /* 264 /*