Save and restore the PCI-X Command register through the per-device saved
capability store instead of a private pci_cap_saved_state buffer.

Reserve the register by its configuration space offset during device
setup, in pci_reserve_pcix_state(), so that the save and restore paths
no longer have to locate a buffer.

Make pci_save_pcix_state() void, so pci_save_state() no longer fails with
-ENOMEM when the PCI-X save buffer is missing. A failure to allocate the
store is reported once during device setup instead.

No other functional change intended.

Signed-off-by: David Matlack <[email protected]>
---
 drivers/pci/pci.c | 47 ++++++++++++++++++++---------------------------
 1 file changed, 20 insertions(+), 27 deletions(-)

diff --git a/drivers/pci/pci.c b/drivers/pci/pci.c
index fde1dcd99e94..6cf4a64cb7e6 100644
--- a/drivers/pci/pci.c
+++ b/drivers/pci/pci.c
@@ -1900,40 +1900,40 @@ static void pci_restore_pcie_state(struct pci_dev *dev)
        }
 }
 
-static int pci_save_pcix_state(struct pci_dev *dev)
+static void pci_save_pcix_state(struct pci_dev *dev)
 {
        int pos;
-       struct pci_cap_saved_state *save_state;
 
        pos = pci_find_capability(dev, PCI_CAP_ID_PCIX);
        if (!pos)
-               return 0;
+               return;
 
-       save_state = pci_find_saved_cap(dev, PCI_CAP_ID_PCIX);
-       if (!save_state) {
-               pci_err(dev, "buffer not found in %s\n", __func__);
-               return -ENOMEM;
-       }
+       pci_save_cap_word(dev, pos + PCI_X_CMD);
+}
 
-       pci_read_config_word(dev, pos + PCI_X_CMD,
-                            (u16 *)save_state->cap.data);
+static void pci_reserve_pcix_state(struct pci_dev *dev)
+{
+       int pos, rc;
 
-       return 0;
+       pos = pci_find_capability(dev, PCI_CAP_ID_PCIX);
+       if (!pos)
+               return;
+
+       rc = pci_reserve_saved_cap(dev, pos + PCI_X_CMD, sizeof(u16));
+       if (rc)
+               pci_err(dev, "unable to reserve PCI-X save state (%pe)\n",
+                       ERR_PTR(rc));
 }
 
 static void pci_restore_pcix_state(struct pci_dev *dev)
 {
-       int i = 0, pos;
-       struct pci_cap_saved_state *save_state;
-       u16 *cap;
+       int pos;
 
-       save_state = pci_find_saved_cap(dev, PCI_CAP_ID_PCIX);
        pos = pci_find_capability(dev, PCI_CAP_ID_PCIX);
-       if (!save_state || !pos)
+       if (!pos)
                return;
-       cap = (u16 *)&save_state->cap.data[0];
 
-       pci_write_config_word(dev, pos + PCI_X_CMD, cap[i++]);
+       pci_restore_cap_word(dev, pos + PCI_X_CMD);
 }
 
 /**
@@ -1953,11 +1953,7 @@ int pci_save_state(struct pci_dev *dev)
        dev->state_saved = true;
 
        pci_save_pcie_state(dev);
-
-       i = pci_save_pcix_state(dev);
-       if (i != 0)
-               return i;
-
+       pci_save_pcix_state(dev);
        pci_save_dpc_state(dev);
        pci_save_aer_state(dev);
        pci_save_ptm_state(dev);
@@ -3749,10 +3745,7 @@ void pci_allocate_cap_save_buffers(struct pci_dev *dev)
        int error;
 
        pci_reserve_pcie_state(dev);
-
-       error = pci_add_cap_save_buffer(dev, PCI_CAP_ID_PCIX, sizeof(u16));
-       if (error)
-               pci_err(dev, "unable to preallocate PCI-X save buffer\n");
+       pci_reserve_pcix_state(dev);
 
        error = pci_add_ext_cap_save_buffer(dev, PCI_EXT_CAP_ID_LTR,
                                            2 * sizeof(u16));
-- 
2.56.0.455.g6c5a503b38-goog


Reply via email to