aboutsummaryrefslogtreecommitdiffstats
path: root/pci
diff options
context:
space:
mode:
authorGreg Kroah-Hartman <gregkh@suse.de>2006-05-01 22:57:24 -0700
committerGreg Kroah-Hartman <gregkh@suse.de>2006-05-01 22:57:24 -0700
commit5fe8a0d180166b24d6181657324a460c429939b5 (patch)
tree10a9cb3c335c76f7325553cdbce3093019d6c405 /pci
parentde68488eebf4191d07dad2802b458a08f73f0e58 (diff)
downloadpatches-5fe8a0d180166b24d6181657324a460c429939b5.tar.gz
added pci hotplug patches
Diffstat (limited to 'pci')
-rw-r--r--pci/acpi_pcihp-add-support-for-_hpx.patch424
-rw-r--r--pci/acpi_pcihp-fix-programming-_hpp-values.patch135
-rw-r--r--pci/acpi_pcihp-remove-improper-error-message-about-oshp.patch30
-rw-r--r--pci/pciehp-fix-programming-hotplug-parameters.patch178
-rw-r--r--pci/shpc-cleanup-shpc-logical-slot-register-access.patch142
-rw-r--r--pci/shpc-cleanup-shpc-logical-slot-register-bits-access.patch299
-rw-r--r--pci/shpc-cleanup-shpc-register-access.patch536
-rw-r--r--pci/shpc-fix-shpc-contoller-serr-int-register-bits-access.patch115
-rw-r--r--pci/shpc-fix-shpc-logical-slot-register-bits-access.patch148
9 files changed, 2007 insertions, 0 deletions
diff --git a/pci/acpi_pcihp-add-support-for-_hpx.patch b/pci/acpi_pcihp-add-support-for-_hpx.patch
new file mode 100644
index 0000000000000..201a6c5b71958
--- /dev/null
+++ b/pci/acpi_pcihp-add-support-for-_hpx.patch
@@ -0,0 +1,424 @@
+From pcihpd-discuss-admin@lists.sourceforge.net Mon May 1 19:00:10 2006
+Message-ID: <4456BC7A.10908@jp.fujitsu.com>
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: gregkh@suse.de, kristen.c.accardi@intel.com
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: acpi_pcihp: Add support for _HPX
+Date: Tue, 02 May 2006 10:57:14 +0900
+
+This patch adds support for _HPX (Hot Plug Parameter Extensions)
+defined in ACPI3.0a spec.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/acpi_pcihp.c | 190 +++++++++++++++++++++++++++++++++++--
+ drivers/pci/hotplug/acpiphp_glue.c | 31 +++---
+ drivers/pci/hotplug/pci_hotplug.h | 48 ++++++++-
+ drivers/pci/hotplug/shpchp_pci.c | 35 ++++--
+ 4 files changed, 265 insertions(+), 39 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/acpi_pcihp.c
++++ gregkh-2.6/drivers/pci/hotplug/acpi_pcihp.c
+@@ -37,6 +37,171 @@
+ #define METHOD_NAME__HPP "_HPP"
+ #define METHOD_NAME_OSHP "OSHP"
+
++static acpi_status
++decode_type0_hpx_record(union acpi_object *record, struct hotplug_params *hpx)
++{
++ int i;
++ union acpi_object *fields = record->package.elements;
++ u32 revision = fields[1].integer.value;
++
++ switch (revision) {
++ case 1:
++ if (record->package.count != 6)
++ return AE_ERROR;
++ for (i = 2; i < 6; i++)
++ if (fields[i].type != ACPI_TYPE_INTEGER)
++ return AE_ERROR;
++ hpx->t0 = &hpx->type0_data;
++ hpx->t0->revision = revision;
++ hpx->t0->cache_line_size = fields[2].integer.value;
++ hpx->t0->latency_timer = fields[3].integer.value;
++ hpx->t0->enable_serr = fields[4].integer.value;
++ hpx->t0->enable_perr = fields[5].integer.value;
++ break;
++ default:
++ printk(KERN_WARNING
++ "%s: Type 0 Revision %d record not supported\n",
++ __FUNCTION__, revision);
++ return AE_ERROR;
++ }
++ return AE_OK;
++}
++
++static acpi_status
++decode_type1_hpx_record(union acpi_object *record, struct hotplug_params *hpx)
++{
++ int i;
++ union acpi_object *fields = record->package.elements;
++ u32 revision = fields[1].integer.value;
++
++ switch (revision) {
++ case 1:
++ if (record->package.count != 5)
++ return AE_ERROR;
++ for (i = 2; i < 5; i++)
++ if (fields[i].type != ACPI_TYPE_INTEGER)
++ return AE_ERROR;
++ hpx->t1 = &hpx->type1_data;
++ hpx->t1->revision = revision;
++ hpx->t1->max_mem_read = fields[2].integer.value;
++ hpx->t1->avg_max_split = fields[3].integer.value;
++ hpx->t1->tot_max_split = fields[4].integer.value;
++ break;
++ default:
++ printk(KERN_WARNING
++ "%s: Type 1 Revision %d record not supported\n",
++ __FUNCTION__, revision);
++ return AE_ERROR;
++ }
++ return AE_OK;
++}
++
++static acpi_status
++decode_type2_hpx_record(union acpi_object *record, struct hotplug_params *hpx)
++{
++ int i;
++ union acpi_object *fields = record->package.elements;
++ u32 revision = fields[1].integer.value;
++
++ switch (revision) {
++ case 1:
++ if (record->package.count != 18)
++ return AE_ERROR;
++ for (i = 2; i < 18; i++)
++ if (fields[i].type != ACPI_TYPE_INTEGER)
++ return AE_ERROR;
++ hpx->t2 = &hpx->type2_data;
++ hpx->t2->revision = revision;
++ hpx->t2->unc_err_mask_and = fields[2].integer.value;
++ hpx->t2->unc_err_mask_or = fields[3].integer.value;
++ hpx->t2->unc_err_sever_and = fields[4].integer.value;
++ hpx->t2->unc_err_sever_or = fields[5].integer.value;
++ hpx->t2->cor_err_mask_and = fields[6].integer.value;
++ hpx->t2->cor_err_mask_or = fields[7].integer.value;
++ hpx->t2->adv_err_cap_and = fields[8].integer.value;
++ hpx->t2->adv_err_cap_or = fields[9].integer.value;
++ hpx->t2->pci_exp_devctl_and = fields[10].integer.value;
++ hpx->t2->pci_exp_devctl_or = fields[11].integer.value;
++ hpx->t2->pci_exp_lnkctl_and = fields[12].integer.value;
++ hpx->t2->pci_exp_lnkctl_or = fields[13].integer.value;
++ hpx->t2->sec_unc_err_sever_and = fields[14].integer.value;
++ hpx->t2->sec_unc_err_sever_or = fields[15].integer.value;
++ hpx->t2->sec_unc_err_mask_and = fields[16].integer.value;
++ hpx->t2->sec_unc_err_mask_or = fields[17].integer.value;
++ break;
++ default:
++ printk(KERN_WARNING
++ "%s: Type 2 Revision %d record not supported\n",
++ __FUNCTION__, revision);
++ return AE_ERROR;
++ }
++ return AE_OK;
++}
++
++static acpi_status
++acpi_run_hpx(acpi_handle handle, struct hotplug_params *hpx)
++{
++ acpi_status status;
++ struct acpi_buffer buffer = {ACPI_ALLOCATE_BUFFER, NULL};
++ union acpi_object *package, *record, *fields;
++ u32 type;
++ int i;
++
++ /* Clear the return buffer with zeros */
++ memset(hpx, 0, sizeof(struct hotplug_params));
++
++ status = acpi_evaluate_object(handle, "_HPX", NULL, &buffer);
++ if (ACPI_FAILURE(status))
++ return status;
++
++ package = (union acpi_object *)buffer.pointer;
++ if (package->type != ACPI_TYPE_PACKAGE) {
++ status = AE_ERROR;
++ goto exit;
++ }
++
++ for (i = 0; i < package->package.count; i++) {
++ record = &package->package.elements[i];
++ if (record->type != ACPI_TYPE_PACKAGE) {
++ status = AE_ERROR;
++ goto exit;
++ }
++
++ fields = record->package.elements;
++ if (fields[0].type != ACPI_TYPE_INTEGER ||
++ fields[1].type != ACPI_TYPE_INTEGER) {
++ status = AE_ERROR;
++ goto exit;
++ }
++
++ type = fields[0].integer.value;
++ switch (type) {
++ case 0:
++ status = decode_type0_hpx_record(record, hpx);
++ if (ACPI_FAILURE(status))
++ goto exit;
++ break;
++ case 1:
++ status = decode_type1_hpx_record(record, hpx);
++ if (ACPI_FAILURE(status))
++ goto exit;
++ break;
++ case 2:
++ status = decode_type2_hpx_record(record, hpx);
++ if (ACPI_FAILURE(status))
++ goto exit;
++ break;
++ default:
++ printk(KERN_ERR "%s: Type %d record not supported\n",
++ __FUNCTION__, type);
++ status = AE_ERROR;
++ goto exit;
++ }
++ }
++ exit:
++ kfree(buffer.pointer);
++ return status;
++}
+
+ static acpi_status
+ acpi_run_hpp(acpi_handle handle, struct hotplug_params *hpp)
+@@ -50,6 +215,9 @@ acpi_run_hpp(acpi_handle handle, struct
+
+ acpi_get_name(handle, ACPI_FULL_PATHNAME, &string);
+
++ /* Clear the return buffer with zeros */
++ memset(hpp, 0, sizeof(struct hotplug_params));
++
+ /* get _hpp */
+ status = acpi_evaluate_object(handle, METHOD_NAME__HPP, NULL, &ret_buf);
+ switch (status) {
+@@ -98,15 +266,16 @@ acpi_run_hpp(acpi_handle handle, struct
+ }
+ }
+
+- hpp->cache_line_size = nui[0];
+- hpp->latency_timer = nui[1];
+- hpp->enable_serr = nui[2];
+- hpp->enable_perr = nui[3];
+-
+- pr_debug(" _HPP: cache_line_size=0x%x\n", hpp->cache_line_size);
+- pr_debug(" _HPP: latency timer =0x%x\n", hpp->latency_timer);
+- pr_debug(" _HPP: enable SERR =0x%x\n", hpp->enable_serr);
+- pr_debug(" _HPP: enable PERR =0x%x\n", hpp->enable_perr);
++ hpp->t0 = &hpp->type0_data;
++ hpp->t0->cache_line_size = nui[0];
++ hpp->t0->latency_timer = nui[1];
++ hpp->t0->enable_serr = nui[2];
++ hpp->t0->enable_perr = nui[3];
++
++ pr_debug(" _HPP: cache_line_size=0x%x\n", hpp->t0->cache_line_size);
++ pr_debug(" _HPP: latency timer =0x%x\n", hpp->t0->latency_timer);
++ pr_debug(" _HPP: enable SERR =0x%x\n", hpp->t0->enable_serr);
++ pr_debug(" _HPP: enable PERR =0x%x\n", hpp->t0->enable_perr);
+
+ free_and_return:
+ kfree(string.pointer);
+@@ -174,6 +343,9 @@ acpi_status acpi_get_hp_params_from_firm
+ * this pci dev. If we don't find any _HPP, use hardcoded defaults
+ */
+ while (handle) {
++ status = acpi_run_hpx(handle, hpp);
++ if (ACPI_SUCCESS(status))
++ break;
+ status = acpi_run_hpp(handle, hpp);
+ if (ACPI_SUCCESS(status))
+ break;
+--- gregkh-2.6.orig/drivers/pci/hotplug/acpiphp_glue.c
++++ gregkh-2.6/drivers/pci/hotplug/acpiphp_glue.c
+@@ -287,12 +287,18 @@ static void decode_hpp(struct acpiphp_br
+ acpi_status status;
+
+ status = acpi_get_hp_params_from_firmware(bridge->pci_bus, &bridge->hpp);
+- if (ACPI_FAILURE(status)) {
++ if (ACPI_FAILURE(status) ||
++ !bridge->hpp.t0 || (bridge->hpp.t0->revision > 1)) {
+ /* use default numbers */
+- bridge->hpp.cache_line_size = 0x10;
+- bridge->hpp.latency_timer = 0x40;
+- bridge->hpp.enable_serr = 0;
+- bridge->hpp.enable_perr = 0;
++ printk(KERN_WARNING
++ "%s: Could not get hotplug parameters. Use defaults\n",
++ __FUNCTION__);
++ bridge->hpp.t0 = &bridge->hpp.type0_data;
++ bridge->hpp.t0->revision = 0;
++ bridge->hpp.t0->cache_line_size = 0x10;
++ bridge->hpp.t0->latency_timer = 0x40;
++ bridge->hpp.t0->enable_serr = 0;
++ bridge->hpp.t0->enable_perr = 0;
+ }
+ }
+
+@@ -1206,16 +1212,17 @@ static void program_hpp(struct pci_dev *
+ (dev->hdr_type == PCI_HEADER_TYPE_BRIDGE &&
+ (dev->class >> 8) == PCI_CLASS_BRIDGE_PCI)))
+ return;
++
+ pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE,
+- bridge->hpp.cache_line_size);
++ bridge->hpp.t0->cache_line_size);
+ pci_write_config_byte(dev, PCI_LATENCY_TIMER,
+- bridge->hpp.latency_timer);
++ bridge->hpp.t0->latency_timer);
+ pci_read_config_word(dev, PCI_COMMAND, &pci_cmd);
+- if (bridge->hpp.enable_serr)
++ if (bridge->hpp.t0->enable_serr)
+ pci_cmd |= PCI_COMMAND_SERR;
+ else
+ pci_cmd &= ~PCI_COMMAND_SERR;
+- if (bridge->hpp.enable_perr)
++ if (bridge->hpp.t0->enable_perr)
+ pci_cmd |= PCI_COMMAND_PARITY;
+ else
+ pci_cmd &= ~PCI_COMMAND_PARITY;
+@@ -1224,13 +1231,13 @@ static void program_hpp(struct pci_dev *
+ /* Program bridge control value and child devices */
+ if ((dev->class >> 8) == PCI_CLASS_BRIDGE_PCI) {
+ pci_write_config_byte(dev, PCI_SEC_LATENCY_TIMER,
+- bridge->hpp.latency_timer);
++ bridge->hpp.t0->latency_timer);
+ pci_read_config_word(dev, PCI_BRIDGE_CONTROL, &pci_bctl);
+- if (bridge->hpp.enable_serr)
++ if (bridge->hpp.t0->enable_serr)
+ pci_bctl |= PCI_BRIDGE_CTL_SERR;
+ else
+ pci_bctl &= ~PCI_BRIDGE_CTL_SERR;
+- if (bridge->hpp.enable_perr)
++ if (bridge->hpp.t0->enable_perr)
+ pci_bctl |= PCI_BRIDGE_CTL_PARITY;
+ else
+ pci_bctl &= ~PCI_BRIDGE_CTL_PARITY;
+--- gregkh-2.6.orig/drivers/pci/hotplug/pci_hotplug.h
++++ gregkh-2.6/drivers/pci/hotplug/pci_hotplug.h
+@@ -176,11 +176,51 @@ extern int pci_hp_change_slot_info (stru
+ struct hotplug_slot_info *info);
+ extern struct subsystem pci_hotplug_slots_subsys;
+
++/* PCI Setting Record (Type 0) */
++struct hpp_type0 {
++ u32 revision;
++ u8 cache_line_size;
++ u8 latency_timer;
++ u8 enable_serr;
++ u8 enable_perr;
++};
++
++/* PCI-X Setting Record (Type 1) */
++struct hpp_type1 {
++ u32 revision;
++ u8 max_mem_read;
++ u8 avg_max_split;
++ u16 tot_max_split;
++};
++
++/* PCI Express Setting Record (Type 2) */
++struct hpp_type2 {
++ u32 revision;
++ u32 unc_err_mask_and;
++ u32 unc_err_mask_or;
++ u32 unc_err_sever_and;
++ u32 unc_err_sever_or;
++ u32 cor_err_mask_and;
++ u32 cor_err_mask_or;
++ u32 adv_err_cap_and;
++ u32 adv_err_cap_or;
++ u16 pci_exp_devctl_and;
++ u16 pci_exp_devctl_or;
++ u16 pci_exp_lnkctl_and;
++ u16 pci_exp_lnkctl_or;
++ u32 sec_unc_err_sever_and;
++ u32 sec_unc_err_sever_or;
++ u32 sec_unc_err_mask_and;
++ u32 sec_unc_err_mask_or;
++};
++
+ struct hotplug_params {
+- u8 cache_line_size;
+- u8 latency_timer;
+- u8 enable_serr;
+- u8 enable_perr;
++ struct hpp_type0 *t0; /* Type0: NULL if not available */
++ struct hpp_type1 *t1; /* Type1: NULL if not available */
++ struct hpp_type2 *t2; /* Type2: NULL if not available */
++ struct hpp_type0 type0_data;
++ struct hpp_type1 type1_data;
++ struct hpp_type2 type2_data;
+ };
+
+ #ifdef CONFIG_ACPI
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_pci.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_pci.c
+@@ -47,21 +47,28 @@ static void program_fw_provided_values(s
+ return;
+
+ /* use default values if we can't get them from firmware */
+- if (get_hp_params_from_firmware(dev, &hpp)) {
+- hpp.cache_line_size = 8;
+- hpp.latency_timer = 0x40;
+- hpp.enable_serr = 0;
+- hpp.enable_perr = 0;
+- }
+-
+- pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE, hpp.cache_line_size);
+- pci_write_config_byte(dev, PCI_LATENCY_TIMER, hpp.latency_timer);
++ if (get_hp_params_from_firmware(dev, &hpp) ||
++ !hpp.t0 || (hpp.t0->revision > 1)) {
++ printk(KERN_WARNING
++ "%s: Could not get hotplug parameters. Use defaults\n",
++ __FUNCTION__);
++ hpp.t0 = &hpp.type0_data;
++ hpp.t0->revision = 0;
++ hpp.t0->cache_line_size = 8;
++ hpp.t0->latency_timer = 0x40;
++ hpp.t0->enable_serr = 0;
++ hpp.t0->enable_perr = 0;
++ }
++
++ pci_write_config_byte(dev,
++ PCI_CACHE_LINE_SIZE, hpp.t0->cache_line_size);
++ pci_write_config_byte(dev, PCI_LATENCY_TIMER, hpp.t0->latency_timer);
+ pci_read_config_word(dev, PCI_COMMAND, &pci_cmd);
+- if (hpp.enable_serr)
++ if (hpp.t0->enable_serr)
+ pci_cmd |= PCI_COMMAND_SERR;
+ else
+ pci_cmd &= ~PCI_COMMAND_SERR;
+- if (hpp.enable_perr)
++ if (hpp.t0->enable_perr)
+ pci_cmd |= PCI_COMMAND_PARITY;
+ else
+ pci_cmd &= ~PCI_COMMAND_PARITY;
+@@ -70,13 +77,13 @@ static void program_fw_provided_values(s
+ /* Program bridge control value and child devices */
+ if ((dev->class >> 8) == PCI_CLASS_BRIDGE_PCI) {
+ pci_write_config_byte(dev, PCI_SEC_LATENCY_TIMER,
+- hpp.latency_timer);
++ hpp.t0->latency_timer);
+ pci_read_config_word(dev, PCI_BRIDGE_CONTROL, &pci_bctl);
+- if (hpp.enable_serr)
++ if (hpp.t0->enable_serr)
+ pci_bctl |= PCI_BRIDGE_CTL_SERR;
+ else
+ pci_bctl &= ~PCI_BRIDGE_CTL_SERR;
+- if (hpp.enable_perr)
++ if (hpp.t0->enable_perr)
+ pci_bctl |= PCI_BRIDGE_CTL_PARITY;
+ else
+ pci_bctl &= ~PCI_BRIDGE_CTL_PARITY;
diff --git a/pci/acpi_pcihp-fix-programming-_hpp-values.patch b/pci/acpi_pcihp-fix-programming-_hpp-values.patch
new file mode 100644
index 0000000000000..ca212453e04bf
--- /dev/null
+++ b/pci/acpi_pcihp-fix-programming-_hpp-values.patch
@@ -0,0 +1,135 @@
+From pcihpd-discuss-admin@lists.sourceforge.net Mon May 1 18:58:14 2006
+Message-ID: <4456BBEA.2000005@jp.fujitsu.com>
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: gregkh@suse.de, kristen.c.accardi@intel.com
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: acpi_pcihp: Fix programming _HPP values
+Date: Tue, 02 May 2006 10:54:50 +0900
+
+This patch fixes the problem that hotplug parameters are not programed
+when PCI cards are hot-added by ACPIPHP, SHPCHP and PCIEHP driver. The
+pci_dev structure being hot-added is not bound to ACPI handle, so we
+need to trace PCI bus tree to find ACPI handle.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+
+---
+ drivers/pci/hotplug/acpi_pcihp.c | 34 ++++++++++++++++++++++++----------
+ drivers/pci/hotplug/acpiphp_glue.c | 3 ++-
+ drivers/pci/hotplug/pci_hotplug.h | 2 +-
+ drivers/pci/hotplug/pciehp.h | 2 +-
+ drivers/pci/hotplug/shpchp.h | 2 +-
+ 5 files changed, 29 insertions(+), 14 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/acpi_pcihp.c
++++ gregkh-2.6/drivers/pci/hotplug/acpi_pcihp.c
+@@ -145,14 +145,27 @@ EXPORT_SYMBOL_GPL(acpi_run_oshp);
+
+ /* acpi_get_hp_params_from_firmware
+ *
+- * @dev - the pci_dev of the newly added device
++ * @bus - the pci_bus of the bus on which the device is newly added
+ * @hpp - allocated by the caller
+ */
+-acpi_status acpi_get_hp_params_from_firmware(struct pci_dev *dev,
++acpi_status acpi_get_hp_params_from_firmware(struct pci_bus *bus,
+ struct hotplug_params *hpp)
+ {
+ acpi_status status = AE_NOT_FOUND;
+- struct pci_dev *pdev = dev;
++ acpi_handle handle, phandle;
++ struct pci_bus *pbus = bus;
++ struct pci_dev *pdev;
++
++ do {
++ pdev = pbus->self;
++ if (!pdev) {
++ handle = acpi_get_pci_rootbridge_handle(
++ pci_domain_nr(pbus), pbus->number);
++ break;
++ }
++ handle = DEVICE_ACPI_HANDLE(&(pdev->dev));
++ pbus = pbus->parent;
++ } while (!handle);
+
+ /*
+ * _HPP settings apply to all child buses, until another _HPP is
+@@ -160,15 +173,16 @@ acpi_status acpi_get_hp_params_from_firm
+ * look for it in the parent device scope since that would apply to
+ * this pci dev. If we don't find any _HPP, use hardcoded defaults
+ */
+- while (pdev && (ACPI_FAILURE(status))) {
+- acpi_handle handle = DEVICE_ACPI_HANDLE(&(pdev->dev));
+- if (!handle)
+- break;
++ while (handle) {
+ status = acpi_run_hpp(handle, hpp);
+- if (!(pdev->bus->parent))
++ if (ACPI_SUCCESS(status))
++ break;
++ if (acpi_root_bridge(handle))
++ break;
++ status = acpi_get_parent(handle, &phandle);
++ if (ACPI_FAILURE(status))
+ break;
+- /* Check if a parent object supports _HPP */
+- pdev = pdev->bus->parent->self;
++ handle = phandle;
+ }
+ return status;
+ }
+--- gregkh-2.6.orig/drivers/pci/hotplug/acpiphp_glue.c
++++ gregkh-2.6/drivers/pci/hotplug/acpiphp_glue.c
+@@ -286,7 +286,7 @@ static void decode_hpp(struct acpiphp_br
+ {
+ acpi_status status;
+
+- status = acpi_get_hp_params_from_firmware(bridge->pci_dev, &bridge->hpp);
++ status = acpi_get_hp_params_from_firmware(bridge->pci_bus, &bridge->hpp);
+ if (ACPI_FAILURE(status)) {
+ /* use default numbers */
+ bridge->hpp.cache_line_size = 0x10;
+@@ -1250,6 +1250,7 @@ static void acpiphp_set_hpp_values(acpi_
+
+ memset(&bridge, 0, sizeof(bridge));
+ bridge.handle = handle;
++ bridge.pci_bus = bus;
+ bridge.pci_dev = bus->self;
+ decode_hpp(&bridge);
+ list_for_each_entry(dev, &bus->devices, bus_list)
+--- gregkh-2.6.orig/drivers/pci/hotplug/pci_hotplug.h
++++ gregkh-2.6/drivers/pci/hotplug/pci_hotplug.h
+@@ -188,7 +188,7 @@ struct hotplug_params {
+ #include <acpi/acpi_bus.h>
+ #include <acpi/actypes.h>
+ extern acpi_status acpi_run_oshp(acpi_handle handle);
+-extern acpi_status acpi_get_hp_params_from_firmware(struct pci_dev *dev,
++extern acpi_status acpi_get_hp_params_from_firmware(struct pci_bus *bus,
+ struct hotplug_params *hpp);
+ int acpi_root_bridge(acpi_handle handle);
+ #endif
+--- gregkh-2.6.orig/drivers/pci/hotplug/pciehp.h
++++ gregkh-2.6/drivers/pci/hotplug/pciehp.h
+@@ -284,7 +284,7 @@ struct hpc_ops {
+ static inline int pciehp_get_hp_params_from_firmware(struct pci_dev *dev,
+ struct hotplug_params *hpp)
+ {
+- if (ACPI_FAILURE(acpi_get_hp_params_from_firmware(dev, hpp)))
++ if (ACPI_FAILURE(acpi_get_hp_params_from_firmware(dev->bus, hpp)))
+ return -ENODEV;
+ return 0;
+ }
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp.h
++++ gregkh-2.6/drivers/pci/hotplug/shpchp.h
+@@ -196,7 +196,7 @@ extern void queue_pushbutton_work(void *
+ static inline int get_hp_params_from_firmware(struct pci_dev *dev,
+ struct hotplug_params *hpp)
+ {
+- if (ACPI_FAILURE(acpi_get_hp_params_from_firmware(dev, hpp)))
++ if (ACPI_FAILURE(acpi_get_hp_params_from_firmware(dev->bus, hpp)))
+ return -ENODEV;
+ return 0;
+ }
diff --git a/pci/acpi_pcihp-remove-improper-error-message-about-oshp.patch b/pci/acpi_pcihp-remove-improper-error-message-about-oshp.patch
new file mode 100644
index 0000000000000..2adf2db50eee7
--- /dev/null
+++ b/pci/acpi_pcihp-remove-improper-error-message-about-oshp.patch
@@ -0,0 +1,30 @@
+From pcihpd-discuss-admin@lists.sourceforge.net Mon May 1 18:59:10 2006
+Message-ID: <4456BC22.8090806@jp.fujitsu.com>
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: gregkh@suse.de, kristen.c.accardi@intel.com
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: acpi_pcihp: Remove improper error message about OSHP
+Date: Tue, 02 May 2006 10:55:46 +0900
+
+This patch removes improper error messages from the acpi_run_oshp()
+function.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/acpi_pcihp.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/acpi_pcihp.c
++++ gregkh-2.6/drivers/pci/hotplug/acpi_pcihp.c
+@@ -129,7 +129,7 @@ acpi_status acpi_run_oshp(acpi_handle ha
+
+ /* run OSHP */
+ status = acpi_evaluate_object(handle, METHOD_NAME_OSHP, NULL, NULL);
+- if (ACPI_FAILURE(status))
++ if (ACPI_FAILURE(status) && (status != AE_NOT_FOUND))
+ printk(KERN_ERR "%s:%s OSHP fails=0x%x\n", __FUNCTION__,
+ (char *)string.pointer, status);
+ else
diff --git a/pci/pciehp-fix-programming-hotplug-parameters.patch b/pci/pciehp-fix-programming-hotplug-parameters.patch
new file mode 100644
index 0000000000000..692e5457d93da
--- /dev/null
+++ b/pci/pciehp-fix-programming-hotplug-parameters.patch
@@ -0,0 +1,178 @@
+From pcihpd-discuss-admin@lists.sourceforge.net Mon May 1 19:01:17 2006
+Message-ID: <4456BCB4.30707@jp.fujitsu.com>
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: gregkh@suse.de, kristen.c.accardi@intel.com
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: pciehp: Fix programming hotplug parameters
+Date: Tue, 02 May 2006 10:58:12 +0900
+
+Current PCHEHP driver doesn't have any code to program hotplug
+parameters from firmware. So hotplug parameters are never programed at
+hot-add time. This patch add support for programming hotplug
+parameters to PCIEHP driver.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/pciehp_pci.c | 141 ++++++++++++++++++++++++++++++++++++++-
+ 1 file changed, 139 insertions(+), 2 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/pciehp_pci.c
++++ gregkh-2.6/drivers/pci/hotplug/pciehp_pci.c
+@@ -34,6 +34,144 @@
+ #include "../pci.h"
+ #include "pciehp.h"
+
++static void program_hpp_type0(struct pci_dev *dev, struct hpp_type0 *hpp)
++{
++ u16 pci_cmd, pci_bctl;
++
++ if (hpp->revision > 1) {
++ printk(KERN_WARNING "%s: Rev.%d type0 record not supported\n",
++ __FUNCTION__, hpp->revision);
++ return;
++ }
++
++ pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE, hpp->cache_line_size);
++ pci_write_config_byte(dev, PCI_LATENCY_TIMER, hpp->latency_timer);
++ pci_read_config_word(dev, PCI_COMMAND, &pci_cmd);
++ if (hpp->enable_serr)
++ pci_cmd |= PCI_COMMAND_SERR;
++ else
++ pci_cmd &= ~PCI_COMMAND_SERR;
++ if (hpp->enable_perr)
++ pci_cmd |= PCI_COMMAND_PARITY;
++ else
++ pci_cmd &= ~PCI_COMMAND_PARITY;
++ pci_write_config_word(dev, PCI_COMMAND, pci_cmd);
++
++ /* Program bridge control value */
++ if ((dev->class >> 8) == PCI_CLASS_BRIDGE_PCI) {
++ pci_write_config_byte(dev, PCI_SEC_LATENCY_TIMER,
++ hpp->latency_timer);
++ pci_read_config_word(dev, PCI_BRIDGE_CONTROL, &pci_bctl);
++ if (hpp->enable_serr)
++ pci_bctl |= PCI_BRIDGE_CTL_SERR;
++ else
++ pci_bctl &= ~PCI_BRIDGE_CTL_SERR;
++ if (hpp->enable_perr)
++ pci_bctl |= PCI_BRIDGE_CTL_PARITY;
++ else
++ pci_bctl &= ~PCI_BRIDGE_CTL_PARITY;
++ pci_write_config_word(dev, PCI_BRIDGE_CONTROL, pci_bctl);
++ }
++}
++
++static void program_hpp_type2(struct pci_dev *dev, struct hpp_type2 *hpp)
++{
++ int pos;
++ u16 reg16;
++ u32 reg32;
++
++ if (hpp->revision > 1) {
++ printk(KERN_WARNING "%s: Rev.%d type2 record not supported\n",
++ __FUNCTION__, hpp->revision);
++ return;
++ }
++
++ /* Find PCI Express capability */
++ pos = pci_find_capability(dev, PCI_CAP_ID_EXP);
++ if (!pos)
++ return;
++
++ /* Initialize Device Control Register */
++ pci_read_config_word(dev, pos + PCI_EXP_DEVCTL, &reg16);
++ reg32 = (reg16 & hpp->pci_exp_devctl_and) | hpp->pci_exp_devctl_or;
++ pci_write_config_word(dev, pos + PCI_EXP_DEVCTL, reg16);
++
++ /* Initialize Link Control Register */
++ if (dev->subordinate) {
++ pci_read_config_word(dev, pos + PCI_EXP_LNKCTL, &reg16);
++ reg16 = (reg32 & hpp->pci_exp_lnkctl_and)
++ | hpp->pci_exp_lnkctl_or;
++ pci_write_config_word(dev, pos + PCI_EXP_LNKCTL, reg16);
++ }
++
++ /* Find Advanced Error Reporting Enhanced Capability */
++ pos = 256;
++ do {
++ pci_read_config_dword(dev, pos, &reg32);
++ if (PCI_EXT_CAP_ID(reg32) == PCI_EXT_CAP_ID_ERR)
++ break;
++ } while ((pos = PCI_EXT_CAP_NEXT(reg32)));
++ if (!pos)
++ return;
++
++ /* Initialize Uncorrectable Error Mask Register */
++ pci_read_config_dword(dev, pos + PCI_ERR_UNCOR_MASK, &reg32);
++ reg32 = (reg32 & hpp->unc_err_mask_and) | hpp->unc_err_mask_or;
++ pci_write_config_dword(dev, pos + PCI_ERR_UNCOR_MASK, reg32);
++
++ /* Initialize Uncorrectable Error Severity Register */
++ pci_read_config_dword(dev, pos + PCI_ERR_UNCOR_SEVER, &reg32);
++ reg32 = (reg32 & hpp->unc_err_sever_and) | hpp->unc_err_sever_or;
++ pci_write_config_dword(dev, pos + PCI_ERR_UNCOR_SEVER, reg32);
++
++ /* Initialize Correctable Error Mask Register */
++ pci_read_config_dword(dev, pos + PCI_ERR_COR_MASK, &reg32);
++ reg32 = (reg32 & hpp->cor_err_mask_and) | hpp->cor_err_mask_or;
++ pci_write_config_dword(dev, pos + PCI_ERR_COR_MASK, reg32);
++
++ /* Initialize Advanced Error Capabilities and Control Register */
++ pci_read_config_dword(dev, pos + PCI_ERR_CAP, &reg32);
++ reg32 = (reg32 & hpp->adv_err_cap_and) | hpp->adv_err_cap_or;
++ pci_write_config_dword(dev, pos + PCI_ERR_CAP, reg32);
++
++ /*
++ * FIXME: The following two registers are not supported yet.
++ *
++ * o Secondary Uncorrectable Error Severity Register
++ * o Secondary Uncorrectable Error Mask Register
++ */
++}
++
++static void program_fw_provided_values(struct pci_dev *dev)
++{
++ struct pci_dev *cdev;
++ struct hotplug_params hpp;
++
++ /* Program hpp values for this device */
++ if (!(dev->hdr_type == PCI_HEADER_TYPE_NORMAL ||
++ (dev->hdr_type == PCI_HEADER_TYPE_BRIDGE &&
++ (dev->class >> 8) == PCI_CLASS_BRIDGE_PCI)))
++ return;
++
++ if (pciehp_get_hp_params_from_firmware(dev, &hpp)) {
++ printk(KERN_WARNING "%s: Could not get hotplug parameters\n",
++ __FUNCTION__);
++ return;
++ }
++
++ if (hpp.t2)
++ program_hpp_type2(dev, hpp.t2);
++ if (hpp.t0)
++ program_hpp_type0(dev, hpp.t0);
++
++ /* Program child devices */
++ if (dev->subordinate) {
++ list_for_each_entry(cdev, &dev->subordinate->devices,
++ bus_list)
++ program_fw_provided_values(cdev);
++ }
++}
++
+ static int pciehp_add_bridge(struct pci_dev *dev)
+ {
+ struct pci_bus *parent = dev->bus;
+@@ -92,8 +230,7 @@ int pciehp_configure_device(struct slot
+ (dev->hdr_type == PCI_HEADER_TYPE_CARDBUS)) {
+ pciehp_add_bridge(dev);
+ }
+- /* TBD: program firmware provided _HPP values */
+- /* program_fw_provided_values(dev); */
++ program_fw_provided_values(dev);
+ }
+
+ pci_bus_assign_resources(parent);
diff --git a/pci/shpc-cleanup-shpc-logical-slot-register-access.patch b/pci/shpc-cleanup-shpc-logical-slot-register-access.patch
new file mode 100644
index 0000000000000..c827331718ff2
--- /dev/null
+++ b/pci/shpc-cleanup-shpc-logical-slot-register-access.patch
@@ -0,0 +1,142 @@
+From kaneshige.kenji@jp.fujitsu.com Mon May 1 19:12:18 2006
+Message-ID: <4456BF66.6090200@jp.fujitsu.com>
+Date: Tue, 02 May 2006 11:09:42 +0900
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: Greg KH <gregkh@suse.de>, Kristen Accardi <kristen.c.accardi@intel.com>
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: SHPC: Cleanup SHPC Logical Slot Register access
+
+This patch cleans up the code to access slot logical registers. This
+patch has no functional changes.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/shpchp_hpc.c | 31 ++++++++++++++++++-------------
+ 1 file changed, 18 insertions(+), 13 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_hpc.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_hpc.c
+@@ -90,6 +90,11 @@
+ #define MRLSENSOR 0x40000000
+ #define ATTN_BUTTON 0x80000000
+
++/*
++ * Logical Slot Register definitions
++ */
++#define SLOT_REG(i) (SLOT1 + (4 * i))
++
+ /* Slot Status Field Definitions */
+ /* Slot State */
+ #define PWR_ONLY 0x0001
+@@ -433,7 +438,7 @@ static int hpc_get_attention_status(stru
+ return -1;
+ }
+
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ atten_led_state = (slot_status & 0x0030) >> 4;
+
+@@ -474,7 +479,7 @@ static int hpc_get_power_status(struct s
+ return -1;
+ }
+
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ slot_state = (slot_status & 0x0003);
+
+@@ -514,7 +519,7 @@ static int hpc_get_latch_status(struct s
+ return -1;
+ }
+
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ slot_status = (u16)slot_reg;
+
+ *status = ((slot_status & 0x0100) == 0) ? 0 : 1; /* 0 -> close; 1 -> open */
+@@ -538,7 +543,7 @@ static int hpc_get_adapter_status(struct
+ return -1;
+ }
+
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ slot_status = (u16)slot_reg;
+ card_state = (u8)((slot_status & 0x0C00) >> 10);
+ *status = (card_state != 0x3) ? 1 : 0;
+@@ -568,7 +573,7 @@ static int hpc_get_adapter_speed(struct
+ {
+ int retval = 0;
+ struct controller *ctrl = slot->ctrl;
+- u32 slot_reg = shpc_readl(ctrl, SLOT1 + 4 * slot->hp_slot);
++ u32 slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ u8 pcix_cap = (slot_reg >> 12) & 7;
+ u8 m66_cap = (slot_reg >> 9) & 1;
+
+@@ -648,7 +653,7 @@ static int hpc_query_power_fault(struct
+ return -1;
+ }
+
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ pwr_fault_state = (slot_status & 0x0040) >> 7;
+ status = (pwr_fault_state == 1) ? 0 : 1;
+@@ -805,7 +810,7 @@ static void hpc_release_ctlr(struct cont
+ * Mask all slot event interrupts
+ */
+ for (i = 0; i < ctrl->num_slots; i++)
+- shpc_writel(ctrl, SLOT1 + (4 * i), 0xffff3fff);
++ shpc_writel(ctrl, SLOT_REG(i), 0xffff3fff);
+
+ cleanup_slots(ctrl);
+
+@@ -1072,7 +1077,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ for (hp_slot = 0; hp_slot < ctrl->num_slots; hp_slot++) {
+ /* To find out which slot has interrupt pending */
+ if ((intr_loc >> hp_slot) & 0x01) {
+- temp_dword = shpc_readl(ctrl, SLOT1 + (4*hp_slot));
++ temp_dword = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Slot %x with intr, slot register = %x\n",
+ __FUNCTION__, hp_slot, temp_dword);
+ temp_byte = (temp_dword >> 16) & 0xFF;
+@@ -1091,7 +1096,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+
+ /* Clear all slot events */
+ temp_dword = 0xe01f3fff;
+- shpc_writel(ctrl, SLOT1 + (4*hp_slot), temp_dword);
++ shpc_writel(ctrl, SLOT_REG(hp_slot), temp_dword);
+
+ intr_loc2 = shpc_readl(ctrl, INTR_LOC);
+ dbg("%s: intr_loc2 = %x\n",__FUNCTION__, intr_loc2);
+@@ -1379,11 +1384,11 @@ int shpc_init(struct controller * ctrl,
+ * Slot SERR-INT Mask & clear all the existing event if any
+ */
+ for (hp_slot = 0; hp_slot < php_ctlr->num_slots; hp_slot++) {
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*hp_slot );
++ slot_reg = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+ tempdword = 0xffff3fff;
+- shpc_writel(ctrl, SLOT1 + (4*hp_slot), tempdword);
++ shpc_writel(ctrl, SLOT_REG(hp_slot), tempdword);
+ }
+
+ if (shpchp_poll_mode) {/* Install interrupt polling code */
+@@ -1430,11 +1435,11 @@ int shpc_init(struct controller * ctrl,
+ ctlr_seq_num++;
+
+ for (hp_slot = 0; hp_slot < php_ctlr->num_slots; hp_slot++) {
+- slot_reg = shpc_readl(ctrl, SLOT1 + 4*hp_slot );
++ slot_reg = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+ tempdword = 0xe01f3fff;
+- shpc_writel(ctrl, SLOT1 + (4*hp_slot), tempdword);
++ shpc_writel(ctrl, SLOT_REG(hp_slot), tempdword);
+ }
+ if (!shpchp_poll_mode) {
+ /* Unmask all general input interrupts and SERR */
diff --git a/pci/shpc-cleanup-shpc-logical-slot-register-bits-access.patch b/pci/shpc-cleanup-shpc-logical-slot-register-bits-access.patch
new file mode 100644
index 0000000000000..36d0a499060f6
--- /dev/null
+++ b/pci/shpc-cleanup-shpc-logical-slot-register-bits-access.patch
@@ -0,0 +1,299 @@
+From kaneshige.kenji@jp.fujitsu.com Mon May 1 19:13:04 2006
+Message-ID: <4456BF9D.6090608@jp.fujitsu.com>
+Date: Tue, 02 May 2006 11:10:37 +0900
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: Greg KH <gregkh@suse.de>, Kristen Accardi <kristen.c.accardi@intel.com>
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: SHPC: Cleanup SHPC Logical Slot Register bits access
+
+This patch cleans up the code to access bits in slot logical
+registers. This patch has no functional change.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/shpchp_hpc.c | 151 ++++++++++++++++-----------------------
+ 1 file changed, 64 insertions(+), 87 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_hpc.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_hpc.c
+@@ -95,43 +95,40 @@
+ */
+ #define SLOT_REG(i) (SLOT1 + (4 * i))
+
+-/* Slot Status Field Definitions */
+-/* Slot State */
+-#define PWR_ONLY 0x0001
+-#define ENABLED 0x0002
+-#define DISABLED 0x0003
+-
+-/* Power Indicator State */
+-#define PWR_LED_ON 0x0004
+-#define PWR_LED_BLINK 0x0008
+-#define PWR_LED_OFF 0x000c
+-
+-/* Attention Indicator State */
+-#define ATTEN_LED_ON 0x0010
+-#define ATTEN_LED_BLINK 0x0020
+-#define ATTEN_LED_OFF 0x0030
+-
+-/* Power Fault */
+-#define pwr_fault 0x0040
+-
+-/* Attention Button */
+-#define ATTEN_BUTTON 0x0080
+-
+-/* MRL Sensor */
+-#define MRL_SENSOR 0x0100
+-
+-/* 66 MHz Capable */
+-#define IS_66MHZ_CAP 0x0200
+-
+-/* PRSNT1#/PRSNT2# */
+-#define SLOT_EMP 0x0c00
+-
+-/* PCI-X Capability */
+-#define NON_PCIX 0x0000
+-#define PCIX_66 0x1000
+-#define PCIX_133 0x3000
+-#define PCIX_266 0x4000 /* For PI = 2 only */
+-#define PCIX_533 0x5000 /* For PI = 2 only */
++#define SLOT_STATE_SHIFT (0)
++#define SLOT_STATE_MASK (3 << 0)
++#define SLOT_STATE_PWRONLY (1)
++#define SLOT_STATE_ENABLED (2)
++#define SLOT_STATE_DISABLED (3)
++#define PWR_LED_STATE_SHIFT (2)
++#define PWR_LED_STATE_MASK (3 << 2)
++#define ATN_LED_STATE_SHIFT (4)
++#define ATN_LED_STATE_MASK (3 << 4)
++#define ATN_LED_STATE_ON (1)
++#define ATN_LED_STATE_BLINK (2)
++#define ATN_LED_STATE_OFF (3)
++#define POWER_FAULT (1 << 6)
++#define ATN_BUTTON (1 << 7)
++#define MRL_SENSOR (1 << 8)
++#define MHZ66_CAP (1 << 9)
++#define PRSNT_SHIFT (10)
++#define PRSNT_MASK (3 << 10)
++#define PCIX_CAP_SHIFT (12)
++#define PCIX_CAP_MASK_PI1 (3 << 12)
++#define PCIX_CAP_MASK_PI2 (7 << 12)
++#define PRSNT_CHANGE_DETECTED (1 << 16)
++#define ISO_PFAULT_DETECTED (1 << 17)
++#define BUTTON_PRESS_DETECTED (1 << 18)
++#define MRL_CHANGE_DETECTED (1 << 19)
++#define CON_PFAULT_DETECTED (1 << 20)
++#define PRSNT_CHANGE_INTR_MASK (1 << 24)
++#define ISO_PFAULT_INTR_MASK (1 << 25)
++#define BUTTON_PRESS_INTR_MASK (1 << 26)
++#define MRL_CHANGE_INTR_MASK (1 << 27)
++#define CON_PFAULT_INTR_MASK (1 << 28)
++#define MRL_CHANGE_SERR_MASK (1 << 29)
++#define CON_PFAULT_SERR_MASK (1 << 30)
++#define SLOT_REG_RSVDZ_MASK (1 << 15) | (7 << 21)
+
+ /* SHPC 'write' operations/commands */
+
+@@ -428,8 +425,7 @@ static int hpc_get_attention_status(stru
+ {
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+- u16 slot_status;
+- u8 atten_led_state;
++ u8 state;
+
+ DBG_ENTER_ROUTINE
+
+@@ -439,24 +435,20 @@ static int hpc_get_attention_status(stru
+ }
+
+ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- slot_status = (u16) slot_reg;
+- atten_led_state = (slot_status & 0x0030) >> 4;
++ state = (slot_reg & ATN_LED_STATE_MASK) >> ATN_LED_STATE_SHIFT;
+
+- switch (atten_led_state) {
+- case 0:
+- *status = 0xFF; /* Reserved */
+- break;
+- case 1:
++ switch (state) {
++ case ATN_LED_STATE_ON:
+ *status = 1; /* On */
+ break;
+- case 2:
++ case ATN_LED_STATE_BLINK:
+ *status = 2; /* Blink */
+ break;
+- case 3:
++ case ATN_LED_STATE_OFF:
+ *status = 0; /* Off */
+ break;
+ default:
+- *status = 0xFF;
++ *status = 0xFF; /* Reserved */
+ break;
+ }
+
+@@ -468,9 +460,7 @@ static int hpc_get_power_status(struct s
+ {
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+- u16 slot_status;
+- u8 slot_state;
+- int retval = 0;
++ u8 state;
+
+ DBG_ENTER_ROUTINE
+
+@@ -480,29 +470,25 @@ static int hpc_get_power_status(struct s
+ }
+
+ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- slot_status = (u16) slot_reg;
+- slot_state = (slot_status & 0x0003);
++ state = (slot_reg & SLOT_STATE_MASK) >> SLOT_STATE_SHIFT;
+
+- switch (slot_state) {
+- case 0:
+- *status = 0xFF;
+- break;
+- case 1:
++ switch (state) {
++ case SLOT_STATE_PWRONLY:
+ *status = 2; /* Powered only */
+ break;
+- case 2:
++ case SLOT_STATE_ENABLED:
+ *status = 1; /* Enabled */
+ break;
+- case 3:
++ case SLOT_STATE_DISABLED:
+ *status = 0; /* Disabled */
+ break;
+ default:
+- *status = 0xFF;
++ *status = 0xFF; /* Reserved */
+ break;
+ }
+
+ DBG_LEAVE_ROUTINE
+- return retval;
++ return 0;
+ }
+
+
+@@ -510,7 +496,6 @@ static int hpc_get_latch_status(struct s
+ {
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+- u16 slot_status;
+
+ DBG_ENTER_ROUTINE
+
+@@ -520,10 +505,7 @@ static int hpc_get_latch_status(struct s
+ }
+
+ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- slot_status = (u16)slot_reg;
+-
+- *status = ((slot_status & 0x0100) == 0) ? 0 : 1; /* 0 -> close; 1 -> open */
+-
++ *status = !!(slot_reg & MRL_SENSOR); /* 0 -> close; 1 -> open */
+
+ DBG_LEAVE_ROUTINE
+ return 0;
+@@ -533,8 +515,7 @@ static int hpc_get_adapter_status(struct
+ {
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+- u16 slot_status;
+- u8 card_state;
++ u8 state;
+
+ DBG_ENTER_ROUTINE
+
+@@ -544,9 +525,8 @@ static int hpc_get_adapter_status(struct
+ }
+
+ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- slot_status = (u16)slot_reg;
+- card_state = (u8)((slot_status & 0x0C00) >> 10);
+- *status = (card_state != 0x3) ? 1 : 0;
++ state = (slot_reg & PRSNT_MASK) >> PRSNT_SHIFT;
++ *status = (state != 0x3) ? 1 : 0;
+
+ DBG_LEAVE_ROUTINE
+ return 0;
+@@ -574,8 +554,8 @@ static int hpc_get_adapter_speed(struct
+ int retval = 0;
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- u8 pcix_cap = (slot_reg >> 12) & 7;
+- u8 m66_cap = (slot_reg >> 9) & 1;
++ u8 pcix_cap = (slot_reg & PCIX_CAP_MASK_PI2) >> PCIX_CAP_SHIFT;
++ u8 m66_cap = !!(slot_reg & MHZ66_CAP);
+
+ DBG_ENTER_ROUTINE
+
+@@ -643,8 +623,6 @@ static int hpc_query_power_fault(struct
+ {
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+- u16 slot_status;
+- u8 pwr_fault_state, status;
+
+ DBG_ENTER_ROUTINE
+
+@@ -654,13 +632,10 @@ static int hpc_query_power_fault(struct
+ }
+
+ slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- slot_status = (u16) slot_reg;
+- pwr_fault_state = (slot_status & 0x0040) >> 7;
+- status = (pwr_fault_state == 1) ? 0 : 1;
+
+ DBG_LEAVE_ROUTINE
+ /* Note: Logic 0 => fault */
+- return status;
++ return !(slot_reg & POWER_FAULT);
+ }
+
+ static int hpc_set_attention_status(struct slot *slot, u8 value)
+@@ -1019,7 +994,6 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ struct controller *ctrl = NULL;
+ struct php_ctlr_state_s *php_ctlr;
+ u8 schedule_flag = 0;
+- u8 temp_byte;
+ u32 temp_dword, intr_loc, intr_loc2;
+ int hp_slot;
+
+@@ -1080,17 +1054,20 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ temp_dword = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Slot %x with intr, slot register = %x\n",
+ __FUNCTION__, hp_slot, temp_dword);
+- temp_byte = (temp_dword >> 16) & 0xFF;
+- if ((php_ctlr->switch_change_callback) && (temp_byte & 0x08))
++ if ((php_ctlr->switch_change_callback) &&
++ (temp_dword & MRL_CHANGE_DETECTED))
+ schedule_flag += php_ctlr->switch_change_callback(
+ hp_slot, php_ctlr->callback_instance_id);
+- if ((php_ctlr->attention_button_callback) && (temp_byte & 0x04))
++ if ((php_ctlr->attention_button_callback) &&
++ (temp_dword & BUTTON_PRESS_DETECTED))
+ schedule_flag += php_ctlr->attention_button_callback(
+ hp_slot, php_ctlr->callback_instance_id);
+- if ((php_ctlr->presence_change_callback) && (temp_byte & 0x01))
++ if ((php_ctlr->presence_change_callback) &&
++ (temp_dword & PRSNT_CHANGE_DETECTED))
+ schedule_flag += php_ctlr->presence_change_callback(
+ hp_slot , php_ctlr->callback_instance_id);
+- if ((php_ctlr->power_fault_callback) && (temp_byte & 0x12))
++ if ((php_ctlr->power_fault_callback) &&
++ (temp_dword & (ISO_PFAULT_DETECTED | CON_PFAULT_DETECTED)))
+ schedule_flag += php_ctlr->power_fault_callback(
+ hp_slot, php_ctlr->callback_instance_id);
+
diff --git a/pci/shpc-cleanup-shpc-register-access.patch b/pci/shpc-cleanup-shpc-register-access.patch
new file mode 100644
index 0000000000000..e5d200d0c3962
--- /dev/null
+++ b/pci/shpc-cleanup-shpc-register-access.patch
@@ -0,0 +1,536 @@
+From kaneshige.kenji@jp.fujitsu.com Mon May 1 19:11:17 2006
+Message-ID: <4456BF2A.40304@jp.fujitsu.com>
+Date: Tue, 02 May 2006 11:08:42 +0900
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: Greg KH <gregkh@suse.de>, Kristen Accardi <kristen.c.accardi@intel.com>,
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: SHPC: Cleanup SHPC register access
+
+This patch cleans up the code to access SHPC working register
+sets. This patch has no functional changes.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/shpchp_hpc.c | 192 ++++++++++++++++++++++-----------------
+ 1 file changed, 112 insertions(+), 80 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_hpc.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_hpc.c
+@@ -208,6 +208,49 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ static void start_int_poll_timer(struct php_ctlr_state_s *php_ctlr, int seconds);
+ static int hpc_check_cmd_status(struct controller *ctrl);
+
++static inline u8 shpc_readb(struct controller *ctrl, int reg)
++{
++ return readb(ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline void shpc_writeb(struct controller *ctrl, int reg, u8 val)
++{
++ writeb(val, ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline u16 shpc_readw(struct controller *ctrl, int reg)
++{
++ return readw(ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline void shpc_writew(struct controller *ctrl, int reg, u16 val)
++{
++ writew(val, ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline u32 shpc_readl(struct controller *ctrl, int reg)
++{
++ return readl(ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline void shpc_writel(struct controller *ctrl, int reg, u32 val)
++{
++ writel(val, ctrl->hpc_ctlr_handle->creg + reg);
++}
++
++static inline int shpc_indirect_read(struct controller *ctrl, int index,
++ u32 *value)
++{
++ int rc;
++ u32 cap_offset = ctrl->cap_offset;
++ struct pci_dev *pdev = ctrl->pci_dev;
++
++ rc = pci_write_config_byte(pdev, cap_offset + DWORD_SELECT, index);
++ if (rc)
++ return rc;
++ return pci_read_config_dword(pdev, cap_offset + DWORD_DATA, value);
++}
++
+ /* This is the interrupt polling timeout function. */
+ static void int_poll_timeout(unsigned long lphp_ctlr)
+ {
+@@ -273,6 +316,7 @@ static inline int shpc_wait_cmd(struct c
+ static int shpc_write_cmd(struct slot *slot, u8 t_slot, u8 cmd)
+ {
+ struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u16 cmd_status;
+ int retval = 0;
+ u16 temp_word;
+@@ -289,7 +333,7 @@ static int shpc_write_cmd(struct slot *s
+ }
+
+ for (i = 0; i < 10; i++) {
+- cmd_status = readw(php_ctlr->creg + CMD_STATUS);
++ cmd_status = shpc_readw(ctrl, CMD_STATUS);
+
+ if (!(cmd_status & 0x1))
+ break;
+@@ -297,7 +341,7 @@ static int shpc_write_cmd(struct slot *s
+ msleep(100);
+ }
+
+- cmd_status = readw(php_ctlr->creg + CMD_STATUS);
++ cmd_status = shpc_readw(ctrl, CMD_STATUS);
+
+ if (cmd_status & 0x1) {
+ /* After 1 sec and and the controller is still busy */
+@@ -314,7 +358,7 @@ static int shpc_write_cmd(struct slot *s
+ * command.
+ */
+ slot->ctrl->cmd_busy = 1;
+- writew(temp_word, php_ctlr->creg + CMD);
++ shpc_writew(ctrl, CMD, temp_word);
+
+ /*
+ * Wait for command completion.
+@@ -338,7 +382,6 @@ static int shpc_write_cmd(struct slot *s
+
+ static int hpc_check_cmd_status(struct controller *ctrl)
+ {
+- struct php_ctlr_state_s *php_ctlr = ctrl->hpc_ctlr_handle;
+ u16 cmd_status;
+ int retval = 0;
+
+@@ -349,7 +392,7 @@ static int hpc_check_cmd_status(struct c
+ return -1;
+ }
+
+- cmd_status = readw(php_ctlr->creg + CMD_STATUS) & 0x000F;
++ cmd_status = shpc_readw(ctrl, CMD_STATUS) & 0x000F;
+
+ switch (cmd_status >> 1) {
+ case 0:
+@@ -378,7 +421,7 @@ static int hpc_check_cmd_status(struct c
+
+ static int hpc_get_attention_status(struct slot *slot, u8 *status)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+ u16 slot_status;
+ u8 atten_led_state;
+@@ -390,7 +433,7 @@ static int hpc_get_attention_status(stru
+ return -1;
+ }
+
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ atten_led_state = (slot_status & 0x0030) >> 4;
+
+@@ -418,7 +461,7 @@ static int hpc_get_attention_status(stru
+
+ static int hpc_get_power_status(struct slot * slot, u8 *status)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+ u16 slot_status;
+ u8 slot_state;
+@@ -431,7 +474,7 @@ static int hpc_get_power_status(struct s
+ return -1;
+ }
+
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ slot_state = (slot_status & 0x0003);
+
+@@ -460,7 +503,7 @@ static int hpc_get_power_status(struct s
+
+ static int hpc_get_latch_status(struct slot *slot, u8 *status)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+ u16 slot_status;
+
+@@ -471,7 +514,7 @@ static int hpc_get_latch_status(struct s
+ return -1;
+ }
+
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
+ slot_status = (u16)slot_reg;
+
+ *status = ((slot_status & 0x0100) == 0) ? 0 : 1; /* 0 -> close; 1 -> open */
+@@ -483,7 +526,7 @@ static int hpc_get_latch_status(struct s
+
+ static int hpc_get_adapter_status(struct slot *slot, u8 *status)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+ u16 slot_status;
+ u8 card_state;
+@@ -495,7 +538,7 @@ static int hpc_get_adapter_status(struct
+ return -1;
+ }
+
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
+ slot_status = (u16)slot_reg;
+ card_state = (u8)((slot_status & 0x0C00) >> 10);
+ *status = (card_state != 0x3) ? 1 : 0;
+@@ -506,7 +549,7 @@ static int hpc_get_adapter_status(struct
+
+ static int hpc_get_prog_int(struct slot *slot, u8 *prog_int)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+
+ DBG_ENTER_ROUTINE
+
+@@ -515,7 +558,7 @@ static int hpc_get_prog_int(struct slot
+ return -1;
+ }
+
+- *prog_int = readb(php_ctlr->creg + PROG_INTERFACE);
++ *prog_int = shpc_readb(ctrl, PROG_INTERFACE);
+
+ DBG_LEAVE_ROUTINE
+ return 0;
+@@ -524,8 +567,8 @@ static int hpc_get_prog_int(struct slot
+ static int hpc_get_adapter_speed(struct slot *slot, enum pci_bus_speed *value)
+ {
+ int retval = 0;
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
+- u32 slot_reg = readl(php_ctlr->creg + SLOT1 + 4 * slot->hp_slot);
++ struct controller *ctrl = slot->ctrl;
++ u32 slot_reg = shpc_readl(ctrl, SLOT1 + 4 * slot->hp_slot);
+ u8 pcix_cap = (slot_reg >> 12) & 7;
+ u8 m66_cap = (slot_reg >> 9) & 1;
+
+@@ -564,7 +607,7 @@ static int hpc_get_adapter_speed(struct
+
+ static int hpc_get_mode1_ECC_cap(struct slot *slot, u8 *mode)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u16 sec_bus_status;
+ u8 pi;
+ int retval = 0;
+@@ -576,8 +619,8 @@ static int hpc_get_mode1_ECC_cap(struct
+ return -1;
+ }
+
+- pi = readb(php_ctlr->creg + PROG_INTERFACE);
+- sec_bus_status = readw(php_ctlr->creg + SEC_BUS_CONFIG);
++ pi = shpc_readb(ctrl, PROG_INTERFACE);
++ sec_bus_status = shpc_readw(ctrl, SEC_BUS_CONFIG);
+
+ if (pi == 2) {
+ *mode = (sec_bus_status & 0x0100) >> 8;
+@@ -593,7 +636,7 @@ static int hpc_get_mode1_ECC_cap(struct
+
+ static int hpc_query_power_fault(struct slot * slot)
+ {
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg;
+ u16 slot_status;
+ u8 pwr_fault_state, status;
+@@ -605,7 +648,7 @@ static int hpc_query_power_fault(struct
+ return -1;
+ }
+
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*(slot->hp_slot));
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*(slot->hp_slot));
+ slot_status = (u16) slot_reg;
+ pwr_fault_state = (slot_status & 0x0040) >> 7;
+ status = (pwr_fault_state == 1) ? 0 : 1;
+@@ -724,7 +767,7 @@ int shpc_get_ctlr_slot_config(struct con
+ int *updown, /* physical_slot_num increament: 1 or -1 */
+ int *flags)
+ {
+- struct php_ctlr_state_s *php_ctlr = ctrl->hpc_ctlr_handle;
++ u32 slot_config;
+
+ DBG_ENTER_ROUTINE
+
+@@ -733,12 +776,13 @@ int shpc_get_ctlr_slot_config(struct con
+ return -1;
+ }
+
+- *first_device_num = php_ctlr->slot_device_offset; /* Obtained in shpc_init() */
+- *num_ctlr_slots = php_ctlr->num_slots; /* Obtained in shpc_init() */
++ slot_config = shpc_readl(ctrl, SLOT_CONFIG);
++ *first_device_num = (slot_config & FIRST_DEV_NUM) >> 8;
++ *num_ctlr_slots = slot_config & SLOT_NUM;
++ *physical_slot_num = (slot_config & PSN) >> 16;
++ *updown = ((slot_config & UPDOWN) >> 29) ? 1 : -1;
+
+- *physical_slot_num = (readl(php_ctlr->creg + SLOT_CONFIG) & PSN) >> 16;
+ dbg("%s: physical_slot_num = %x\n", __FUNCTION__, *physical_slot_num);
+- *updown = ((readl(php_ctlr->creg + SLOT_CONFIG) & UPDOWN ) >> 29) ? 1 : -1;
+
+ DBG_LEAVE_ROUTINE
+ return 0;
+@@ -761,7 +805,7 @@ static void hpc_release_ctlr(struct cont
+ * Mask all slot event interrupts
+ */
+ for (i = 0; i < ctrl->num_slots; i++)
+- writel(0xffff3fff, php_ctlr->creg + SLOT1 + (4 * i));
++ shpc_writel(ctrl, SLOT1 + (4 * i), 0xffff3fff);
+
+ cleanup_slots(ctrl);
+
+@@ -901,12 +945,12 @@ static int hpc_slot_disable(struct slot
+ static int hpc_set_bus_speed_mode(struct slot * slot, enum pci_bus_speed value)
+ {
+ int retval;
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ u8 pi, cmd;
+
+ DBG_ENTER_ROUTINE
+
+- pi = readb(php_ctlr->creg + PROG_INTERFACE);
++ pi = shpc_readb(ctrl, PROG_INTERFACE);
+ if ((pi == 1) && (value > PCI_SPEED_133MHz_PCIX))
+ return -EINVAL;
+
+@@ -992,7 +1036,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ return IRQ_NONE;
+
+ /* Check to see if it was our interrupt */
+- intr_loc = readl(php_ctlr->creg + INTR_LOC);
++ intr_loc = shpc_readl(ctrl, INTR_LOC);
+
+ if (!intr_loc)
+ return IRQ_NONE;
+@@ -1001,11 +1045,11 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ if(!shpchp_poll_mode) {
+ /* Mask Global Interrupt Mask - see implementation note on p. 139 */
+ /* of SHPC spec rev 1.0*/
+- temp_dword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ temp_dword |= 0x00000001;
+- writel(temp_dword, php_ctlr->creg + SERR_INTR_ENABLE);
++ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+
+- intr_loc2 = readl(php_ctlr->creg + INTR_LOC);
++ intr_loc2 = shpc_readl(ctrl, INTR_LOC);
+ dbg("%s: intr_loc2 = %x\n",__FUNCTION__, intr_loc2);
+ }
+
+@@ -1015,9 +1059,9 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ * RO only - clear by writing 1 to the Command Completion
+ * Detect bit in Controller SERR-INT register
+ */
+- temp_dword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ temp_dword &= 0xfffdffff;
+- writel(temp_dword, php_ctlr->creg + SERR_INTR_ENABLE);
++ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+ ctrl->cmd_busy = 0;
+ wake_up_interruptible(&ctrl->queue);
+ }
+@@ -1028,7 +1072,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ for (hp_slot = 0; hp_slot < ctrl->num_slots; hp_slot++) {
+ /* To find out which slot has interrupt pending */
+ if ((intr_loc >> hp_slot) & 0x01) {
+- temp_dword = readl(php_ctlr->creg + SLOT1 + (4*hp_slot));
++ temp_dword = shpc_readl(ctrl, SLOT1 + (4*hp_slot));
+ dbg("%s: Slot %x with intr, slot register = %x\n",
+ __FUNCTION__, hp_slot, temp_dword);
+ temp_byte = (temp_dword >> 16) & 0xFF;
+@@ -1047,18 +1091,18 @@ static irqreturn_t shpc_isr(int IRQ, voi
+
+ /* Clear all slot events */
+ temp_dword = 0xe01f3fff;
+- writel(temp_dword, php_ctlr->creg + SLOT1 + (4*hp_slot));
++ shpc_writel(ctrl, SLOT1 + (4*hp_slot), temp_dword);
+
+- intr_loc2 = readl(php_ctlr->creg + INTR_LOC);
++ intr_loc2 = shpc_readl(ctrl, INTR_LOC);
+ dbg("%s: intr_loc2 = %x\n",__FUNCTION__, intr_loc2);
+ }
+ }
+ out:
+ if (!shpchp_poll_mode) {
+ /* Unmask Global Interrupt Mask */
+- temp_dword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ temp_dword &= 0xfffffffe;
+- writel(temp_dword, php_ctlr->creg + SERR_INTR_ENABLE);
++ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+ }
+
+ return IRQ_HANDLED;
+@@ -1067,11 +1111,11 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ static int hpc_get_max_bus_speed (struct slot *slot, enum pci_bus_speed *value)
+ {
+ int retval = 0;
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ enum pci_bus_speed bus_speed = PCI_SPEED_UNKNOWN;
+- u8 pi = readb(php_ctlr->creg + PROG_INTERFACE);
+- u32 slot_avail1 = readl(php_ctlr->creg + SLOT_AVAIL1);
+- u32 slot_avail2 = readl(php_ctlr->creg + SLOT_AVAIL2);
++ u8 pi = shpc_readb(ctrl, PROG_INTERFACE);
++ u32 slot_avail1 = shpc_readl(ctrl, SLOT_AVAIL1);
++ u32 slot_avail2 = shpc_readl(ctrl, SLOT_AVAIL2);
+
+ DBG_ENTER_ROUTINE
+
+@@ -1114,10 +1158,10 @@ static int hpc_get_max_bus_speed (struct
+ static int hpc_get_cur_bus_speed (struct slot *slot, enum pci_bus_speed *value)
+ {
+ int retval = 0;
+- struct php_ctlr_state_s *php_ctlr = slot->ctrl->hpc_ctlr_handle;
++ struct controller *ctrl = slot->ctrl;
+ enum pci_bus_speed bus_speed = PCI_SPEED_UNKNOWN;
+- u16 sec_bus_reg = readw(php_ctlr->creg + SEC_BUS_CONFIG);
+- u8 pi = readb(php_ctlr->creg + PROG_INTERFACE);
++ u16 sec_bus_reg = shpc_readw(ctrl, SEC_BUS_CONFIG);
++ u8 pi = shpc_readb(ctrl, PROG_INTERFACE);
+ u8 speed_mode = (pi == 2) ? (sec_bus_reg & 0xF) : (sec_bus_reg & 0x7);
+
+ DBG_ENTER_ROUTINE
+@@ -1206,19 +1250,6 @@ static struct hpc_ops shpchp_hpc_ops = {
+ .release_ctlr = hpc_release_ctlr,
+ };
+
+-inline static int shpc_indirect_creg_read(struct controller *ctrl, int index,
+- u32 *value)
+-{
+- int rc;
+- u32 cap_offset = ctrl->cap_offset;
+- struct pci_dev *pdev = ctrl->pci_dev;
+-
+- rc = pci_write_config_byte(pdev, cap_offset + DWORD_SELECT, index);
+- if (rc)
+- return rc;
+- return pci_read_config_dword(pdev, cap_offset + DWORD_DATA, value);
+-}
+-
+ int shpc_init(struct controller * ctrl, struct pci_dev * pdev)
+ {
+ struct php_ctlr_state_s *php_ctlr, *p;
+@@ -1227,7 +1258,7 @@ int shpc_init(struct controller * ctrl,
+ u8 hp_slot;
+ static int first = 1;
+ u32 shpc_base_offset;
+- u32 tempdword, slot_reg;
++ u32 tempdword, slot_reg, slot_config;
+ u8 i;
+
+ DBG_ENTER_ROUTINE
+@@ -1257,13 +1288,13 @@ int shpc_init(struct controller * ctrl,
+ }
+ dbg("%s: cap_offset = %x\n", __FUNCTION__, ctrl->cap_offset);
+
+- rc = shpc_indirect_creg_read(ctrl, 0, &shpc_base_offset);
++ rc = shpc_indirect_read(ctrl, 0, &shpc_base_offset);
+ if (rc) {
+ err("%s: cannot read base_offset\n", __FUNCTION__);
+ goto abort_free_ctlr;
+ }
+
+- rc = shpc_indirect_creg_read(ctrl, 3, &tempdword);
++ rc = shpc_indirect_read(ctrl, 3, &tempdword);
+ if (rc) {
+ err("%s: cannot read slot config\n", __FUNCTION__);
+ goto abort_free_ctlr;
+@@ -1272,7 +1303,7 @@ int shpc_init(struct controller * ctrl,
+ dbg("%s: num_slots (indirect) %x\n", __FUNCTION__, num_slots);
+
+ for (i = 0; i < 9 + num_slots; i++) {
+- rc = shpc_indirect_creg_read(ctrl, i, &tempdword);
++ rc = shpc_indirect_read(ctrl, i, &tempdword);
+ if (rc) {
+ err("%s: cannot read creg (index = %d)\n",
+ __FUNCTION__, i);
+@@ -1326,29 +1357,33 @@ int shpc_init(struct controller * ctrl,
+ php_ctlr->power_fault_callback = shpchp_handle_power_fault;
+ php_ctlr->callback_instance_id = instance_id;
+
++ ctrl->hpc_ctlr_handle = php_ctlr;
++ ctrl->hpc_ops = &shpchp_hpc_ops;
++
+ /* Return PCI Controller Info */
+- php_ctlr->slot_device_offset = (readl(php_ctlr->creg + SLOT_CONFIG) & FIRST_DEV_NUM ) >> 8;
+- php_ctlr->num_slots = readl(php_ctlr->creg + SLOT_CONFIG) & SLOT_NUM;
++ slot_config = shpc_readl(ctrl, SLOT_CONFIG);
++ php_ctlr->slot_device_offset = (slot_config & FIRST_DEV_NUM) >> 8;
++ php_ctlr->num_slots = slot_config & SLOT_NUM;
+ dbg("%s: slot_device_offset %x\n", __FUNCTION__, php_ctlr->slot_device_offset);
+ dbg("%s: num_slots %x\n", __FUNCTION__, php_ctlr->num_slots);
+
+ /* Mask Global Interrupt Mask & Command Complete Interrupt Mask */
+- tempdword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
+ tempdword = 0x0003000f;
+- writel(tempdword, php_ctlr->creg + SERR_INTR_ENABLE);
+- tempdword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ shpc_writel(ctrl, SERR_INTR_ENABLE, tempdword);
++ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
+
+ /* Mask the MRL sensor SERR Mask of individual slot in
+ * Slot SERR-INT Mask & clear all the existing event if any
+ */
+ for (hp_slot = 0; hp_slot < php_ctlr->num_slots; hp_slot++) {
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*hp_slot );
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*hp_slot );
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+ tempdword = 0xffff3fff;
+- writel(tempdword, php_ctlr->creg + SLOT1 + (4*hp_slot));
++ shpc_writel(ctrl, SLOT1 + (4*hp_slot), tempdword);
+ }
+
+ if (shpchp_poll_mode) {/* Install interrupt polling code */
+@@ -1392,24 +1427,21 @@ int shpc_init(struct controller * ctrl,
+ }
+ spin_unlock(&list_lock);
+
+-
+ ctlr_seq_num++;
+- ctrl->hpc_ctlr_handle = php_ctlr;
+- ctrl->hpc_ops = &shpchp_hpc_ops;
+
+ for (hp_slot = 0; hp_slot < php_ctlr->num_slots; hp_slot++) {
+- slot_reg = readl(php_ctlr->creg + SLOT1 + 4*hp_slot );
++ slot_reg = shpc_readl(ctrl, SLOT1 + 4*hp_slot );
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+ tempdword = 0xe01f3fff;
+- writel(tempdword, php_ctlr->creg + SLOT1 + (4*hp_slot));
++ shpc_writel(ctrl, SLOT1 + (4*hp_slot), tempdword);
+ }
+ if (!shpchp_poll_mode) {
+ /* Unmask all general input interrupts and SERR */
+- tempdword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ tempdword = 0x0000000a;
+- writel(tempdword, php_ctlr->creg + SERR_INTR_ENABLE);
+- tempdword = readl(php_ctlr->creg + SERR_INTR_ENABLE);
++ shpc_writel(ctrl, SERR_INTR_ENABLE, tempdword);
++ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
+ }
+
diff --git a/pci/shpc-fix-shpc-contoller-serr-int-register-bits-access.patch b/pci/shpc-fix-shpc-contoller-serr-int-register-bits-access.patch
new file mode 100644
index 0000000000000..0e17888ae884f
--- /dev/null
+++ b/pci/shpc-fix-shpc-contoller-serr-int-register-bits-access.patch
@@ -0,0 +1,115 @@
+From kaneshige.kenji@jp.fujitsu.com Mon May 1 19:15:35 2006
+Message-ID: <4456C015.7080604@jp.fujitsu.com>
+Date: Tue, 02 May 2006 11:12:37 +0900
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: Greg KH <gregkh@suse.de>, Kristen Accardi <kristen.c.accardi@intel.com>
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: SHPC: Fix SHPC Contoller SERR-INT Register bits access
+
+Current SHPCHP driver doesn't take care of RsvdP/RsvdZ[*] bits in
+controller SERR-INT register. This might cause unpredicable
+results. This patch fixes this bug.
+
+[*] RsvdP and RsvdZ are defined in SHPC spec as follows:
+
+ RsvdP - Reserved and Preserved. Register bits of this type are
+ reserved for future use as R/W bits. The value read is
+ undefined. Writes are ignored. Software must follow These rules
+ when accessing RsvdP bits:
+
+ - Software must ignore RsvdP bits when testing values read
+ from these registers.
+ - Software must not depend on RsvdP bit's ability to retain
+ information when written
+ - Software must always write back the value read in the RsvdP
+ bits when writing one of these registers.
+
+ RsvdZ - Reserved and Zero. Register bits of this type are reserved
+ for future use as R/WC bits. The value read is undefined. Writes
+ are ignored. Software must follow these rules when accessing RsvdZ
+ bits:
+
+ - Software must ignore RsvdZ bits when testing values read
+ from these registers.
+ - Software must not depends on a RsvdZ bit's ability to retain
+ information when written.
+ - Software must always write 0 to RsvdZ bits when writing one
+ of these register.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/shpchp_hpc.c | 25 ++++++++++++++++++++-----
+ 1 file changed, 20 insertions(+), 5 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_hpc.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_hpc.c
+@@ -91,6 +91,17 @@
+ #define ATTN_BUTTON 0x80000000
+
+ /*
++ * Controller SERR-INT Register
++ */
++#define GLOBAL_INTR_MASK (1 << 0)
++#define GLOBAL_SERR_MASK (1 << 1)
++#define COMMAND_INTR_MASK (1 << 2)
++#define ARBITER_SERR_MASK (1 << 3)
++#define COMMAND_DETECTED (1 << 16)
++#define ARBITER_DETECTED (1 << 17)
++#define SERR_INTR_RSVDZ_MASK 0xfffc0000
++
++/*
+ * Logical Slot Register definitions
+ */
+ #define SLOT_REG(i) (SLOT1 + (4 * i))
+@@ -1047,7 +1058,8 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ /* Mask Global Interrupt Mask - see implementation note on p. 139 */
+ /* of SHPC spec rev 1.0*/
+ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+- temp_dword |= 0x00000001;
++ temp_dword |= GLOBAL_INTR_MASK;
++ temp_dword &= ~SERR_INTR_RSVDZ_MASK;
+ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+
+ intr_loc2 = shpc_readl(ctrl, INTR_LOC);
+@@ -1061,7 +1073,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ * Detect bit in Controller SERR-INT register
+ */
+ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+- temp_dword &= 0xfffdffff;
++ temp_dword &= ~SERR_INTR_RSVDZ_MASK;
+ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+ ctrl->cmd_busy = 0;
+ wake_up_interruptible(&ctrl->queue);
+@@ -1105,7 +1117,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ if (!shpchp_poll_mode) {
+ /* Unmask Global Interrupt Mask */
+ temp_dword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+- temp_dword &= 0xfffffffe;
++ temp_dword &= ~(GLOBAL_INTR_MASK | SERR_INTR_RSVDZ_MASK);
+ shpc_writel(ctrl, SERR_INTR_ENABLE, temp_dword);
+ }
+
+@@ -1374,7 +1386,9 @@ int shpc_init(struct controller * ctrl,
+ /* Mask Global Interrupt Mask & Command Complete Interrupt Mask */
+ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
+- tempdword = 0x0003000f;
++ tempdword |= (GLOBAL_INTR_MASK | GLOBAL_SERR_MASK |
++ COMMAND_INTR_MASK | ARBITER_SERR_MASK);
++ tempdword &= ~SERR_INTR_RSVDZ_MASK;
+ shpc_writel(ctrl, SERR_INTR_ENABLE, tempdword);
+ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
+@@ -1452,7 +1466,8 @@ int shpc_init(struct controller * ctrl,
+ if (!shpchp_poll_mode) {
+ /* Unmask all general input interrupts and SERR */
+ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+- tempdword = 0x0000000a;
++ tempdword &= ~(GLOBAL_INTR_MASK | COMMAND_INTR_MASK |
++ SERR_INTR_RSVDZ_MASK);
+ shpc_writel(ctrl, SERR_INTR_ENABLE, tempdword);
+ tempdword = shpc_readl(ctrl, SERR_INTR_ENABLE);
+ dbg("%s: SERR_INTR_ENABLE = %x\n", __FUNCTION__, tempdword);
diff --git a/pci/shpc-fix-shpc-logical-slot-register-bits-access.patch b/pci/shpc-fix-shpc-logical-slot-register-bits-access.patch
new file mode 100644
index 0000000000000..aa00b6717da66
--- /dev/null
+++ b/pci/shpc-fix-shpc-logical-slot-register-bits-access.patch
@@ -0,0 +1,148 @@
+From kaneshige.kenji@jp.fujitsu.com Mon May 1 19:14:15 2006
+Message-ID: <4456BFEA.4070008@jp.fujitsu.com>
+Date: Tue, 02 May 2006 11:11:54 +0900
+From: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+To: Greg KH <gregkh@suse.de>, Kristen Accardi <kristen.c.accardi@intel.com>
+Cc: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Subject: SHPC: Fix SHPC Logical Slot Register bits access
+
+Current SHPCHP driver doesn't take care of RsvdP/RsvdZ[*] bits
+in logical slot registers. This might cause unpredicable results. This
+patch fixes this bug.
+
+[*] RsvdP and RsvdZ are defined in SHPC spec as follows:
+
+ RsvdP - Reserved and Preserved. Register bits of this type are
+ reserved for future use as R/W bits. The value read is
+ undefined. Writes are ignored. Software must follow These rules
+ when accessing RsvdP bits:
+
+ - Software must ignore RsvdP bits when testing values read
+ from these registers.
+ - Software must not depend on RsvdP bit's ability to retain
+ information when written
+ - Software must always write back the value read in the RsvdP
+ bits when writing one of these registers.
+
+ RsvdZ - Reserved and Zero. Register bits of this type are reserved
+ for future use as R/WC bits. The value read is undefined. Writes
+ are ignored. Software must follow these rules when accessing RsvdZ
+ bits:
+
+ - Software must ignore RsvdZ bits when testing values read
+ from these registers.
+ - Software must not depends on a RsvdZ bit's ability to retain
+ information when written.
+ - Software must always write 0 to RsvdZ bits when writing one
+ of these register.
+
+Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
+Cc: Kristen Accardi <kristen.c.accardi@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/pci/hotplug/shpchp_hpc.c | 49 +++++++++++++++++++++++++++++++--------
+ 1 file changed, 40 insertions(+), 9 deletions(-)
+
+--- gregkh-2.6.orig/drivers/pci/hotplug/shpchp_hpc.c
++++ gregkh-2.6/drivers/pci/hotplug/shpchp_hpc.c
+@@ -554,11 +554,25 @@ static int hpc_get_adapter_speed(struct
+ int retval = 0;
+ struct controller *ctrl = slot->ctrl;
+ u32 slot_reg = shpc_readl(ctrl, SLOT_REG(slot->hp_slot));
+- u8 pcix_cap = (slot_reg & PCIX_CAP_MASK_PI2) >> PCIX_CAP_SHIFT;
+ u8 m66_cap = !!(slot_reg & MHZ66_CAP);
++ u8 pi, pcix_cap;
+
+ DBG_ENTER_ROUTINE
+
++ if ((retval = hpc_get_prog_int(slot, &pi)))
++ return retval;
++
++ switch (pi) {
++ case 1:
++ pcix_cap = (slot_reg & PCIX_CAP_MASK_PI1) >> PCIX_CAP_SHIFT;
++ break;
++ case 2:
++ pcix_cap = (slot_reg & PCIX_CAP_MASK_PI2) >> PCIX_CAP_SHIFT;
++ break;
++ default:
++ return -ENODEV;
++ }
++
+ dbg("%s: slot_reg = %x, pcix_cap = %x, m66_cap = %x\n",
+ __FUNCTION__, slot_reg, pcix_cap, m66_cap);
+
+@@ -773,6 +787,7 @@ static void hpc_release_ctlr(struct cont
+ struct php_ctlr_state_s *php_ctlr = ctrl->hpc_ctlr_handle;
+ struct php_ctlr_state_s *p, *p_prev;
+ int i;
++ u32 slot_reg;
+
+ DBG_ENTER_ROUTINE
+
+@@ -782,10 +797,17 @@ static void hpc_release_ctlr(struct cont
+ }
+
+ /*
+- * Mask all slot event interrupts
++ * Mask event interrupts and SERRs of all slots
+ */
+- for (i = 0; i < ctrl->num_slots; i++)
+- shpc_writel(ctrl, SLOT_REG(i), 0xffff3fff);
++ for (i = 0; i < ctrl->num_slots; i++) {
++ slot_reg = shpc_readl(ctrl, SLOT_REG(i));
++ slot_reg |= (PRSNT_CHANGE_INTR_MASK | ISO_PFAULT_INTR_MASK |
++ BUTTON_PRESS_INTR_MASK | MRL_CHANGE_INTR_MASK |
++ CON_PFAULT_INTR_MASK | MRL_CHANGE_SERR_MASK |
++ CON_PFAULT_SERR_MASK);
++ slot_reg &= ~SLOT_REG_RSVDZ_MASK;
++ shpc_writel(ctrl, SLOT_REG(i), slot_reg);
++ }
+
+ cleanup_slots(ctrl);
+
+@@ -1072,7 +1094,7 @@ static irqreturn_t shpc_isr(int IRQ, voi
+ hp_slot, php_ctlr->callback_instance_id);
+
+ /* Clear all slot events */
+- temp_dword = 0xe01f3fff;
++ temp_dword &= ~SLOT_REG_RSVDZ_MASK;
+ shpc_writel(ctrl, SLOT_REG(hp_slot), temp_dword);
+
+ intr_loc2 = shpc_readl(ctrl, INTR_LOC);
+@@ -1364,8 +1386,12 @@ int shpc_init(struct controller * ctrl,
+ slot_reg = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+- tempdword = 0xffff3fff;
+- shpc_writel(ctrl, SLOT_REG(hp_slot), tempdword);
++ slot_reg |= (PRSNT_CHANGE_INTR_MASK | ISO_PFAULT_INTR_MASK |
++ BUTTON_PRESS_INTR_MASK | MRL_CHANGE_INTR_MASK |
++ CON_PFAULT_INTR_MASK | MRL_CHANGE_SERR_MASK |
++ CON_PFAULT_SERR_MASK);
++ slot_reg &= ~SLOT_REG_RSVDZ_MASK;
++ shpc_writel(ctrl, SLOT_REG(hp_slot), slot_reg);
+ }
+
+ if (shpchp_poll_mode) {/* Install interrupt polling code */
+@@ -1411,12 +1437,17 @@ int shpc_init(struct controller * ctrl,
+
+ ctlr_seq_num++;
+
++ /*
++ * Unmask all event interrupts of all slots
++ */
+ for (hp_slot = 0; hp_slot < php_ctlr->num_slots; hp_slot++) {
+ slot_reg = shpc_readl(ctrl, SLOT_REG(hp_slot));
+ dbg("%s: Default Logical Slot Register %d value %x\n", __FUNCTION__,
+ hp_slot, slot_reg);
+- tempdword = 0xe01f3fff;
+- shpc_writel(ctrl, SLOT_REG(hp_slot), tempdword);
++ slot_reg &= ~(PRSNT_CHANGE_INTR_MASK | ISO_PFAULT_INTR_MASK |
++ BUTTON_PRESS_INTR_MASK | MRL_CHANGE_INTR_MASK |
++ CON_PFAULT_INTR_MASK | SLOT_REG_RSVDZ_MASK);
++ shpc_writel(ctrl, SLOT_REG(hp_slot), slot_reg);
+ }
+ if (!shpchp_poll_mode) {
+ /* Unmask all general input interrupts and SERR */