Loading drivers/net/ethernet/qlogic/qed/qed.h +10 −1 Original line number Diff line number Diff line Loading @@ -195,6 +195,11 @@ enum qed_dev_cap { QED_DEV_CAP_ROCE, }; enum qed_wol_support { QED_WOL_SUPPORT_NONE, QED_WOL_SUPPORT_PME, }; struct qed_hw_info { /* PCI personality */ enum qed_pci_personality personality; Loading Loading @@ -227,6 +232,8 @@ struct qed_hw_info { u32 hw_mode; unsigned long device_capabilities; u16 mtu; enum qed_wol_support b_wol_support; }; struct qed_hw_cid_data { Loading Loading @@ -539,7 +546,9 @@ struct qed_dev { u8 mcp_rev; u8 boot_mode; u8 wol; /* WoL related configurations */ u8 wol_config; u8 wol_mac[ETH_ALEN]; u32 int_mode; enum qed_coalescing_mode int_coalescing_mode; Loading drivers/net/ethernet/qlogic/qed/qed_dev.c +17 −2 Original line number Diff line number Diff line Loading @@ -1364,8 +1364,24 @@ int qed_hw_reset(struct qed_dev *cdev) { int rc = 0; u32 unload_resp, unload_param; u32 wol_param; int i; switch (cdev->wol_config) { case QED_OV_WOL_DISABLED: wol_param = DRV_MB_PARAM_UNLOAD_WOL_DISABLED; break; case QED_OV_WOL_ENABLED: wol_param = DRV_MB_PARAM_UNLOAD_WOL_ENABLED; break; default: DP_NOTICE(cdev, "Unknown WoL configuration %02x\n", cdev->wol_config); /* Fallthrough */ case QED_OV_WOL_DEFAULT: wol_param = DRV_MB_PARAM_UNLOAD_WOL_MCP; } for_each_hwfn(cdev, i) { struct qed_hwfn *p_hwfn = &cdev->hwfns[i]; Loading Loading @@ -1394,8 +1410,7 @@ int qed_hw_reset(struct qed_dev *cdev) /* Send unload command to MCP */ rc = qed_mcp_cmd(p_hwfn, p_hwfn->p_main_ptt, DRV_MSG_CODE_UNLOAD_REQ, DRV_MB_PARAM_UNLOAD_WOL_MCP, DRV_MSG_CODE_UNLOAD_REQ, wol_param, &unload_resp, &unload_param); if (rc) { DP_NOTICE(p_hwfn, "qed_hw_reset: UNLOAD_REQ failed\n"); Loading drivers/net/ethernet/qlogic/qed/qed_hsi.h +4 −0 Original line number Diff line number Diff line Loading @@ -8601,6 +8601,7 @@ struct public_drv_mb { #define DRV_MSG_CODE_BIST_TEST 0x001e0000 #define DRV_MSG_CODE_SET_LED_MODE 0x00200000 #define DRV_MSG_CODE_OS_WOL 0x002e0000 #define DRV_MSG_SEQ_NUMBER_MASK 0x0000ffff Loading Loading @@ -8697,6 +8698,9 @@ struct public_drv_mb { #define FW_MSG_CODE_NVM_OK 0x00010000 #define FW_MSG_CODE_OK 0x00160000 #define FW_MSG_CODE_OS_WOL_SUPPORTED 0x00800000 #define FW_MSG_CODE_OS_WOL_NOT_SUPPORTED 0x00810000 #define FW_MSG_SEQ_NUMBER_MASK 0x0000ffff u32 fw_mb_param; Loading drivers/net/ethernet/qlogic/qed/qed_main.c +29 −0 Original line number Diff line number Diff line Loading @@ -221,6 +221,10 @@ int qed_fill_dev_info(struct qed_dev *cdev, dev_info->fw_eng = FW_ENGINEERING_VERSION; dev_info->mf_mode = cdev->mf_mode; dev_info->tx_switching = true; if (QED_LEADING_HWFN(cdev)->hw_info.b_wol_support == QED_WOL_SUPPORT_PME) dev_info->wol_support = true; } else { qed_vf_get_fw_version(&cdev->hwfns[0], &dev_info->fw_major, &dev_info->fw_minor, &dev_info->fw_rev, Loading Loading @@ -1433,6 +1437,30 @@ static int qed_set_led(struct qed_dev *cdev, enum qed_led_mode mode) return status; } static int qed_update_wol(struct qed_dev *cdev, bool enabled) { struct qed_hwfn *hwfn = QED_LEADING_HWFN(cdev); struct qed_ptt *ptt; int rc = 0; if (IS_VF(cdev)) return 0; ptt = qed_ptt_acquire(hwfn); if (!ptt) return -EAGAIN; rc = qed_mcp_ov_update_wol(hwfn, ptt, enabled ? QED_OV_WOL_ENABLED : QED_OV_WOL_DISABLED); if (rc) goto out; rc = qed_mcp_ov_update_current_config(hwfn, ptt, QED_OV_CLIENT_DRV); out: qed_ptt_release(hwfn, ptt); return rc; } static int qed_update_drv_state(struct qed_dev *cdev, bool active) { struct qed_hwfn *hwfn = QED_LEADING_HWFN(cdev); Loading Loading @@ -1541,6 +1569,7 @@ const struct qed_common_ops qed_common_ops_pass = { .update_drv_state = &qed_update_drv_state, .update_mac = &qed_update_mac, .update_mtu = &qed_update_mtu, .update_wol = &qed_update_wol, }; void qed_get_protocol_stats(struct qed_dev *cdev, Loading drivers/net/ethernet/qlogic/qed/qed_mcp.c +54 −2 Original line number Diff line number Diff line Loading @@ -330,6 +330,7 @@ static int qed_mcp_cmd_and_union(struct qed_hwfn *p_hwfn, struct qed_mcp_mb_params *p_mb_params) { u32 union_data_addr; int rc; /* MCP not initialized */ Loading Loading @@ -375,11 +376,32 @@ int qed_mcp_cmd(struct qed_hwfn *p_hwfn, u32 *o_mcp_param) { struct qed_mcp_mb_params mb_params; union drv_union_data data_src; int rc; memset(&mb_params, 0, sizeof(mb_params)); memset(&data_src, 0, sizeof(data_src)); mb_params.cmd = cmd; mb_params.param = param; /* In case of UNLOAD_DONE, set the primary MAC */ if ((cmd == DRV_MSG_CODE_UNLOAD_DONE) && (p_hwfn->cdev->wol_config == QED_OV_WOL_ENABLED)) { u8 *p_mac = p_hwfn->cdev->wol_mac; data_src.wol_mac.mac_upper = p_mac[0] << 8 | p_mac[1]; data_src.wol_mac.mac_lower = p_mac[2] << 24 | p_mac[3] << 16 | p_mac[4] << 8 | p_mac[5]; DP_VERBOSE(p_hwfn, (QED_MSG_SP | NETIF_MSG_IFDOWN), "Setting WoL MAC: %pM --> [%08x,%08x]\n", p_mac, data_src.wol_mac.mac_upper, data_src.wol_mac.mac_lower); mb_params.p_data_src = &data_src; } rc = qed_mcp_cmd_and_union(p_hwfn, p_ptt, &mb_params); if (rc) return rc; Loading Loading @@ -1058,6 +1080,9 @@ int qed_mcp_fill_shmem_func_info(struct qed_hwfn *p_hwfn, info->mac[3] = (u8)(shmem_info.mac_lower >> 16); info->mac[4] = (u8)(shmem_info.mac_lower >> 8); info->mac[5] = (u8)(shmem_info.mac_lower); /* Store primary MAC for later possible WoL */ memcpy(&p_hwfn->cdev->wol_mac, info->mac, ETH_ALEN); } else { DP_NOTICE(p_hwfn, "MAC is 0 in shmem\n"); } Loading @@ -1071,13 +1096,28 @@ int qed_mcp_fill_shmem_func_info(struct qed_hwfn *p_hwfn, info->mtu = (u16)shmem_info.mtu_size; p_hwfn->hw_info.b_wol_support = QED_WOL_SUPPORT_NONE; p_hwfn->cdev->wol_config = (u8)QED_OV_WOL_DEFAULT; if (qed_mcp_is_init(p_hwfn)) { u32 resp = 0, param = 0; int rc; rc = qed_mcp_cmd(p_hwfn, p_ptt, DRV_MSG_CODE_OS_WOL, 0, &resp, ¶m); if (rc) return rc; if (resp == FW_MSG_CODE_OS_WOL_SUPPORTED) p_hwfn->hw_info.b_wol_support = QED_WOL_SUPPORT_PME; } DP_VERBOSE(p_hwfn, (QED_MSG_SP | NETIF_MSG_IFUP), "Read configuration from shmem: pause_on_host %02x protocol %02x BW [%02x - %02x] MAC %02x:%02x:%02x:%02x:%02x:%02x wwn port %llx node %llx ovlan %04x\n", "Read configuration from shmem: pause_on_host %02x protocol %02x BW [%02x - %02x] MAC %02x:%02x:%02x:%02x:%02x:%02x wwn port %llx node %llx ovlan %04x wol %02x\n", info->pause_on_host, info->protocol, info->bandwidth_min, info->bandwidth_max, info->mac[0], info->mac[1], info->mac[2], info->mac[3], info->mac[4], info->mac[5], info->wwn_port, info->wwn_node, info->ovlan); info->wwn_port, info->wwn_node, info->ovlan, (u8)p_hwfn->hw_info.b_wol_support); return 0; } Loading Loading @@ -1322,6 +1362,9 @@ int qed_mcp_ov_update_mac(struct qed_hwfn *p_hwfn, if (rc) DP_ERR(p_hwfn, "Failed to send mac address, rc = %d\n", rc); /* Store primary MAC for later possible WoL */ memcpy(p_hwfn->cdev->wol_mac, mac, ETH_ALEN); return rc; } Loading @@ -1332,6 +1375,12 @@ int qed_mcp_ov_update_wol(struct qed_hwfn *p_hwfn, u32 drv_mb_param; int rc; if (p_hwfn->hw_info.b_wol_support == QED_WOL_SUPPORT_NONE) { DP_VERBOSE(p_hwfn, QED_MSG_SP, "Can't change WoL configuration when WoL isn't supported\n"); return -EINVAL; } switch (wol) { case QED_OV_WOL_DEFAULT: drv_mb_param = DRV_MB_PARAM_WOL_DEFAULT; Loading @@ -1352,6 +1401,9 @@ int qed_mcp_ov_update_wol(struct qed_hwfn *p_hwfn, if (rc) DP_ERR(p_hwfn, "Failed to send wol mode, rc = %d\n", rc); /* Store the WoL update for a future unload */ p_hwfn->cdev->wol_config = (u8)wol; return rc; } Loading Loading
drivers/net/ethernet/qlogic/qed/qed.h +10 −1 Original line number Diff line number Diff line Loading @@ -195,6 +195,11 @@ enum qed_dev_cap { QED_DEV_CAP_ROCE, }; enum qed_wol_support { QED_WOL_SUPPORT_NONE, QED_WOL_SUPPORT_PME, }; struct qed_hw_info { /* PCI personality */ enum qed_pci_personality personality; Loading Loading @@ -227,6 +232,8 @@ struct qed_hw_info { u32 hw_mode; unsigned long device_capabilities; u16 mtu; enum qed_wol_support b_wol_support; }; struct qed_hw_cid_data { Loading Loading @@ -539,7 +546,9 @@ struct qed_dev { u8 mcp_rev; u8 boot_mode; u8 wol; /* WoL related configurations */ u8 wol_config; u8 wol_mac[ETH_ALEN]; u32 int_mode; enum qed_coalescing_mode int_coalescing_mode; Loading
drivers/net/ethernet/qlogic/qed/qed_dev.c +17 −2 Original line number Diff line number Diff line Loading @@ -1364,8 +1364,24 @@ int qed_hw_reset(struct qed_dev *cdev) { int rc = 0; u32 unload_resp, unload_param; u32 wol_param; int i; switch (cdev->wol_config) { case QED_OV_WOL_DISABLED: wol_param = DRV_MB_PARAM_UNLOAD_WOL_DISABLED; break; case QED_OV_WOL_ENABLED: wol_param = DRV_MB_PARAM_UNLOAD_WOL_ENABLED; break; default: DP_NOTICE(cdev, "Unknown WoL configuration %02x\n", cdev->wol_config); /* Fallthrough */ case QED_OV_WOL_DEFAULT: wol_param = DRV_MB_PARAM_UNLOAD_WOL_MCP; } for_each_hwfn(cdev, i) { struct qed_hwfn *p_hwfn = &cdev->hwfns[i]; Loading Loading @@ -1394,8 +1410,7 @@ int qed_hw_reset(struct qed_dev *cdev) /* Send unload command to MCP */ rc = qed_mcp_cmd(p_hwfn, p_hwfn->p_main_ptt, DRV_MSG_CODE_UNLOAD_REQ, DRV_MB_PARAM_UNLOAD_WOL_MCP, DRV_MSG_CODE_UNLOAD_REQ, wol_param, &unload_resp, &unload_param); if (rc) { DP_NOTICE(p_hwfn, "qed_hw_reset: UNLOAD_REQ failed\n"); Loading
drivers/net/ethernet/qlogic/qed/qed_hsi.h +4 −0 Original line number Diff line number Diff line Loading @@ -8601,6 +8601,7 @@ struct public_drv_mb { #define DRV_MSG_CODE_BIST_TEST 0x001e0000 #define DRV_MSG_CODE_SET_LED_MODE 0x00200000 #define DRV_MSG_CODE_OS_WOL 0x002e0000 #define DRV_MSG_SEQ_NUMBER_MASK 0x0000ffff Loading Loading @@ -8697,6 +8698,9 @@ struct public_drv_mb { #define FW_MSG_CODE_NVM_OK 0x00010000 #define FW_MSG_CODE_OK 0x00160000 #define FW_MSG_CODE_OS_WOL_SUPPORTED 0x00800000 #define FW_MSG_CODE_OS_WOL_NOT_SUPPORTED 0x00810000 #define FW_MSG_SEQ_NUMBER_MASK 0x0000ffff u32 fw_mb_param; Loading
drivers/net/ethernet/qlogic/qed/qed_main.c +29 −0 Original line number Diff line number Diff line Loading @@ -221,6 +221,10 @@ int qed_fill_dev_info(struct qed_dev *cdev, dev_info->fw_eng = FW_ENGINEERING_VERSION; dev_info->mf_mode = cdev->mf_mode; dev_info->tx_switching = true; if (QED_LEADING_HWFN(cdev)->hw_info.b_wol_support == QED_WOL_SUPPORT_PME) dev_info->wol_support = true; } else { qed_vf_get_fw_version(&cdev->hwfns[0], &dev_info->fw_major, &dev_info->fw_minor, &dev_info->fw_rev, Loading Loading @@ -1433,6 +1437,30 @@ static int qed_set_led(struct qed_dev *cdev, enum qed_led_mode mode) return status; } static int qed_update_wol(struct qed_dev *cdev, bool enabled) { struct qed_hwfn *hwfn = QED_LEADING_HWFN(cdev); struct qed_ptt *ptt; int rc = 0; if (IS_VF(cdev)) return 0; ptt = qed_ptt_acquire(hwfn); if (!ptt) return -EAGAIN; rc = qed_mcp_ov_update_wol(hwfn, ptt, enabled ? QED_OV_WOL_ENABLED : QED_OV_WOL_DISABLED); if (rc) goto out; rc = qed_mcp_ov_update_current_config(hwfn, ptt, QED_OV_CLIENT_DRV); out: qed_ptt_release(hwfn, ptt); return rc; } static int qed_update_drv_state(struct qed_dev *cdev, bool active) { struct qed_hwfn *hwfn = QED_LEADING_HWFN(cdev); Loading Loading @@ -1541,6 +1569,7 @@ const struct qed_common_ops qed_common_ops_pass = { .update_drv_state = &qed_update_drv_state, .update_mac = &qed_update_mac, .update_mtu = &qed_update_mtu, .update_wol = &qed_update_wol, }; void qed_get_protocol_stats(struct qed_dev *cdev, Loading
drivers/net/ethernet/qlogic/qed/qed_mcp.c +54 −2 Original line number Diff line number Diff line Loading @@ -330,6 +330,7 @@ static int qed_mcp_cmd_and_union(struct qed_hwfn *p_hwfn, struct qed_mcp_mb_params *p_mb_params) { u32 union_data_addr; int rc; /* MCP not initialized */ Loading Loading @@ -375,11 +376,32 @@ int qed_mcp_cmd(struct qed_hwfn *p_hwfn, u32 *o_mcp_param) { struct qed_mcp_mb_params mb_params; union drv_union_data data_src; int rc; memset(&mb_params, 0, sizeof(mb_params)); memset(&data_src, 0, sizeof(data_src)); mb_params.cmd = cmd; mb_params.param = param; /* In case of UNLOAD_DONE, set the primary MAC */ if ((cmd == DRV_MSG_CODE_UNLOAD_DONE) && (p_hwfn->cdev->wol_config == QED_OV_WOL_ENABLED)) { u8 *p_mac = p_hwfn->cdev->wol_mac; data_src.wol_mac.mac_upper = p_mac[0] << 8 | p_mac[1]; data_src.wol_mac.mac_lower = p_mac[2] << 24 | p_mac[3] << 16 | p_mac[4] << 8 | p_mac[5]; DP_VERBOSE(p_hwfn, (QED_MSG_SP | NETIF_MSG_IFDOWN), "Setting WoL MAC: %pM --> [%08x,%08x]\n", p_mac, data_src.wol_mac.mac_upper, data_src.wol_mac.mac_lower); mb_params.p_data_src = &data_src; } rc = qed_mcp_cmd_and_union(p_hwfn, p_ptt, &mb_params); if (rc) return rc; Loading Loading @@ -1058,6 +1080,9 @@ int qed_mcp_fill_shmem_func_info(struct qed_hwfn *p_hwfn, info->mac[3] = (u8)(shmem_info.mac_lower >> 16); info->mac[4] = (u8)(shmem_info.mac_lower >> 8); info->mac[5] = (u8)(shmem_info.mac_lower); /* Store primary MAC for later possible WoL */ memcpy(&p_hwfn->cdev->wol_mac, info->mac, ETH_ALEN); } else { DP_NOTICE(p_hwfn, "MAC is 0 in shmem\n"); } Loading @@ -1071,13 +1096,28 @@ int qed_mcp_fill_shmem_func_info(struct qed_hwfn *p_hwfn, info->mtu = (u16)shmem_info.mtu_size; p_hwfn->hw_info.b_wol_support = QED_WOL_SUPPORT_NONE; p_hwfn->cdev->wol_config = (u8)QED_OV_WOL_DEFAULT; if (qed_mcp_is_init(p_hwfn)) { u32 resp = 0, param = 0; int rc; rc = qed_mcp_cmd(p_hwfn, p_ptt, DRV_MSG_CODE_OS_WOL, 0, &resp, ¶m); if (rc) return rc; if (resp == FW_MSG_CODE_OS_WOL_SUPPORTED) p_hwfn->hw_info.b_wol_support = QED_WOL_SUPPORT_PME; } DP_VERBOSE(p_hwfn, (QED_MSG_SP | NETIF_MSG_IFUP), "Read configuration from shmem: pause_on_host %02x protocol %02x BW [%02x - %02x] MAC %02x:%02x:%02x:%02x:%02x:%02x wwn port %llx node %llx ovlan %04x\n", "Read configuration from shmem: pause_on_host %02x protocol %02x BW [%02x - %02x] MAC %02x:%02x:%02x:%02x:%02x:%02x wwn port %llx node %llx ovlan %04x wol %02x\n", info->pause_on_host, info->protocol, info->bandwidth_min, info->bandwidth_max, info->mac[0], info->mac[1], info->mac[2], info->mac[3], info->mac[4], info->mac[5], info->wwn_port, info->wwn_node, info->ovlan); info->wwn_port, info->wwn_node, info->ovlan, (u8)p_hwfn->hw_info.b_wol_support); return 0; } Loading Loading @@ -1322,6 +1362,9 @@ int qed_mcp_ov_update_mac(struct qed_hwfn *p_hwfn, if (rc) DP_ERR(p_hwfn, "Failed to send mac address, rc = %d\n", rc); /* Store primary MAC for later possible WoL */ memcpy(p_hwfn->cdev->wol_mac, mac, ETH_ALEN); return rc; } Loading @@ -1332,6 +1375,12 @@ int qed_mcp_ov_update_wol(struct qed_hwfn *p_hwfn, u32 drv_mb_param; int rc; if (p_hwfn->hw_info.b_wol_support == QED_WOL_SUPPORT_NONE) { DP_VERBOSE(p_hwfn, QED_MSG_SP, "Can't change WoL configuration when WoL isn't supported\n"); return -EINVAL; } switch (wol) { case QED_OV_WOL_DEFAULT: drv_mb_param = DRV_MB_PARAM_WOL_DEFAULT; Loading @@ -1352,6 +1401,9 @@ int qed_mcp_ov_update_wol(struct qed_hwfn *p_hwfn, if (rc) DP_ERR(p_hwfn, "Failed to send wol mode, rc = %d\n", rc); /* Store the WoL update for a future unload */ p_hwfn->cdev->wol_config = (u8)wol; return rc; } Loading