diff options
Diffstat (limited to 'drivers/net')
| -rw-r--r-- | drivers/net/bnx2x.h | 4 | ||||
| -rw-r--r-- | drivers/net/bnx2x_main.c | 71 |
2 files changed, 73 insertions, 2 deletions
diff --git a/drivers/net/bnx2x.h b/drivers/net/bnx2x.h index ccef13b41dfa..694c8cd59e09 100644 --- a/drivers/net/bnx2x.h +++ b/drivers/net/bnx2x.h | |||
| @@ -1089,6 +1089,7 @@ struct bnx2x { | |||
| 1089 | #define INIT_CSEM_INT_TABLE_DATA(bp) (bp->csem_int_table_data) | 1089 | #define INIT_CSEM_INT_TABLE_DATA(bp) (bp->csem_int_table_data) |
| 1090 | #define INIT_CSEM_PRAM_DATA(bp) (bp->csem_pram_data) | 1090 | #define INIT_CSEM_PRAM_DATA(bp) (bp->csem_pram_data) |
| 1091 | 1091 | ||
| 1092 | char fw_ver[32]; | ||
| 1092 | const struct firmware *firmware; | 1093 | const struct firmware *firmware; |
| 1093 | }; | 1094 | }; |
| 1094 | 1095 | ||
| @@ -1352,6 +1353,9 @@ static inline u32 reg_poll(struct bnx2x *bp, u32 reg, u32 expected, int ms, | |||
| 1352 | #define PXP2_REG_PXP2_INT_STS PXP2_REG_PXP2_INT_STS_0 | 1353 | #define PXP2_REG_PXP2_INT_STS PXP2_REG_PXP2_INT_STS_0 |
| 1353 | #endif | 1354 | #endif |
| 1354 | 1355 | ||
| 1356 | #define BNX2X_VPD_LEN 128 | ||
| 1357 | #define VENDOR_ID_LEN 4 | ||
| 1358 | |||
| 1355 | /* MISC_REG_RESET_REG - this is here for the hsi to work don't touch */ | 1359 | /* MISC_REG_RESET_REG - this is here for the hsi to work don't touch */ |
| 1356 | 1360 | ||
| 1357 | #endif /* bnx2x.h */ | 1361 | #endif /* bnx2x.h */ |
diff --git a/drivers/net/bnx2x_main.c b/drivers/net/bnx2x_main.c index 2b6717748eb8..d0884862b96c 100644 --- a/drivers/net/bnx2x_main.c +++ b/drivers/net/bnx2x_main.c | |||
| @@ -9759,6 +9759,70 @@ static int __devinit bnx2x_get_hwinfo(struct bnx2x *bp) | |||
| 9759 | return rc; | 9759 | return rc; |
| 9760 | } | 9760 | } |
| 9761 | 9761 | ||
| 9762 | static void __devinit bnx2x_read_fwinfo(struct bnx2x *bp) | ||
| 9763 | { | ||
| 9764 | int cnt, i, block_end, rodi; | ||
| 9765 | char vpd_data[BNX2X_VPD_LEN+1]; | ||
| 9766 | char str_id_reg[VENDOR_ID_LEN+1]; | ||
| 9767 | char str_id_cap[VENDOR_ID_LEN+1]; | ||
| 9768 | u8 len; | ||
| 9769 | |||
| 9770 | cnt = pci_read_vpd(bp->pdev, 0, BNX2X_VPD_LEN, vpd_data); | ||
| 9771 | memset(bp->fw_ver, 0, sizeof(bp->fw_ver)); | ||
| 9772 | |||
| 9773 | if (cnt < BNX2X_VPD_LEN) | ||
| 9774 | goto out_not_found; | ||
| 9775 | |||
| 9776 | i = pci_vpd_find_tag(vpd_data, 0, BNX2X_VPD_LEN, | ||
| 9777 | PCI_VPD_LRDT_RO_DATA); | ||
| 9778 | if (i < 0) | ||
| 9779 | goto out_not_found; | ||
| 9780 | |||
| 9781 | |||
| 9782 | block_end = i + PCI_VPD_LRDT_TAG_SIZE + | ||
| 9783 | pci_vpd_lrdt_size(&vpd_data[i]); | ||
| 9784 | |||
| 9785 | i += PCI_VPD_LRDT_TAG_SIZE; | ||
| 9786 | |||
| 9787 | if (block_end > BNX2X_VPD_LEN) | ||
| 9788 | goto out_not_found; | ||
| 9789 | |||
| 9790 | rodi = pci_vpd_find_info_keyword(vpd_data, i, block_end, | ||
| 9791 | PCI_VPD_RO_KEYWORD_MFR_ID); | ||
| 9792 | if (rodi < 0) | ||
| 9793 | goto out_not_found; | ||
| 9794 | |||
| 9795 | len = pci_vpd_info_field_size(&vpd_data[rodi]); | ||
| 9796 | |||
| 9797 | if (len != VENDOR_ID_LEN) | ||
| 9798 | goto out_not_found; | ||
| 9799 | |||
| 9800 | rodi += PCI_VPD_INFO_FLD_HDR_SIZE; | ||
| 9801 | |||
| 9802 | /* vendor specific info */ | ||
| 9803 | snprintf(str_id_reg, VENDOR_ID_LEN + 1, "%04x", PCI_VENDOR_ID_DELL); | ||
| 9804 | snprintf(str_id_cap, VENDOR_ID_LEN + 1, "%04X", PCI_VENDOR_ID_DELL); | ||
| 9805 | if (!strncmp(str_id_reg, &vpd_data[rodi], VENDOR_ID_LEN) || | ||
| 9806 | !strncmp(str_id_cap, &vpd_data[rodi], VENDOR_ID_LEN)) { | ||
| 9807 | |||
| 9808 | rodi = pci_vpd_find_info_keyword(vpd_data, i, block_end, | ||
| 9809 | PCI_VPD_RO_KEYWORD_VENDOR0); | ||
| 9810 | if (rodi >= 0) { | ||
| 9811 | len = pci_vpd_info_field_size(&vpd_data[rodi]); | ||
| 9812 | |||
| 9813 | rodi += PCI_VPD_INFO_FLD_HDR_SIZE; | ||
| 9814 | |||
| 9815 | if (len < 32 && (len + rodi) <= BNX2X_VPD_LEN) { | ||
| 9816 | memcpy(bp->fw_ver, &vpd_data[rodi], len); | ||
| 9817 | bp->fw_ver[len] = ' '; | ||
| 9818 | } | ||
| 9819 | } | ||
| 9820 | return; | ||
| 9821 | } | ||
| 9822 | out_not_found: | ||
| 9823 | return; | ||
| 9824 | } | ||
| 9825 | |||
| 9762 | static int __devinit bnx2x_init_bp(struct bnx2x *bp) | 9826 | static int __devinit bnx2x_init_bp(struct bnx2x *bp) |
| 9763 | { | 9827 | { |
| 9764 | int func = BP_FUNC(bp); | 9828 | int func = BP_FUNC(bp); |
| @@ -9780,6 +9844,7 @@ static int __devinit bnx2x_init_bp(struct bnx2x *bp) | |||
| 9780 | 9844 | ||
| 9781 | rc = bnx2x_get_hwinfo(bp); | 9845 | rc = bnx2x_get_hwinfo(bp); |
| 9782 | 9846 | ||
| 9847 | bnx2x_read_fwinfo(bp); | ||
| 9783 | /* need to reset chip if undi was active */ | 9848 | /* need to reset chip if undi was active */ |
| 9784 | if (!BP_NOMCP(bp)) | 9849 | if (!BP_NOMCP(bp)) |
| 9785 | bnx2x_undi_unload(bp); | 9850 | bnx2x_undi_unload(bp); |
| @@ -10170,11 +10235,13 @@ static void bnx2x_get_drvinfo(struct net_device *dev, | |||
| 10170 | bnx2x_release_phy_lock(bp); | 10235 | bnx2x_release_phy_lock(bp); |
| 10171 | } | 10236 | } |
| 10172 | 10237 | ||
| 10173 | snprintf(info->fw_version, 32, "BC:%d.%d.%d%s%s", | 10238 | strncpy(info->fw_version, bp->fw_ver, 32); |
| 10239 | snprintf(info->fw_version + strlen(bp->fw_ver), 32 - strlen(bp->fw_ver), | ||
| 10240 | "bc %d.%d.%d%s%s", | ||
| 10174 | (bp->common.bc_ver & 0xff0000) >> 16, | 10241 | (bp->common.bc_ver & 0xff0000) >> 16, |
| 10175 | (bp->common.bc_ver & 0xff00) >> 8, | 10242 | (bp->common.bc_ver & 0xff00) >> 8, |
| 10176 | (bp->common.bc_ver & 0xff), | 10243 | (bp->common.bc_ver & 0xff), |
| 10177 | ((phy_fw_ver[0] != '\0') ? " PHY:" : ""), phy_fw_ver); | 10244 | ((phy_fw_ver[0] != '\0') ? " phy " : ""), phy_fw_ver); |
| 10178 | strcpy(info->bus_info, pci_name(bp->pdev)); | 10245 | strcpy(info->bus_info, pci_name(bp->pdev)); |
| 10179 | info->n_stats = BNX2X_NUM_STATS; | 10246 | info->n_stats = BNX2X_NUM_STATS; |
| 10180 | info->testinfo_len = BNX2X_NUM_TESTS; | 10247 | info->testinfo_len = BNX2X_NUM_TESTS; |
