aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorYinghai Lu <yinghai@kernel.org>2012-09-17 22:22:32 -0700
committerYinghai Lu <yinghai@kernel.org>2012-09-17 22:22:32 -0700
commit537d28686b2bbe82ba1d12b75570510ae6511f2e (patch)
tree24adf8d6583f6e8178b251e21c6459ab22d7131a
parent604a4e62824aedcf29b6209e93c8f90e72738783 (diff)
downloadlinux-yinghai-537d28686b2bbe82ba1d12b75570510ae6511f2e.tar.gz
PCI: Disable mem in the ioapic removing path
For physical hot plug should be ok, but for remove/rescan path will need us to disable that. otherwise rescan mmio resource for pci ioapic device will not be sized and allocated, aka skiped. For ioapic_probe:pci_enable_device will not enable the device correctly, and will bail out early. So we can just disable mmio for all removing case. that will hurt real hotplug path. Signed-off-by: <yinghai@kernel.org> Cc: Jesse Barnes <jbarnes@virtuousgeek.org>
-rw-r--r--drivers/pci/ioapic.c13
1 files changed, 13 insertions, 0 deletions
diff --git a/drivers/pci/ioapic.c b/drivers/pci/ioapic.c
index 4183a5c6cb6bc8..0b2c210f0050a9 100644
--- a/drivers/pci/ioapic.c
+++ b/drivers/pci/ioapic.c
@@ -88,6 +88,17 @@ exit_free:
return -ENODEV;
}
+static void pci_disable_device_mem(struct pci_dev *dev)
+{
+ u16 pci_command;
+
+ pci_read_config_word(dev, PCI_COMMAND, &pci_command);
+ if (pci_command & PCI_COMMAND_MEMORY) {
+ pci_command &= ~PCI_COMMAND_MEMORY;
+ pci_write_config_word(dev, PCI_COMMAND, pci_command);
+ }
+}
+
static void __devexit ioapic_remove(struct pci_dev *dev)
{
struct ioapic *ioapic = pci_get_drvdata(dev);
@@ -95,6 +106,8 @@ static void __devexit ioapic_remove(struct pci_dev *dev)
acpi_unregister_ioapic(ioapic->handle, ioapic->gsi_base);
pci_release_region(dev, 0);
pci_disable_device(dev);
+ /* need to disable it, otherwise remove/rescan will not work */
+ pci_disable_device_mem(dev);
kfree(ioapic);
}