summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/pci/rebar.c18
-rw-r--r--drivers/pci/setup-bus.c20
2 files changed, 19 insertions, 19 deletions
diff --git a/drivers/pci/rebar.c b/drivers/pci/rebar.c
index ecdebdeb2dff..39f8cf3b70d5 100644
--- a/drivers/pci/rebar.c
+++ b/drivers/pci/rebar.c
@@ -295,7 +295,6 @@ int pci_resize_resource(struct pci_dev *dev, int resno, int size,
int exclude_bars)
{
struct pci_host_bridge *host;
- int old, ret;
/* Check if we must preserve the firmware's resource assignment */
host = pci_find_host_bridge(dev->bus);
@@ -308,21 +307,6 @@ int pci_resize_resource(struct pci_dev *dev, int resno, int size,
if (!pci_rebar_size_supported(dev, resno, size))
return -EINVAL;
- old = pci_rebar_get_current_size(dev, resno);
- if (old < 0)
- return old;
-
- ret = pci_rebar_set_size(dev, resno, size);
- if (ret)
- return ret;
-
- ret = pci_do_resource_release_and_resize(dev, resno, size, exclude_bars);
- if (ret)
- goto error_resize;
- return 0;
-
-error_resize:
- pci_rebar_set_size(dev, resno, old);
- return ret;
+ return pci_do_resource_release_and_resize(dev, resno, size, exclude_bars);
}
EXPORT_SYMBOL(pci_resize_resource);
diff --git a/drivers/pci/setup-bus.c b/drivers/pci/setup-bus.c
index 9c374feafc77..a61d38777cdc 100644
--- a/drivers/pci/setup-bus.c
+++ b/drivers/pci/setup-bus.c
@@ -2504,12 +2504,20 @@ int pci_do_resource_release_and_resize(struct pci_dev *pdev, int resno, int size
struct resource *b_win, *r;
LIST_HEAD(saved);
unsigned int i;
- int ret = 0;
+ int old, ret;
b_win = pbus_select_window(bus, res);
if (!b_win)
return -EINVAL;
+ old = pci_rebar_get_current_size(pdev, resno);
+ if (old < 0)
+ return old;
+
+ ret = pci_rebar_set_size(pdev, resno, size);
+ if (ret)
+ return ret;
+
pci_dev_for_each_resource(pdev, r, i) {
if (i >= PCI_BRIDGE_RESOURCES)
break;
@@ -2542,7 +2550,15 @@ out:
return ret;
restore:
- /* Revert to the old configuration */
+ /*
+ * Revert to the old configuration.
+ *
+ * BAR Size must be restored first because it affects the read-only
+ * bits in BAR (the old address might not be restorable otherwise
+ * due to low address bits).
+ */
+ pci_rebar_set_size(pdev, resno, old);
+
list_for_each_entry(dev_res, &saved, list) {
struct resource *res = dev_res->res;
struct pci_dev *dev = dev_res->dev;