]> asedeno.scripts.mit.edu Git - linux.git/commitdiff
PCI: Add support for Immediate Readiness
authorFelipe Balbi <felipe.balbi@linux.intel.com>
Fri, 7 Sep 2018 06:16:51 +0000 (09:16 +0300)
committerBjorn Helgaas <bhelgaas@google.com>
Fri, 28 Sep 2018 17:47:34 +0000 (12:47 -0500)
PCIe r4.0, sec 7.5.1.1.4 defines a new bit in the Status Register:

  Immediate Readiness – This optional bit, when Set, indicates the Function
  is guaranteed to be ready to successfully complete valid configuration
  accesses at any time following any reset that the host is capable of
  issuing Configuration Requests to this Function.

  When this bit is Set, for accesses to this Function, software is exempt
  from all requirements to delay configuration accesses following any type
  of reset, including but not limited to the timing requirements defined in
  Section 6.6.

This means that all delays after a Conventional or Function Reset can be
skipped.

This patch reads such bit and caches its value in a flag inside struct
pci_dev to be checked later if we should delay or can skip delays after a
reset.  While at that, also move the explicit msleep(100) call from
pcie_flr() and pci_af_flr() to pci_dev_wait().

Signed-off-by: Felipe Balbi <felipe.balbi@linux.intel.com>
[bhelgaas: rename PCI_STATUS_IMMEDIATE to PCI_STATUS_IMM_READY]
Signed-off-by: Bjorn Helgaas <bhelgaas@google.com>
drivers/pci/pci.c
include/linux/pci.h
include/uapi/linux/pci_regs.h

index 1835f3a7aa8d2f5a502a0629bfb0c0cc96420dd4..ee7c2f4eef9be37863bde3bbf44e0b54146e71e3 100644 (file)
@@ -999,7 +999,7 @@ static void __pci_start_power_transition(struct pci_dev *dev, pci_power_t state)
                 * because have already delayed for the bridge.
                 */
                if (dev->runtime_d3cold) {
-                       if (dev->d3cold_delay)
+                       if (dev->d3cold_delay && !dev->imm_ready)
                                msleep(dev->d3cold_delay);
                        /*
                         * When powering on a bridge from D3cold, the
@@ -2644,6 +2644,7 @@ EXPORT_SYMBOL_GPL(pci_d3cold_disable);
 void pci_pm_init(struct pci_dev *dev)
 {
        int pm;
+       u16 status;
        u16 pmc;
 
        pm_runtime_forbid(&dev->dev);
@@ -2706,6 +2707,10 @@ void pci_pm_init(struct pci_dev *dev)
                /* Disable the PME# generation functionality */
                pci_pme_active(dev, false);
        }
+
+       pci_read_config_word(dev, PCI_STATUS, &status);
+       if (status & PCI_STATUS_IMM_READY)
+               dev->imm_ready = 1;
 }
 
 static unsigned long pci_ea_flags(struct pci_dev *dev, u8 prop)
@@ -4376,6 +4381,9 @@ int pcie_flr(struct pci_dev *dev)
 
        pcie_capability_set_word(dev, PCI_EXP_DEVCTL, PCI_EXP_DEVCTL_BCR_FLR);
 
+       if (dev->imm_ready)
+               return 0;
+
        /*
         * Per PCIe r4.0, sec 6.6.2, a device must complete an FLR within
         * 100ms, but may silently discard requests while the FLR is in
@@ -4417,6 +4425,9 @@ static int pci_af_flr(struct pci_dev *dev, int probe)
 
        pci_write_config_byte(dev, pos + PCI_AF_CTRL, PCI_AF_CTRL_FLR);
 
+       if (dev->imm_ready)
+               return 0;
+
        /*
         * Per Advanced Capabilities for Conventional PCI ECN, 13 April 2006,
         * updated 27 July 2006; a device must complete an FLR within
index 6925828f9f250fae21e19ef8338d46694621e2a2..60da5d7d4310f31f1790812c38a362c3812d6cb9 100644 (file)
@@ -325,6 +325,7 @@ struct pci_dev {
        pci_power_t     current_state;  /* Current operating state. In ACPI,
                                           this is D0-D3, D0 being fully
                                           functional, and D3 being off. */
+       unsigned int    imm_ready:1;    /* Supports Immediate Readiness */
        u8              pm_cap;         /* PM capability offset */
        unsigned int    pme_support:5;  /* Bitmask of states from which PME#
                                           can be generated */
index ee556ccc93f48c2e715875d9b94d69e6ce638e72..e1e9888c85e6810aad2e54ab25cbbaf49b72ba57 100644 (file)
@@ -52,6 +52,7 @@
 #define  PCI_COMMAND_INTX_DISABLE 0x400 /* INTx Emulation Disable */
 
 #define PCI_STATUS             0x06    /* 16 bits */
+#define  PCI_STATUS_IMM_READY  0x01    /* Immediate Readiness */
 #define  PCI_STATUS_INTERRUPT  0x08    /* Interrupt status */
 #define  PCI_STATUS_CAP_LIST   0x10    /* Support Capability List */
 #define  PCI_STATUS_66MHZ      0x20    /* Support 66 MHz PCI 2.1 bus */