diff options
Diffstat (limited to 'drivers/net/phy/phy-c45.c')
-rw-r--r-- | drivers/net/phy/phy-c45.c | 77 |
1 files changed, 29 insertions, 48 deletions
diff --git a/drivers/net/phy/phy-c45.c b/drivers/net/phy/phy-c45.c index 5695935fdce9..bdd70d424491 100644 --- a/drivers/net/phy/phy-c45.c +++ b/drivers/net/phy/phy-c45.c @@ -9,6 +9,7 @@ #include <linux/phy.h> #include "mdio-open-alliance.h" +#include "phylib-internal.h" /** * genphy_c45_baset1_able - checks if the PMA has BASE-T1 extended abilities @@ -680,18 +681,14 @@ EXPORT_SYMBOL_GPL(genphy_c45_read_mdix); * @phydev: target phy_device struct * @adv: the linkmode advertisement settings */ -int genphy_c45_write_eee_adv(struct phy_device *phydev, unsigned long *adv) +static int genphy_c45_write_eee_adv(struct phy_device *phydev, + unsigned long *adv) { int val, changed = 0; if (linkmode_intersects(phydev->supported_eee, PHY_EEE_CAP1_FEATURES)) { val = linkmode_to_mii_eee_cap1_t(adv); - /* In eee_broken_modes are stored MDIO_AN_EEE_ADV specific raw - * register values. - */ - val &= ~phydev->eee_broken_modes; - /* IEEE 802.3-2018 45.2.7.13 EEE advertisement 1 * (Register 7.60) */ @@ -942,7 +939,7 @@ EXPORT_SYMBOL_GPL(genphy_c45_read_eee_abilities); */ int genphy_c45_an_config_eee_aneg(struct phy_device *phydev) { - if (!phydev->eee_enabled) { + if (!phydev->eee_cfg.eee_enabled) { __ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {}; return genphy_c45_write_eee_adv(phydev, adv); @@ -950,6 +947,7 @@ int genphy_c45_an_config_eee_aneg(struct phy_device *phydev) return genphy_c45_write_eee_adv(phydev, phydev->advertising_eee); } +EXPORT_SYMBOL_GPL(genphy_c45_an_config_eee_aneg); /** * genphy_c45_pma_baset1_read_abilities - read supported baset1 link modes from PMA @@ -1230,8 +1228,11 @@ int gen10g_config_aneg(struct phy_device *phydev) } EXPORT_SYMBOL_GPL(gen10g_config_aneg); -int genphy_c45_loopback(struct phy_device *phydev, bool enable) +int genphy_c45_loopback(struct phy_device *phydev, bool enable, int speed) { + if (enable && speed) + return -EOPNOTSUPP; + return phy_modify_mmd(phydev, MDIO_MMD_PCS, MDIO_CTRL1, MDIO_PCS_CTRL1_LOOPBACK, enable ? MDIO_PCS_CTRL1_LOOPBACK : 0); @@ -1467,46 +1468,32 @@ EXPORT_SYMBOL_GPL(genphy_c45_plca_get_status); /** * genphy_c45_eee_is_active - get EEE status * @phydev: target phy_device struct - * @adv: variable to store advertised linkmodes * @lp: variable to store LP advertised linkmodes - * @is_enabled: variable to store EEE enabled/disabled configuration value * - * Description: this function will read local and link partner PHY - * advertisements. Compare them return current EEE state. + * Description: this function will read link partner PHY advertisement + * and compare it to local advertisement to return current EEE state. */ -int genphy_c45_eee_is_active(struct phy_device *phydev, unsigned long *adv, - unsigned long *lp, bool *is_enabled) +int genphy_c45_eee_is_active(struct phy_device *phydev, unsigned long *lp) { - __ETHTOOL_DECLARE_LINK_MODE_MASK(tmp_adv) = {}; __ETHTOOL_DECLARE_LINK_MODE_MASK(tmp_lp) = {}; __ETHTOOL_DECLARE_LINK_MODE_MASK(common); - bool eee_enabled, eee_active; int ret; - ret = genphy_c45_read_eee_adv(phydev, tmp_adv); - if (ret) - return ret; + if (!phydev->eee_cfg.eee_enabled) + return 0; ret = genphy_c45_read_eee_lpa(phydev, tmp_lp); if (ret) return ret; - eee_enabled = !linkmode_empty(tmp_adv); - linkmode_and(common, tmp_adv, tmp_lp); - if (eee_enabled && !linkmode_empty(common)) - eee_active = phy_check_valid(phydev->speed, phydev->duplex, - common); - else - eee_active = false; - - if (adv) - linkmode_copy(adv, tmp_adv); if (lp) linkmode_copy(lp, tmp_lp); - if (is_enabled) - *is_enabled = eee_enabled; - return eee_active; + linkmode_and(common, phydev->advertising_eee, tmp_lp); + if (linkmode_empty(common)) + return 0; + + return phy_check_valid(phydev->speed, phydev->duplex, common); } EXPORT_SYMBOL(genphy_c45_eee_is_active); @@ -1521,21 +1508,16 @@ EXPORT_SYMBOL(genphy_c45_eee_is_active); int genphy_c45_ethtool_get_eee(struct phy_device *phydev, struct ethtool_keee *data) { - __ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {}; - __ETHTOOL_DECLARE_LINK_MODE_MASK(lp) = {}; - bool is_enabled; int ret; - ret = genphy_c45_eee_is_active(phydev, adv, lp, &is_enabled); + ret = genphy_c45_eee_is_active(phydev, data->lp_advertised); if (ret < 0) return ret; - data->eee_enabled = is_enabled; - data->eee_active = ret; - linkmode_copy(data->supported, phydev->supported_eee); - linkmode_copy(data->advertised, adv); - linkmode_copy(data->lp_advertised, lp); - + data->eee_active = phydev->eee_active; + linkmode_andnot(data->supported, phydev->supported_eee, + phydev->eee_disabled_modes); + linkmode_copy(data->advertised, phydev->advertising_eee); return 0; } EXPORT_SYMBOL(genphy_c45_ethtool_get_eee); @@ -1568,15 +1550,14 @@ int genphy_c45_ethtool_set_eee(struct phy_device *phydev, phydev_warn(phydev, "At least some EEE link modes are not supported.\n"); return -EINVAL; } - } else { - adv = phydev->supported_eee; - } - linkmode_copy(phydev->advertising_eee, adv); + linkmode_andnot(phydev->advertising_eee, adv, + phydev->eee_disabled_modes); + } else if (linkmode_empty(phydev->advertising_eee)) { + phy_advertise_eee_all(phydev); + } } - phydev->eee_enabled = data->eee_enabled; - ret = genphy_c45_an_config_eee_aneg(phydev); if (ret > 0) { ret = phy_restart_aneg(phydev); |