diff options
author | Allan, Bruce W <bruce.w.allan@intel.com> | 2012-08-20 00:55:29 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2012-08-23 01:58:27 -0400 |
commit | b32607dd47d456b99f0a16f1c37bc8a0975ffb19 (patch) | |
tree | 74be66275dc26089b3a2c7b73b83d08198cff551 | |
parent | 9e67030af367ab524d0856af9e992de241eca3c7 (diff) |
mdio: translation of MMD EEE registers to/from ethtool settings
The helper functions which translate IEEE MDIO Manageable Device (MMD)
Energy-Efficient Ethernet (EEE) registers 3.20, 7.60 and 7.61 to and from
the comparable ethtool supported/advertised settings will be needed by
drivers other than those in PHYLIB (e.g. e1000e in a follow-on patch).
In the same fashion as similar translation functions in linux/mii.h, move
these functions from the PHYLIB core to the linux/mdio.h header file so the
code will not have to be duplicated in each driver needing MMD-to-ethtool
(and vice-versa) translations. The function and some variable names have
been renamed to be more descriptive.
Not tested on the only hardware that currently calls the related functions,
stmmac, because I don't have access to any. Has been compile tested and
the translations have been tested on a locally modified version of e1000e.
Signed-off-by: Bruce Allan <bruce.w.allan@intel.com>
Cc: Giuseppe Cavallaro <peppe.cavallaro@st.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r-- | drivers/net/phy/phy.c | 74 | ||||
-rw-r--r-- | include/linux/mdio.h | 83 |
2 files changed, 90 insertions, 67 deletions
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c index 7ca2ff97c368..ef9ea9248223 100644 --- a/drivers/net/phy/phy.c +++ b/drivers/net/phy/phy.c | |||
@@ -1035,66 +1035,6 @@ static void phy_write_mmd_indirect(struct mii_bus *bus, int prtad, int devad, | |||
1035 | bus->write(bus, addr, MII_MMD_DATA, data); | 1035 | bus->write(bus, addr, MII_MMD_DATA, data); |
1036 | } | 1036 | } |
1037 | 1037 | ||
1038 | static u32 phy_eee_to_adv(u16 eee_adv) | ||
1039 | { | ||
1040 | u32 adv = 0; | ||
1041 | |||
1042 | if (eee_adv & MDIO_EEE_100TX) | ||
1043 | adv |= ADVERTISED_100baseT_Full; | ||
1044 | if (eee_adv & MDIO_EEE_1000T) | ||
1045 | adv |= ADVERTISED_1000baseT_Full; | ||
1046 | if (eee_adv & MDIO_EEE_10GT) | ||
1047 | adv |= ADVERTISED_10000baseT_Full; | ||
1048 | if (eee_adv & MDIO_EEE_1000KX) | ||
1049 | adv |= ADVERTISED_1000baseKX_Full; | ||
1050 | if (eee_adv & MDIO_EEE_10GKX4) | ||
1051 | adv |= ADVERTISED_10000baseKX4_Full; | ||
1052 | if (eee_adv & MDIO_EEE_10GKR) | ||
1053 | adv |= ADVERTISED_10000baseKR_Full; | ||
1054 | |||
1055 | return adv; | ||
1056 | } | ||
1057 | |||
1058 | static u32 phy_eee_to_supported(u16 eee_caported) | ||
1059 | { | ||
1060 | u32 supported = 0; | ||
1061 | |||
1062 | if (eee_caported & MDIO_EEE_100TX) | ||
1063 | supported |= SUPPORTED_100baseT_Full; | ||
1064 | if (eee_caported & MDIO_EEE_1000T) | ||
1065 | supported |= SUPPORTED_1000baseT_Full; | ||
1066 | if (eee_caported & MDIO_EEE_10GT) | ||
1067 | supported |= SUPPORTED_10000baseT_Full; | ||
1068 | if (eee_caported & MDIO_EEE_1000KX) | ||
1069 | supported |= SUPPORTED_1000baseKX_Full; | ||
1070 | if (eee_caported & MDIO_EEE_10GKX4) | ||
1071 | supported |= SUPPORTED_10000baseKX4_Full; | ||
1072 | if (eee_caported & MDIO_EEE_10GKR) | ||
1073 | supported |= SUPPORTED_10000baseKR_Full; | ||
1074 | |||
1075 | return supported; | ||
1076 | } | ||
1077 | |||
1078 | static u16 phy_adv_to_eee(u32 adv) | ||
1079 | { | ||
1080 | u16 reg = 0; | ||
1081 | |||
1082 | if (adv & ADVERTISED_100baseT_Full) | ||
1083 | reg |= MDIO_EEE_100TX; | ||
1084 | if (adv & ADVERTISED_1000baseT_Full) | ||
1085 | reg |= MDIO_EEE_1000T; | ||
1086 | if (adv & ADVERTISED_10000baseT_Full) | ||
1087 | reg |= MDIO_EEE_10GT; | ||
1088 | if (adv & ADVERTISED_1000baseKX_Full) | ||
1089 | reg |= MDIO_EEE_1000KX; | ||
1090 | if (adv & ADVERTISED_10000baseKX4_Full) | ||
1091 | reg |= MDIO_EEE_10GKX4; | ||
1092 | if (adv & ADVERTISED_10000baseKR_Full) | ||
1093 | reg |= MDIO_EEE_10GKR; | ||
1094 | |||
1095 | return reg; | ||
1096 | } | ||
1097 | |||
1098 | /** | 1038 | /** |
1099 | * phy_init_eee - init and check the EEE feature | 1039 | * phy_init_eee - init and check the EEE feature |
1100 | * @phydev: target phy_device struct | 1040 | * @phydev: target phy_device struct |
@@ -1132,7 +1072,7 @@ int phy_init_eee(struct phy_device *phydev, bool clk_stop_enable) | |||
1132 | if (eee_cap < 0) | 1072 | if (eee_cap < 0) |
1133 | return eee_cap; | 1073 | return eee_cap; |
1134 | 1074 | ||
1135 | cap = phy_eee_to_supported(eee_cap); | 1075 | cap = mmd_eee_cap_to_ethtool_sup_t(eee_cap); |
1136 | if (!cap) | 1076 | if (!cap) |
1137 | goto eee_exit; | 1077 | goto eee_exit; |
1138 | 1078 | ||
@@ -1149,8 +1089,8 @@ int phy_init_eee(struct phy_device *phydev, bool clk_stop_enable) | |||
1149 | if (eee_adv < 0) | 1089 | if (eee_adv < 0) |
1150 | return eee_adv; | 1090 | return eee_adv; |
1151 | 1091 | ||
1152 | adv = phy_eee_to_adv(eee_adv); | 1092 | adv = mmd_eee_adv_to_ethtool_adv_t(eee_adv); |
1153 | lp = phy_eee_to_adv(eee_lp); | 1093 | lp = mmd_eee_adv_to_ethtool_adv_t(eee_lp); |
1154 | idx = phy_find_setting(phydev->speed, phydev->duplex); | 1094 | idx = phy_find_setting(phydev->speed, phydev->duplex); |
1155 | if ((lp & adv & settings[idx].setting)) | 1095 | if ((lp & adv & settings[idx].setting)) |
1156 | goto eee_exit; | 1096 | goto eee_exit; |
@@ -1210,21 +1150,21 @@ int phy_ethtool_get_eee(struct phy_device *phydev, struct ethtool_eee *data) | |||
1210 | MDIO_MMD_PCS, phydev->addr); | 1150 | MDIO_MMD_PCS, phydev->addr); |
1211 | if (val < 0) | 1151 | if (val < 0) |
1212 | return val; | 1152 | return val; |
1213 | data->supported = phy_eee_to_supported(val); | 1153 | data->supported = mmd_eee_cap_to_ethtool_sup_t(val); |
1214 | 1154 | ||
1215 | /* Get advertisement EEE */ | 1155 | /* Get advertisement EEE */ |
1216 | val = phy_read_mmd_indirect(phydev->bus, MDIO_AN_EEE_ADV, | 1156 | val = phy_read_mmd_indirect(phydev->bus, MDIO_AN_EEE_ADV, |
1217 | MDIO_MMD_AN, phydev->addr); | 1157 | MDIO_MMD_AN, phydev->addr); |
1218 | if (val < 0) | 1158 | if (val < 0) |
1219 | return val; | 1159 | return val; |
1220 | data->advertised = phy_eee_to_adv(val); | 1160 | data->advertised = mmd_eee_adv_to_ethtool_adv_t(val); |
1221 | 1161 | ||
1222 | /* Get LP advertisement EEE */ | 1162 | /* Get LP advertisement EEE */ |
1223 | val = phy_read_mmd_indirect(phydev->bus, MDIO_AN_EEE_LPABLE, | 1163 | val = phy_read_mmd_indirect(phydev->bus, MDIO_AN_EEE_LPABLE, |
1224 | MDIO_MMD_AN, phydev->addr); | 1164 | MDIO_MMD_AN, phydev->addr); |
1225 | if (val < 0) | 1165 | if (val < 0) |
1226 | return val; | 1166 | return val; |
1227 | data->lp_advertised = phy_eee_to_adv(val); | 1167 | data->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(val); |
1228 | 1168 | ||
1229 | return 0; | 1169 | return 0; |
1230 | } | 1170 | } |
@@ -1241,7 +1181,7 @@ int phy_ethtool_set_eee(struct phy_device *phydev, struct ethtool_eee *data) | |||
1241 | { | 1181 | { |
1242 | int val; | 1182 | int val; |
1243 | 1183 | ||
1244 | val = phy_adv_to_eee(data->advertised); | 1184 | val = ethtool_adv_to_mmd_eee_adv_t(data->advertised); |
1245 | phy_write_mmd_indirect(phydev->bus, MDIO_AN_EEE_ADV, MDIO_MMD_AN, | 1185 | phy_write_mmd_indirect(phydev->bus, MDIO_AN_EEE_ADV, MDIO_MMD_AN, |
1246 | phydev->addr, val); | 1186 | phydev->addr, val); |
1247 | 1187 | ||
diff --git a/include/linux/mdio.h b/include/linux/mdio.h index 7cccafe50e7b..6c406845f7e2 100644 --- a/include/linux/mdio.h +++ b/include/linux/mdio.h | |||
@@ -377,5 +377,88 @@ static inline void mdio45_ethtool_gset(const struct mdio_if_info *mdio, | |||
377 | extern int mdio_mii_ioctl(const struct mdio_if_info *mdio, | 377 | extern int mdio_mii_ioctl(const struct mdio_if_info *mdio, |
378 | struct mii_ioctl_data *mii_data, int cmd); | 378 | struct mii_ioctl_data *mii_data, int cmd); |
379 | 379 | ||
380 | /** | ||
381 | * mmd_eee_cap_to_ethtool_sup_t | ||
382 | * @eee_cap: value of the MMD EEE Capability register | ||
383 | * | ||
384 | * A small helper function that translates MMD EEE Capability (3.20) bits | ||
385 | * to ethtool supported settings. | ||
386 | */ | ||
387 | static inline u32 mmd_eee_cap_to_ethtool_sup_t(u16 eee_cap) | ||
388 | { | ||
389 | u32 supported = 0; | ||
390 | |||
391 | if (eee_cap & MDIO_EEE_100TX) | ||
392 | supported |= SUPPORTED_100baseT_Full; | ||
393 | if (eee_cap & MDIO_EEE_1000T) | ||
394 | supported |= SUPPORTED_1000baseT_Full; | ||
395 | if (eee_cap & MDIO_EEE_10GT) | ||
396 | supported |= SUPPORTED_10000baseT_Full; | ||
397 | if (eee_cap & MDIO_EEE_1000KX) | ||
398 | supported |= SUPPORTED_1000baseKX_Full; | ||
399 | if (eee_cap & MDIO_EEE_10GKX4) | ||
400 | supported |= SUPPORTED_10000baseKX4_Full; | ||
401 | if (eee_cap & MDIO_EEE_10GKR) | ||
402 | supported |= SUPPORTED_10000baseKR_Full; | ||
403 | |||
404 | return supported; | ||
405 | } | ||
406 | |||
407 | /** | ||
408 | * mmd_eee_adv_to_ethtool_adv_t | ||
409 | * @eee_adv: value of the MMD EEE Advertisement/Link Partner Ability registers | ||
410 | * | ||
411 | * A small helper function that translates the MMD EEE Advertisment (7.60) | ||
412 | * and MMD EEE Link Partner Ability (7.61) bits to ethtool advertisement | ||
413 | * settings. | ||
414 | */ | ||
415 | static inline u32 mmd_eee_adv_to_ethtool_adv_t(u16 eee_adv) | ||
416 | { | ||
417 | u32 adv = 0; | ||
418 | |||
419 | if (eee_adv & MDIO_EEE_100TX) | ||
420 | adv |= ADVERTISED_100baseT_Full; | ||
421 | if (eee_adv & MDIO_EEE_1000T) | ||
422 | adv |= ADVERTISED_1000baseT_Full; | ||
423 | if (eee_adv & MDIO_EEE_10GT) | ||
424 | adv |= ADVERTISED_10000baseT_Full; | ||
425 | if (eee_adv & MDIO_EEE_1000KX) | ||
426 | adv |= ADVERTISED_1000baseKX_Full; | ||
427 | if (eee_adv & MDIO_EEE_10GKX4) | ||
428 | adv |= ADVERTISED_10000baseKX4_Full; | ||
429 | if (eee_adv & MDIO_EEE_10GKR) | ||
430 | adv |= ADVERTISED_10000baseKR_Full; | ||
431 | |||
432 | return adv; | ||
433 | } | ||
434 | |||
435 | /** | ||
436 | * ethtool_adv_to_mmd_eee_adv_t | ||
437 | * @adv: the ethtool advertisement settings | ||
438 | * | ||
439 | * A small helper function that translates ethtool advertisement settings | ||
440 | * to EEE advertisements for the MMD EEE Advertisement (7.60) and | ||
441 | * MMD EEE Link Partner Ability (7.61) registers. | ||
442 | */ | ||
443 | static inline u16 ethtool_adv_to_mmd_eee_adv_t(u32 adv) | ||
444 | { | ||
445 | u16 reg = 0; | ||
446 | |||
447 | if (adv & ADVERTISED_100baseT_Full) | ||
448 | reg |= MDIO_EEE_100TX; | ||
449 | if (adv & ADVERTISED_1000baseT_Full) | ||
450 | reg |= MDIO_EEE_1000T; | ||
451 | if (adv & ADVERTISED_10000baseT_Full) | ||
452 | reg |= MDIO_EEE_10GT; | ||
453 | if (adv & ADVERTISED_1000baseKX_Full) | ||
454 | reg |= MDIO_EEE_1000KX; | ||
455 | if (adv & ADVERTISED_10000baseKX4_Full) | ||
456 | reg |= MDIO_EEE_10GKX4; | ||
457 | if (adv & ADVERTISED_10000baseKR_Full) | ||
458 | reg |= MDIO_EEE_10GKR; | ||
459 | |||
460 | return reg; | ||
461 | } | ||
462 | |||
380 | #endif /* __KERNEL__ */ | 463 | #endif /* __KERNEL__ */ |
381 | #endif /* __LINUX_MDIO_H__ */ | 464 | #endif /* __LINUX_MDIO_H__ */ |