aboutsummaryrefslogtreecommitdiff
path: root/platforms
diff options
context:
space:
mode:
authorGavin Shan <gwshan@linux.vnet.ibm.com>2017-05-30 15:54:45 +1000
committerStewart Smith <stewart@linux.vnet.ibm.com>2017-06-16 14:38:46 +1000
commit7133ba8dac984763fc952bcdd1632d1da9a28bce (patch)
tree4b557cde80a542c3e4a580ca86f0d9e3333d97df /platforms
parentfe604732f58f76858e4517dfab1c8a13b4e83118 (diff)
downloadskiboot-7133ba8dac984763fc952bcdd1632d1da9a28bce.zip
skiboot-7133ba8dac984763fc952bcdd1632d1da9a28bce.tar.gz
skiboot-7133ba8dac984763fc952bcdd1632d1da9a28bce.tar.bz2
platforms/ibm-fsp/firenze: Refactor firenze_pci_setup_power_mgt()
This refactors firenze_pci_setup_power_mgt() and no logicial changes introduced: * Avoid nested if block; * Remove the local variable @buddy. The information is retrieved directly from struct firenze_pci_slot_info::buddy; * Comments to explain the fixed register offset (0x69) for slot's power control and shared power state between local slot and its buddy. Signed-off-by: Gavin Shan <gwshan@linux.vnet.ibm.com> Signed-off-by: Stewart Smith <stewart@linux.vnet.ibm.com>
Diffstat (limited to 'platforms')
-rw-r--r--platforms/ibm-fsp/firenze-pci.c79
1 files changed, 44 insertions, 35 deletions
diff --git a/platforms/ibm-fsp/firenze-pci.c b/platforms/ibm-fsp/firenze-pci.c
index b777956..3c193ed 100644
--- a/platforms/ibm-fsp/firenze-pci.c
+++ b/platforms/ibm-fsp/firenze-pci.c
@@ -817,45 +817,54 @@ static void firenze_pci_setup_power_mgt(struct pci_slot *slot,
struct firenze_pci_slot *plat_slot,
struct firenze_pci_slot_info *info)
{
- uint8_t buddy;
-
- buddy = info->buddy;
plat_slot->i2c_bus = firenze_pci_find_i2c_bus(info->chip_id,
info->master_id,
info->port_id);
- if (plat_slot->i2c_bus)
- plat_slot->req = i2c_alloc_req(plat_slot->i2c_bus);
- else
- plat_slot->req = NULL;
+ if (!plat_slot->i2c_bus)
+ return;
- if (plat_slot->req) {
- plat_slot->req->dev_addr = info->slave_addr;
- plat_slot->req->offset_bytes = 1;
- plat_slot->req->rw_buf = plat_slot->i2c_rw_buf;
- plat_slot->req->rw_len = 1;
- plat_slot->req->completion = firenze_i2c_req_done;
- plat_slot->req->user_data = slot;
- firenze_pci_slot_fixup(slot, info);
-
- plat_slot->req->offset = 0x69;
- switch (info->channel) {
- case 0:
- plat_slot->power_status = &firenze_pci_slots[buddy].power_status;
- plat_slot->power_mask = 0x33;
- plat_slot->power_on = 0x22;
- plat_slot->power_off = 0;
- break;
- case 1:
- plat_slot->power_status = &firenze_pci_slots[buddy].power_status;
- plat_slot->power_mask = 0xcc;
- plat_slot->power_on = 0x88;
- plat_slot->power_off = 0;
- break;
- default:
- prlog(PR_DEBUG, "%016llx: Invalid channel %d\n",
- slot->id, info->channel);
- plat_slot->i2c_bus = NULL;
- }
+ plat_slot->req = i2c_alloc_req(plat_slot->i2c_bus);
+ if (!plat_slot->req)
+ return;
+
+ plat_slot->req->dev_addr = info->slave_addr;
+ plat_slot->req->offset_bytes = 1;
+ plat_slot->req->rw_buf = plat_slot->i2c_rw_buf;
+ plat_slot->req->rw_len = 1;
+ plat_slot->req->completion = firenze_i2c_req_done;
+ plat_slot->req->user_data = slot;
+
+ firenze_pci_slot_fixup(slot, info);
+
+ /*
+ * For all slots, the register used to change the power state is
+ * always 0x69. It could have been set to something else in the
+ * above fixup. Lets fix it to 0x69 here.
+ *
+ * The power states of two slots are controlled by one register.
+ * This means two slots have to share data buffer for power states,
+ * which are tracked by struct firenze_pci_slot_info::power_status.
+ * With it, we can avoid affecting slot#B's power state when trying
+ * to adjust that on slot#A. Also, the initial power states for all
+ * slots are assumed to be PCI_SLOT_POWER_ON.
+ */
+ plat_slot->req->offset = 0x69;
+ plat_slot->power_status = &firenze_pci_slots[info->buddy].power_status;
+ switch (info->channel) {
+ case 0:
+ plat_slot->power_mask = 0x33;
+ plat_slot->power_on = 0x22;
+ plat_slot->power_off = 0;
+ break;
+ case 1:
+ plat_slot->power_status = &firenze_pci_slots[info->buddy].power_status;
+ plat_slot->power_mask = 0xcc;
+ plat_slot->power_on = 0x88;
+ plat_slot->power_off = 0;
+ break;
+ default:
+ prlog(PR_ERR, "%016llx: Invalid channel %d\n",
+ slot->id, info->channel);
}
}