diff options
author | Chinh Cao <chinh.t.cao@intel.com> | 2018-08-09 09:29:51 -0400 |
---|---|---|
committer | Jeff Kirsher <jeffrey.t.kirsher@intel.com> | 2018-08-28 13:48:26 -0400 |
commit | 48cb27f2fd18391056ea40cce5e33f1fd741679e (patch) | |
tree | dc0003d1076b7ffefe0ca9f9ebc45ce7ffd355c8 /drivers/net/ethernet/intel/ice/ice_common.c | |
parent | 0f9d5027a7496c451737f0f549be083688a40549 (diff) |
ice: Implement handlers for ethtool PHY/link operations
This patch implements handlers for ethtool get_link_ksettings and
set_link_ksettings. Helper functions use by these handlers are also
introduced in this patch.
Signed-off-by: Chinh Cao <chinh.t.cao@intel.com>
Signed-off-by: Anirudh Venkataramanan <anirudh.venkataramanan@intel.com>
Tested-by: Tony Brelinski <tonyx.brelinski@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Diffstat (limited to 'drivers/net/ethernet/intel/ice/ice_common.c')
-rw-r--r-- | drivers/net/ethernet/intel/ice/ice_common.c | 121 |
1 files changed, 112 insertions, 9 deletions
diff --git a/drivers/net/ethernet/intel/ice/ice_common.c b/drivers/net/ethernet/intel/ice/ice_common.c index b2bb42def038..52c2bf4f108e 100644 --- a/drivers/net/ethernet/intel/ice/ice_common.c +++ b/drivers/net/ethernet/intel/ice/ice_common.c | |||
@@ -125,7 +125,7 @@ ice_aq_manage_mac_read(struct ice_hw *hw, void *buf, u16 buf_size, | |||
125 | * | 125 | * |
126 | * Returns the various PHY capabilities supported on the Port (0x0600) | 126 | * Returns the various PHY capabilities supported on the Port (0x0600) |
127 | */ | 127 | */ |
128 | static enum ice_status | 128 | enum ice_status |
129 | ice_aq_get_phy_caps(struct ice_port_info *pi, bool qual_mods, u8 report_mode, | 129 | ice_aq_get_phy_caps(struct ice_port_info *pi, bool qual_mods, u8 report_mode, |
130 | struct ice_aqc_get_phy_caps_data *pcaps, | 130 | struct ice_aqc_get_phy_caps_data *pcaps, |
131 | struct ice_sq_cd *cd) | 131 | struct ice_sq_cd *cd) |
@@ -1409,6 +1409,110 @@ void ice_clear_pxe_mode(struct ice_hw *hw) | |||
1409 | } | 1409 | } |
1410 | 1410 | ||
1411 | /** | 1411 | /** |
1412 | * ice_get_link_speed_based_on_phy_type - returns link speed | ||
1413 | * @phy_type_low: lower part of phy_type | ||
1414 | * | ||
1415 | * This helper function will convert a phy_type_low to its corresponding link | ||
1416 | * speed. | ||
1417 | * Note: In the structure of phy_type_low, there should be one bit set, as | ||
1418 | * this function will convert one phy type to its speed. | ||
1419 | * If no bit gets set, ICE_LINK_SPEED_UNKNOWN will be returned | ||
1420 | * If more than one bit gets set, ICE_LINK_SPEED_UNKNOWN will be returned | ||
1421 | */ | ||
1422 | static u16 | ||
1423 | ice_get_link_speed_based_on_phy_type(u64 phy_type_low) | ||
1424 | { | ||
1425 | u16 speed_phy_type_low = ICE_AQ_LINK_SPEED_UNKNOWN; | ||
1426 | |||
1427 | switch (phy_type_low) { | ||
1428 | case ICE_PHY_TYPE_LOW_100BASE_TX: | ||
1429 | case ICE_PHY_TYPE_LOW_100M_SGMII: | ||
1430 | speed_phy_type_low = ICE_AQ_LINK_SPEED_100MB; | ||
1431 | break; | ||
1432 | case ICE_PHY_TYPE_LOW_1000BASE_T: | ||
1433 | case ICE_PHY_TYPE_LOW_1000BASE_SX: | ||
1434 | case ICE_PHY_TYPE_LOW_1000BASE_LX: | ||
1435 | case ICE_PHY_TYPE_LOW_1000BASE_KX: | ||
1436 | case ICE_PHY_TYPE_LOW_1G_SGMII: | ||
1437 | speed_phy_type_low = ICE_AQ_LINK_SPEED_1000MB; | ||
1438 | break; | ||
1439 | case ICE_PHY_TYPE_LOW_2500BASE_T: | ||
1440 | case ICE_PHY_TYPE_LOW_2500BASE_X: | ||
1441 | case ICE_PHY_TYPE_LOW_2500BASE_KX: | ||
1442 | speed_phy_type_low = ICE_AQ_LINK_SPEED_2500MB; | ||
1443 | break; | ||
1444 | case ICE_PHY_TYPE_LOW_5GBASE_T: | ||
1445 | case ICE_PHY_TYPE_LOW_5GBASE_KR: | ||
1446 | speed_phy_type_low = ICE_AQ_LINK_SPEED_5GB; | ||
1447 | break; | ||
1448 | case ICE_PHY_TYPE_LOW_10GBASE_T: | ||
1449 | case ICE_PHY_TYPE_LOW_10G_SFI_DA: | ||
1450 | case ICE_PHY_TYPE_LOW_10GBASE_SR: | ||
1451 | case ICE_PHY_TYPE_LOW_10GBASE_LR: | ||
1452 | case ICE_PHY_TYPE_LOW_10GBASE_KR_CR1: | ||
1453 | case ICE_PHY_TYPE_LOW_10G_SFI_AOC_ACC: | ||
1454 | case ICE_PHY_TYPE_LOW_10G_SFI_C2C: | ||
1455 | speed_phy_type_low = ICE_AQ_LINK_SPEED_10GB; | ||
1456 | break; | ||
1457 | case ICE_PHY_TYPE_LOW_25GBASE_T: | ||
1458 | case ICE_PHY_TYPE_LOW_25GBASE_CR: | ||
1459 | case ICE_PHY_TYPE_LOW_25GBASE_CR_S: | ||
1460 | case ICE_PHY_TYPE_LOW_25GBASE_CR1: | ||
1461 | case ICE_PHY_TYPE_LOW_25GBASE_SR: | ||
1462 | case ICE_PHY_TYPE_LOW_25GBASE_LR: | ||
1463 | case ICE_PHY_TYPE_LOW_25GBASE_KR: | ||
1464 | case ICE_PHY_TYPE_LOW_25GBASE_KR_S: | ||
1465 | case ICE_PHY_TYPE_LOW_25GBASE_KR1: | ||
1466 | case ICE_PHY_TYPE_LOW_25G_AUI_AOC_ACC: | ||
1467 | case ICE_PHY_TYPE_LOW_25G_AUI_C2C: | ||
1468 | speed_phy_type_low = ICE_AQ_LINK_SPEED_25GB; | ||
1469 | break; | ||
1470 | case ICE_PHY_TYPE_LOW_40GBASE_CR4: | ||
1471 | case ICE_PHY_TYPE_LOW_40GBASE_SR4: | ||
1472 | case ICE_PHY_TYPE_LOW_40GBASE_LR4: | ||
1473 | case ICE_PHY_TYPE_LOW_40GBASE_KR4: | ||
1474 | case ICE_PHY_TYPE_LOW_40G_XLAUI_AOC_ACC: | ||
1475 | case ICE_PHY_TYPE_LOW_40G_XLAUI: | ||
1476 | speed_phy_type_low = ICE_AQ_LINK_SPEED_40GB; | ||
1477 | break; | ||
1478 | default: | ||
1479 | speed_phy_type_low = ICE_AQ_LINK_SPEED_UNKNOWN; | ||
1480 | break; | ||
1481 | } | ||
1482 | |||
1483 | return speed_phy_type_low; | ||
1484 | } | ||
1485 | |||
1486 | /** | ||
1487 | * ice_update_phy_type | ||
1488 | * @phy_type_low: pointer to the lower part of phy_type | ||
1489 | * @link_speeds_bitmap: targeted link speeds bitmap | ||
1490 | * | ||
1491 | * Note: For the link_speeds_bitmap structure, you can check it at | ||
1492 | * [ice_aqc_get_link_status->link_speed]. Caller can pass in | ||
1493 | * link_speeds_bitmap include multiple speeds. | ||
1494 | * | ||
1495 | * The value of phy_type_low will present a certain link speed. This helper | ||
1496 | * function will turn on bits in the phy_type_low based on the value of | ||
1497 | * link_speeds_bitmap input parameter. | ||
1498 | */ | ||
1499 | void ice_update_phy_type(u64 *phy_type_low, u16 link_speeds_bitmap) | ||
1500 | { | ||
1501 | u16 speed = ICE_AQ_LINK_SPEED_UNKNOWN; | ||
1502 | u64 pt_low; | ||
1503 | int index; | ||
1504 | |||
1505 | /* We first check with low part of phy_type */ | ||
1506 | for (index = 0; index <= ICE_PHY_TYPE_LOW_MAX_INDEX; index++) { | ||
1507 | pt_low = BIT_ULL(index); | ||
1508 | speed = ice_get_link_speed_based_on_phy_type(pt_low); | ||
1509 | |||
1510 | if (link_speeds_bitmap & speed) | ||
1511 | *phy_type_low |= BIT_ULL(index); | ||
1512 | } | ||
1513 | } | ||
1514 | |||
1515 | /** | ||
1412 | * ice_aq_set_phy_cfg | 1516 | * ice_aq_set_phy_cfg |
1413 | * @hw: pointer to the hw struct | 1517 | * @hw: pointer to the hw struct |
1414 | * @lport: logical port number | 1518 | * @lport: logical port number |
@@ -1420,19 +1524,18 @@ void ice_clear_pxe_mode(struct ice_hw *hw) | |||
1420 | * mode as the PF may not have the privilege to set some of the PHY Config | 1524 | * mode as the PF may not have the privilege to set some of the PHY Config |
1421 | * parameters. This status will be indicated by the command response (0x0601). | 1525 | * parameters. This status will be indicated by the command response (0x0601). |
1422 | */ | 1526 | */ |
1423 | static enum ice_status | 1527 | enum ice_status |
1424 | ice_aq_set_phy_cfg(struct ice_hw *hw, u8 lport, | 1528 | ice_aq_set_phy_cfg(struct ice_hw *hw, u8 lport, |
1425 | struct ice_aqc_set_phy_cfg_data *cfg, struct ice_sq_cd *cd) | 1529 | struct ice_aqc_set_phy_cfg_data *cfg, struct ice_sq_cd *cd) |
1426 | { | 1530 | { |
1427 | struct ice_aqc_set_phy_cfg *cmd; | ||
1428 | struct ice_aq_desc desc; | 1531 | struct ice_aq_desc desc; |
1429 | 1532 | ||
1430 | if (!cfg) | 1533 | if (!cfg) |
1431 | return ICE_ERR_PARAM; | 1534 | return ICE_ERR_PARAM; |
1432 | 1535 | ||
1433 | cmd = &desc.params.set_phy; | ||
1434 | ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_set_phy_cfg); | 1536 | ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_set_phy_cfg); |
1435 | cmd->lport_num = lport; | 1537 | desc.params.set_phy.lport_num = lport; |
1538 | desc.flags |= cpu_to_le16(ICE_AQ_FLAG_RD); | ||
1436 | 1539 | ||
1437 | return ice_aq_send_cmd(hw, &desc, cfg, sizeof(*cfg), cd); | 1540 | return ice_aq_send_cmd(hw, &desc, cfg, sizeof(*cfg), cd); |
1438 | } | 1541 | } |
@@ -1481,12 +1584,12 @@ out: | |||
1481 | * ice_set_fc | 1584 | * ice_set_fc |
1482 | * @pi: port information structure | 1585 | * @pi: port information structure |
1483 | * @aq_failures: pointer to status code, specific to ice_set_fc routine | 1586 | * @aq_failures: pointer to status code, specific to ice_set_fc routine |
1484 | * @atomic_restart: enable automatic link update | 1587 | * @ena_auto_link_update: enable automatic link update |
1485 | * | 1588 | * |
1486 | * Set the requested flow control mode. | 1589 | * Set the requested flow control mode. |
1487 | */ | 1590 | */ |
1488 | enum ice_status | 1591 | enum ice_status |
1489 | ice_set_fc(struct ice_port_info *pi, u8 *aq_failures, bool atomic_restart) | 1592 | ice_set_fc(struct ice_port_info *pi, u8 *aq_failures, bool ena_auto_link_update) |
1490 | { | 1593 | { |
1491 | struct ice_aqc_set_phy_cfg_data cfg = { 0 }; | 1594 | struct ice_aqc_set_phy_cfg_data cfg = { 0 }; |
1492 | struct ice_aqc_get_phy_caps_data *pcaps; | 1595 | struct ice_aqc_get_phy_caps_data *pcaps; |
@@ -1536,8 +1639,8 @@ ice_set_fc(struct ice_port_info *pi, u8 *aq_failures, bool atomic_restart) | |||
1536 | int retry_count, retry_max = 10; | 1639 | int retry_count, retry_max = 10; |
1537 | 1640 | ||
1538 | /* Auto restart link so settings take effect */ | 1641 | /* Auto restart link so settings take effect */ |
1539 | if (atomic_restart) | 1642 | if (ena_auto_link_update) |
1540 | cfg.caps |= ICE_AQ_PHY_ENA_ATOMIC_LINK; | 1643 | cfg.caps |= ICE_AQ_PHY_ENA_AUTO_LINK_UPDT; |
1541 | /* Copy over all the old settings */ | 1644 | /* Copy over all the old settings */ |
1542 | cfg.phy_type_low = pcaps->phy_type_low; | 1645 | cfg.phy_type_low = pcaps->phy_type_low; |
1543 | cfg.low_power_ctrl = pcaps->low_power_ctrl; | 1646 | cfg.low_power_ctrl = pcaps->low_power_ctrl; |