Commit 991de2e5 authored by Jiang Liu's avatar Jiang Liu Committed by Bjorn Helgaas

PCI, x86: Implement pcibios_alloc_irq() and pcibios_free_irq()

To support IOAPIC hotplug, we need to allocate PCI IRQ resources on demand
and free them when not used anymore.

Implement pcibios_alloc_irq() and pcibios_free_irq() to dynamically
allocate and free PCI IRQs.

Remove mp_should_keep_irq(), which is no longer used.

[bhelgaas: changelog]
Signed-off-by: default avatarJiang Liu <jiang.liu@linux.intel.com>
Signed-off-by: default avatarBjorn Helgaas <bhelgaas@google.com>
Acked-by: default avatarThomas Gleixner <tglx@linutronix.de>
parent 890e4847
...@@ -93,8 +93,6 @@ extern raw_spinlock_t pci_config_lock; ...@@ -93,8 +93,6 @@ extern raw_spinlock_t pci_config_lock;
extern int (*pcibios_enable_irq)(struct pci_dev *dev); extern int (*pcibios_enable_irq)(struct pci_dev *dev);
extern void (*pcibios_disable_irq)(struct pci_dev *dev); extern void (*pcibios_disable_irq)(struct pci_dev *dev);
extern bool mp_should_keep_irq(struct device *dev);
struct pci_raw_ops { struct pci_raw_ops {
int (*read)(unsigned int domain, unsigned int bus, unsigned int devfn, int (*read)(unsigned int domain, unsigned int bus, unsigned int devfn,
int reg, int len, u32 *val); int reg, int len, u32 *val);
......
...@@ -673,24 +673,22 @@ int pcibios_add_device(struct pci_dev *dev) ...@@ -673,24 +673,22 @@ int pcibios_add_device(struct pci_dev *dev)
return 0; return 0;
} }
int pcibios_enable_device(struct pci_dev *dev, int mask) int pcibios_alloc_irq(struct pci_dev *dev)
{ {
int err; return pcibios_enable_irq(dev);
if ((err = pci_enable_resources(dev, mask)) < 0)
return err;
if (!pci_dev_msi_enabled(dev))
return pcibios_enable_irq(dev);
return 0;
} }
void pcibios_disable_device (struct pci_dev *dev) void pcibios_free_irq(struct pci_dev *dev)
{ {
if (!pci_dev_msi_enabled(dev) && pcibios_disable_irq) if (pcibios_disable_irq)
pcibios_disable_irq(dev); pcibios_disable_irq(dev);
} }
int pcibios_enable_device(struct pci_dev *dev, int mask)
{
return pci_enable_resources(dev, mask);
}
int pci_ext_cfg_avail(void) int pci_ext_cfg_avail(void)
{ {
if (raw_pci_ext_ops) if (raw_pci_ext_ops)
......
...@@ -234,10 +234,13 @@ static int intel_mid_pci_irq_enable(struct pci_dev *dev) ...@@ -234,10 +234,13 @@ static int intel_mid_pci_irq_enable(struct pci_dev *dev)
static void intel_mid_pci_irq_disable(struct pci_dev *dev) static void intel_mid_pci_irq_disable(struct pci_dev *dev)
{ {
if (!mp_should_keep_irq(&dev->dev) && dev->irq_managed && if (dev->irq_managed && dev->irq > 0) {
dev->irq > 0) {
mp_unmap_irq(dev->irq); mp_unmap_irq(dev->irq);
dev->irq_managed = 0; dev->irq_managed = 0;
/*
* Don't reset dev->irq here, otherwise
* intel_mid_pci_irq_enable() will fail on next call.
*/
} }
} }
......
...@@ -1257,22 +1257,9 @@ static int pirq_enable_irq(struct pci_dev *dev) ...@@ -1257,22 +1257,9 @@ static int pirq_enable_irq(struct pci_dev *dev)
return 0; return 0;
} }
bool mp_should_keep_irq(struct device *dev)
{
if (dev->power.is_prepared)
return true;
#ifdef CONFIG_PM
if (dev->power.runtime_status == RPM_SUSPENDING)
return true;
#endif
return false;
}
static void pirq_disable_irq(struct pci_dev *dev) static void pirq_disable_irq(struct pci_dev *dev)
{ {
if (io_apic_assign_pci_irqs && !mp_should_keep_irq(&dev->dev) && if (io_apic_assign_pci_irqs && dev->irq_managed && dev->irq) {
dev->irq_managed && dev->irq) {
mp_unmap_irq(dev->irq); mp_unmap_irq(dev->irq);
dev->irq = 0; dev->irq = 0;
dev->irq_managed = 0; dev->irq_managed = 0;
......
...@@ -484,14 +484,6 @@ void acpi_pci_irq_disable(struct pci_dev *dev) ...@@ -484,14 +484,6 @@ void acpi_pci_irq_disable(struct pci_dev *dev)
if (!pin || !dev->irq_managed || dev->irq <= 0) if (!pin || !dev->irq_managed || dev->irq <= 0)
return; return;
/* Keep IOAPIC pin configuration when suspending */
if (dev->dev.power.is_prepared)
return;
#ifdef CONFIG_PM
if (dev->dev.power.runtime_status == RPM_SUSPENDING)
return;
#endif
entry = acpi_pci_irq_lookup(dev, pin); entry = acpi_pci_irq_lookup(dev, pin);
if (!entry) if (!entry)
return; return;
...@@ -512,5 +504,6 @@ void acpi_pci_irq_disable(struct pci_dev *dev) ...@@ -512,5 +504,6 @@ void acpi_pci_irq_disable(struct pci_dev *dev)
if (gsi >= 0) { if (gsi >= 0) {
acpi_unregister_gsi(gsi); acpi_unregister_gsi(gsi);
dev->irq_managed = 0; dev->irq_managed = 0;
dev->irq = 0;
} }
} }
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment