Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge branch 'net-phylink-xpcs-stmmac-support-pcs-eee-configuration'

Russell King says:

====================
net: phylink,xpcs,stmmac: support PCS EEE configuration

This series adds support for phylink managed EEE at the PCS level,
allowing xpcs_config_eee() to be removed. Sadly, we still end up with
a XPCS specific function to configure the clock multiplier.
====================

Link: https://patch.msgid.link/Z6naiPpxfxGr1Ic6@shell.armlinux.org.uk
Signed-off-by: Jakub Kicinski <kuba@kernel.org>

+107 -42
-7
drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
··· 1046 1046 priv->tx_path_in_lpi_mode = false; 1047 1047 1048 1048 stmmac_set_eee_timer(priv, priv->hw, 0, STMMAC_DEFAULT_TWT_LS); 1049 - if (priv->hw->xpcs) 1050 - xpcs_config_eee(priv->hw->xpcs, priv->plat->mult_fact_100ns, 1051 - false); 1052 - 1053 1049 mutex_unlock(&priv->lock); 1054 1050 } 1055 1051 ··· 1064 1068 1065 1069 stmmac_set_eee_timer(priv, priv->hw, STMMAC_DEFAULT_LIT_LS, 1066 1070 STMMAC_DEFAULT_TWT_LS); 1067 - if (priv->hw->xpcs) 1068 - xpcs_config_eee(priv->hw->xpcs, priv->plat->mult_fact_100ns, 1069 - true); 1070 1071 1071 1072 /* Try to cnfigure the hardware timer. */ 1072 1073 ret = stmmac_set_lpi_mode(priv, priv->hw, STMMAC_LPI_TIMER,
+2
drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
··· 524 524 if (ret) 525 525 return dev_err_probe(priv->device, ret, "No xPCS found\n"); 526 526 527 + xpcs_config_eee_mult_fact(xpcs, priv->plat->mult_fact_100ns); 528 + 527 529 priv->hw->xpcs = xpcs; 528 530 529 531 return 0;
+59 -30
drivers/net/pcs/pcs-xpcs.c
··· 602 602 __set_bit(compat->interface, interfaces); 603 603 } 604 604 605 - int xpcs_config_eee(struct dw_xpcs *xpcs, int mult_fact_100ns, int enable) 606 - { 607 - u16 mask, val; 608 - int ret; 609 - 610 - mask = DW_VR_MII_EEE_LTX_EN | DW_VR_MII_EEE_LRX_EN | 611 - DW_VR_MII_EEE_TX_QUIET_EN | DW_VR_MII_EEE_RX_QUIET_EN | 612 - DW_VR_MII_EEE_TX_EN_CTRL | DW_VR_MII_EEE_RX_EN_CTRL | 613 - DW_VR_MII_EEE_MULT_FACT_100NS; 614 - 615 - if (enable) 616 - val = DW_VR_MII_EEE_LTX_EN | DW_VR_MII_EEE_LRX_EN | 617 - DW_VR_MII_EEE_TX_QUIET_EN | DW_VR_MII_EEE_RX_QUIET_EN | 618 - DW_VR_MII_EEE_TX_EN_CTRL | DW_VR_MII_EEE_RX_EN_CTRL | 619 - FIELD_PREP(DW_VR_MII_EEE_MULT_FACT_100NS, 620 - mult_fact_100ns); 621 - else 622 - val = 0; 623 - 624 - ret = xpcs_modify(xpcs, MDIO_MMD_VEND2, DW_VR_MII_EEE_MCTRL0, mask, 625 - val); 626 - if (ret < 0) 627 - return ret; 628 - 629 - return xpcs_modify(xpcs, MDIO_MMD_VEND2, DW_VR_MII_EEE_MCTRL1, 630 - DW_VR_MII_EEE_TRN_LPI, 631 - enable ? DW_VR_MII_EEE_TRN_LPI : 0); 632 - } 633 - EXPORT_SYMBOL_GPL(xpcs_config_eee); 634 - 635 605 static void xpcs_pre_config(struct phylink_pcs *pcs, phy_interface_t interface) 636 606 { 637 607 struct dw_xpcs *xpcs = phylink_pcs_to_xpcs(pcs); ··· 1163 1193 BMCR_ANRESTART); 1164 1194 } 1165 1195 1196 + static int xpcs_config_eee(struct dw_xpcs *xpcs, bool enable) 1197 + { 1198 + u16 mask, val; 1199 + int ret; 1200 + 1201 + mask = DW_VR_MII_EEE_LTX_EN | DW_VR_MII_EEE_LRX_EN | 1202 + DW_VR_MII_EEE_TX_QUIET_EN | DW_VR_MII_EEE_RX_QUIET_EN | 1203 + DW_VR_MII_EEE_TX_EN_CTRL | DW_VR_MII_EEE_RX_EN_CTRL | 1204 + DW_VR_MII_EEE_MULT_FACT_100NS; 1205 + 1206 + if (enable) 1207 + val = DW_VR_MII_EEE_LTX_EN | DW_VR_MII_EEE_LRX_EN | 1208 + DW_VR_MII_EEE_TX_QUIET_EN | DW_VR_MII_EEE_RX_QUIET_EN | 1209 + DW_VR_MII_EEE_TX_EN_CTRL | DW_VR_MII_EEE_RX_EN_CTRL | 1210 + FIELD_PREP(DW_VR_MII_EEE_MULT_FACT_100NS, 1211 + xpcs->eee_mult_fact); 1212 + else 1213 + val = 0; 1214 + 1215 + ret = xpcs_modify(xpcs, MDIO_MMD_VEND2, DW_VR_MII_EEE_MCTRL0, mask, 1216 + val); 1217 + if (ret < 0) 1218 + return ret; 1219 + 1220 + return xpcs_modify(xpcs, MDIO_MMD_VEND2, DW_VR_MII_EEE_MCTRL1, 1221 + DW_VR_MII_EEE_TRN_LPI, 1222 + enable ? DW_VR_MII_EEE_TRN_LPI : 0); 1223 + } 1224 + 1225 + static void xpcs_disable_eee(struct phylink_pcs *pcs) 1226 + { 1227 + struct dw_xpcs *xpcs = phylink_pcs_to_xpcs(pcs); 1228 + 1229 + xpcs_config_eee(xpcs, false); 1230 + } 1231 + 1232 + static void xpcs_enable_eee(struct phylink_pcs *pcs) 1233 + { 1234 + struct dw_xpcs *xpcs = phylink_pcs_to_xpcs(pcs); 1235 + 1236 + xpcs_config_eee(xpcs, true); 1237 + } 1238 + 1239 + /** 1240 + * xpcs_config_eee_mult_fact() - set the EEE clock multiplying factor 1241 + * @xpcs: pointer to a &struct dw_xpcs instance 1242 + * @mult_fact: the multiplying factor 1243 + * 1244 + * Configure the EEE clock multiplying factor. This value should be such that 1245 + * clk_eee_time_period * (mult_fact + 1) is within the range 80 to 120ns. 1246 + */ 1247 + void xpcs_config_eee_mult_fact(struct dw_xpcs *xpcs, u8 mult_fact) 1248 + { 1249 + xpcs->eee_mult_fact = mult_fact; 1250 + } 1251 + EXPORT_SYMBOL_GPL(xpcs_config_eee_mult_fact); 1252 + 1166 1253 static int xpcs_read_ids(struct dw_xpcs *xpcs) 1167 1254 { 1168 1255 int ret; ··· 1368 1341 .pcs_get_state = xpcs_get_state, 1369 1342 .pcs_an_restart = xpcs_an_restart, 1370 1343 .pcs_link_up = xpcs_link_up, 1344 + .pcs_disable_eee = xpcs_disable_eee, 1345 + .pcs_enable_eee = xpcs_enable_eee, 1371 1346 }; 1372 1347 1373 1348 static int xpcs_identify(struct dw_xpcs *xpcs)
+1
drivers/net/pcs/pcs-xpcs.h
··· 122 122 struct phylink_pcs pcs; 123 123 phy_interface_t interface; 124 124 bool need_reset; 125 + u8 eee_mult_fact; 125 126 }; 126 127 127 128 int xpcs_read(struct dw_xpcs *xpcs, int dev, u32 reg);
+22 -3
drivers/net/phy/phylink.c
··· 1073 1073 pcs->ops->pcs_link_up(pcs, neg_mode, interface, speed, duplex); 1074 1074 } 1075 1075 1076 + static void phylink_pcs_disable_eee(struct phylink_pcs *pcs) 1077 + { 1078 + if (pcs && pcs->ops->pcs_disable_eee) 1079 + pcs->ops->pcs_disable_eee(pcs); 1080 + } 1081 + 1082 + static void phylink_pcs_enable_eee(struct phylink_pcs *pcs) 1083 + { 1084 + if (pcs && pcs->ops->pcs_enable_eee) 1085 + pcs->ops->pcs_enable_eee(pcs); 1086 + } 1087 + 1076 1088 /* Query inband for a specific interface mode, asking the MAC for the 1077 1089 * PCS which will be used to handle the interface mode. 1078 1090 */ ··· 1613 1601 phylink_dbg(pl, "disabling LPI\n"); 1614 1602 1615 1603 pl->mac_ops->mac_disable_tx_lpi(pl->config); 1604 + 1605 + phylink_pcs_disable_eee(pl->pcs); 1616 1606 } 1617 1607 } 1618 1608 ··· 1631 1617 phylink_dbg(pl, "LPI timer %uus, tx clock stop %u\n", 1632 1618 pl->mac_tx_lpi_timer, pl->mac_tx_clk_stop); 1633 1619 1620 + phylink_pcs_enable_eee(pl->pcs); 1621 + 1634 1622 err = pl->mac_ops->mac_enable_tx_lpi(pl->config, pl->mac_tx_lpi_timer, 1635 1623 pl->mac_tx_clk_stop); 1636 - if (!err) 1637 - pl->mac_enable_tx_lpi = true; 1638 - else 1624 + if (err) { 1625 + phylink_pcs_disable_eee(pl->pcs); 1639 1626 phylink_err(pl, "%ps() failed: %pe\n", 1640 1627 pl->mac_ops->mac_enable_tx_lpi, ERR_PTR(err)); 1628 + return; 1629 + } 1630 + 1631 + pl->mac_enable_tx_lpi = true; 1641 1632 } 1642 1633 1643 1634 static void phylink_link_up(struct phylink *pl,
+1 -2
include/linux/pcs/pcs-xpcs.h
··· 50 50 51 51 struct phylink_pcs *xpcs_to_phylink_pcs(struct dw_xpcs *xpcs); 52 52 int xpcs_get_an_mode(struct dw_xpcs *xpcs, phy_interface_t interface); 53 - int xpcs_config_eee(struct dw_xpcs *xpcs, int mult_fact_100ns, 54 - int enable); 53 + void xpcs_config_eee_mult_fact(struct dw_xpcs *xpcs, u8 mult_fact); 55 54 struct dw_xpcs *xpcs_create_mdiodev(struct mii_bus *bus, int addr); 56 55 struct dw_xpcs *xpcs_create_fwnode(struct fwnode_handle *fwnode); 57 56 void xpcs_destroy(struct dw_xpcs *xpcs);
+22
include/linux/phylink.h
··· 477 477 * @pcs_an_restart: restart 802.3z BaseX autonegotiation. 478 478 * @pcs_link_up: program the PCS for the resolved link configuration 479 479 * (where necessary). 480 + * @pcs_disable_eee: optional notification to PCS that EEE has been disabled 481 + * at the MAC. 482 + * @pcs_enable_eee: optional notification to PCS that EEE will be enabled at 483 + * the MAC. 480 484 * @pcs_pre_init: configure PCS components necessary for MAC hardware 481 485 * initialization e.g. RX clock for stmmac. 482 486 */ ··· 504 500 void (*pcs_an_restart)(struct phylink_pcs *pcs); 505 501 void (*pcs_link_up)(struct phylink_pcs *pcs, unsigned int neg_mode, 506 502 phy_interface_t interface, int speed, int duplex); 503 + void (*pcs_disable_eee)(struct phylink_pcs *pcs); 504 + void (*pcs_enable_eee)(struct phylink_pcs *pcs); 507 505 int (*pcs_pre_init)(struct phylink_pcs *pcs); 508 506 }; 509 507 ··· 630 624 */ 631 625 void pcs_link_up(struct phylink_pcs *pcs, unsigned int neg_mode, 632 626 phy_interface_t interface, int speed, int duplex); 627 + 628 + /** 629 + * pcs_disable_eee() - Disable EEE at the PCS 630 + * @pcs: a pointer to a &struct phylink_pcs 631 + * 632 + * Optional method informing the PCS that EEE has been disabled at the MAC. 633 + */ 634 + void pcs_disable_eee(struct phylink_pcs *pcs); 635 + 636 + /** 637 + * pcs_enable_eee() - Enable EEE at the PCS 638 + * @pcs: a pointer to a &struct phylink_pcs 639 + * 640 + * Optional method informing the PCS that EEE is about to be enabled at the MAC. 641 + */ 642 + void pcs_enable_eee(struct phylink_pcs *pcs); 633 643 634 644 /** 635 645 * pcs_pre_init() - Configure PCS components necessary for MAC initialization