diff options
author | Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com> | 2008-12-17 12:07:38 +0900 |
---|---|---|
committer | Jesse Barnes <jbarnes@virtuousgeek.org> | 2009-01-07 11:13:10 -0800 |
commit | c9ffa5a586a97da4d552f89b8f39eea79a63a612 (patch) | |
tree | 47e4a6de7df1c5d41bff61f8bfc81eb464b8d2c6 /drivers/pci/hotplug/pciehp.h | |
parent | 873392ca514f87eae39f53b6944caf85b1a047cb (diff) | |
download | op-kernel-dev-c9ffa5a586a97da4d552f89b8f39eea79a63a612.zip op-kernel-dev-c9ffa5a586a97da4d552f89b8f39eea79a63a612.tar.gz |
PCI: pciehp: add ACPI based slot detection
There is a problem that some non hot-pluggable PCIe slots are detected
as hot-pluggable by pciehp on some platforms. The immediate cause of
this problem is that hot-plug capable bit in the Slot Capabilities
register is set even for non hot-pluggable slots on those platforms.
It seems a BIOS/hardware problem, but we need workaround about that.
Some of those platforms define hot-pluggable PCIe slots on ACPI
namespace properly, while hot-plug capable bit in the Slot
Capabilities register is set improperly. So using ACPI namespace
information in pciehp to detect PCIe hot-pluggable slots would be a
workaround.
This patch adds 'pciehp_detect_mode' module option. When 'acpi' is
specified, pciehp uses ACPI namespace information to detect PCIe
hot-pluggable slots.
Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
Signed-off-by: Jesse Barnes <jbarnes@virtuousgeek.org>
Diffstat (limited to 'drivers/pci/hotplug/pciehp.h')
-rw-r--r-- | drivers/pci/hotplug/pciehp.h | 15 |
1 files changed, 14 insertions, 1 deletions
diff --git a/drivers/pci/hotplug/pciehp.h b/drivers/pci/hotplug/pciehp.h index b2801a7..27fd18f 100644 --- a/drivers/pci/hotplug/pciehp.h +++ b/drivers/pci/hotplug/pciehp.h @@ -220,11 +220,23 @@ struct hpc_ops { #include <acpi/actypes.h> #include <linux/pci-acpi.h> +extern void __init pciehp_acpi_slot_detection_init(void); +extern int pciehp_acpi_slot_detection_check(struct pci_dev *dev); + +static inline void pciehp_firmware_init(void) +{ + pciehp_acpi_slot_detection_init(); +} + static inline int pciehp_get_hp_hw_control_from_firmware(struct pci_dev *dev) { + int retval; u32 flags = (OSC_PCI_EXPRESS_NATIVE_HP_CONTROL | OSC_PCI_EXPRESS_CAP_STRUCTURE_CONTROL); - return acpi_get_hp_hw_control_from_firmware(dev, flags); + retval = acpi_get_hp_hw_control_from_firmware(dev, flags); + if (retval) + return retval; + return pciehp_acpi_slot_detection_check(dev); } static inline int pciehp_get_hp_params_from_firmware(struct pci_dev *dev, @@ -235,6 +247,7 @@ static inline int pciehp_get_hp_params_from_firmware(struct pci_dev *dev, return 0; } #else +#define pciehp_firmware_init() do {} while (0) #define pciehp_get_hp_hw_control_from_firmware(dev) 0 #define pciehp_get_hp_params_from_firmware(dev, hpp) (-ENODEV) #endif /* CONFIG_ACPI */ |