aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorrajesh.shah@intel.com <rajesh.shah@intel.com>2005-10-31 19:20:11 -0500
committerGreg Kroah-Hartman <gregkh@suse.de>2005-11-10 19:09:15 -0500
commit427bf532b5ad6db5addc2bce675d13f874397c0c (patch)
tree3a099b05ab3b1252d6e441855d9b1da02e0daf8c
parent1a9ed1bfe2fb17cc30227a12a3c1212128bb78b6 (diff)
[PATCH] pciehp: request control of each hotplug controller individually
This patch tweaks the way pciehp requests control of the hotplug hardware from BIOS. It now tries to invoke the ACPI _OSC method for a specific hotplug controller only, rather than walking the entire acpi namespace invoking all possible _OSC methods under all host bridges. This allows us to gain control of each hotplug controller individually, even if BIOS fails to give us control of some other hotplug controller in the system. Signed-off-by: Rajesh Shah <rajesh.shah@intel.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
-rw-r--r--drivers/pci/hotplug/pciehprm_acpi.c9
-rw-r--r--drivers/pci/pci-acpi.c11
-rw-r--r--include/linux/pci-acpi.h5
3 files changed, 10 insertions, 15 deletions
diff --git a/drivers/pci/hotplug/pciehprm_acpi.c b/drivers/pci/hotplug/pciehprm_acpi.c
index 5d184582331e..5acdae3d52b1 100644
--- a/drivers/pci/hotplug/pciehprm_acpi.c
+++ b/drivers/pci/hotplug/pciehprm_acpi.c
@@ -143,12 +143,13 @@ static acpi_status acpi_run_oshp(acpi_handle handle)
143int get_hp_hw_control_from_firmware(struct pci_dev *dev) 143int get_hp_hw_control_from_firmware(struct pci_dev *dev)
144{ 144{
145 acpi_status status; 145 acpi_status status;
146 acpi_handle handle = DEVICE_ACPI_HANDLE(&(dev->dev));
146 /* 147 /*
147 * Per PCI firmware specification, we should run the ACPI _OSC 148 * Per PCI firmware specification, we should run the ACPI _OSC
148 * method to get control of hotplug hardware before using it 149 * method to get control of hotplug hardware before using it
149 */ 150 */
150 /* Fixme: run _OSC for a specific host bridge, not all of them */ 151 status = pci_osc_control_set(handle,
151 status = pci_osc_control_set(OSC_PCI_EXPRESS_NATIVE_HP_CONTROL); 152 OSC_PCI_EXPRESS_NATIVE_HP_CONTROL);
152 153
153 /* Fixme: fail native hotplug if _OSC does not exist for root ports */ 154 /* Fixme: fail native hotplug if _OSC does not exist for root ports */
154 if (status == AE_NOT_FOUND) { 155 if (status == AE_NOT_FOUND) {
@@ -156,9 +157,7 @@ int get_hp_hw_control_from_firmware(struct pci_dev *dev)
156 * Some older BIOS's don't support _OSC but support 157 * Some older BIOS's don't support _OSC but support
157 * OSHP to do the same thing 158 * OSHP to do the same thing
158 */ 159 */
159 acpi_handle handle = DEVICE_ACPI_HANDLE(&(dev->dev)); 160 status = acpi_run_oshp(handle);
160 if (handle)
161 status = acpi_run_oshp(handle);
162 } 161 }
163 if (ACPI_FAILURE(status)) { 162 if (ACPI_FAILURE(status)) {
164 err("Cannot get control of hotplug hardware\n"); 163 err("Cannot get control of hotplug hardware\n");
diff --git a/drivers/pci/pci-acpi.c b/drivers/pci/pci-acpi.c
index e9e37abe1f76..a9b00cc2d885 100644
--- a/drivers/pci/pci-acpi.c
+++ b/drivers/pci/pci-acpi.c
@@ -91,9 +91,7 @@ acpi_query_osc (
91static acpi_status 91static acpi_status
92acpi_run_osc ( 92acpi_run_osc (
93 acpi_handle handle, 93 acpi_handle handle,
94 u32 level, 94 void *context)
95 void *context,
96 void **retval )
97{ 95{
98 acpi_status status; 96 acpi_status status;
99 struct acpi_object_list input; 97 struct acpi_object_list input;
@@ -184,7 +182,7 @@ EXPORT_SYMBOL(pci_osc_support_set);
184 * 182 *
185 * Attempt to take control from Firmware on requested control bits. 183 * Attempt to take control from Firmware on requested control bits.
186 **/ 184 **/
187acpi_status pci_osc_control_set(u32 flags) 185acpi_status pci_osc_control_set(acpi_handle handle, u32 flags)
188{ 186{
189 acpi_status status; 187 acpi_status status;
190 u32 ctrlset; 188 u32 ctrlset;
@@ -198,10 +196,7 @@ acpi_status pci_osc_control_set(u32 flags)
198 return AE_SUPPORT; 196 return AE_SUPPORT;
199 } 197 }
200 ctrlset_buf[OSC_CONTROL_TYPE] |= ctrlset; 198 ctrlset_buf[OSC_CONTROL_TYPE] |= ctrlset;
201 status = acpi_get_devices ( PCI_ROOT_HID_STRING, 199 status = acpi_run_osc(handle, ctrlset_buf);
202 acpi_run_osc,
203 ctrlset_buf,
204 NULL );
205 if (ACPI_FAILURE (status)) { 200 if (ACPI_FAILURE (status)) {
206 ctrlset_buf[OSC_CONTROL_TYPE] &= ~ctrlset; 201 ctrlset_buf[OSC_CONTROL_TYPE] &= ~ctrlset;
207 } 202 }
diff --git a/include/linux/pci-acpi.h b/include/linux/pci-acpi.h
index 857126a36ecc..4877e35ae202 100644
--- a/include/linux/pci-acpi.h
+++ b/include/linux/pci-acpi.h
@@ -47,14 +47,15 @@
47 OSC_PCI_EXPRESS_CAP_STRUCTURE_CONTROL) 47 OSC_PCI_EXPRESS_CAP_STRUCTURE_CONTROL)
48 48
49#ifdef CONFIG_ACPI 49#ifdef CONFIG_ACPI
50extern acpi_status pci_osc_control_set(u32 flags); 50extern acpi_status pci_osc_control_set(acpi_handle handle, u32 flags);
51extern acpi_status pci_osc_support_set(u32 flags); 51extern acpi_status pci_osc_support_set(u32 flags);
52#else 52#else
53#if !defined(acpi_status) 53#if !defined(acpi_status)
54typedef u32 acpi_status; 54typedef u32 acpi_status;
55#define AE_ERROR (acpi_status) (0x0001) 55#define AE_ERROR (acpi_status) (0x0001)
56#endif 56#endif
57static inline acpi_status pci_osc_control_set(u32 flags) {return AE_ERROR;} 57static inline acpi_status pci_osc_control_set(acpi_handle handle, u32 flags)
58{return AE_ERROR;}
58static inline acpi_status pci_osc_support_set(u32 flags) {return AE_ERROR;} 59static inline acpi_status pci_osc_support_set(u32 flags) {return AE_ERROR;}
59#endif 60#endif
60 61