linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
@ 2023-02-01 14:58 Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support Oleksij Rempel
                   ` (23 more replies)
  0 siblings, 24 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

changes v4:
- remove following helpers:
  mmd_eee_cap_to_ethtool_sup_t
  mmd_eee_adv_to_ethtool_adv_t
  ethtool_adv_to_mmd_eee_adv_t
  and port drivers from this helpers to linkmode helpers.
- rebase against latest net-next
- port phy_init_eee() to genphy_c45_eee_is_active()

changes v3:
- rework some parts of EEE infrastructure and move it to c45 code.
- add supported_eee storage and start using it in EEE code and by the
  micrel driver.
- add EEE support for ar8035 PHY
- add SmartEEE support to FEC i.MX series.

changes v2:
- use phydev->supported instead of reading MII_BMSR regiaster
- fix @get_eee > @set_eee

With this patch series we provide EEE control for KSZ9477 family of switches and
AR8035 with i.MX6 configuration.
According to my tests, on a system with KSZ8563 switch and 100Mbit idle link,
we consume 0,192W less power per port if EEE is enabled.

Oleksij Rempel (23):
  net: dsa: microchip: enable EEE support
  net: phy: add genphy_c45_read_eee_abilities() function
  net: phy: micrel: add ksz9477_get_features()
  net: phy: export phy_check_valid() function
  net: phy: add genphy_c45_ethtool_get/set_eee() support
  net: phy: c22: migrate to genphy_c45_write_eee_adv()
  net: phy: c45: migrate to genphy_c45_write_eee_adv()
  net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active()
  net: phy: start using genphy_c45_ethtool_get/set_eee()
  net: phy: add driver specific get/set_eee support
  net: phy: at803x: implement ethtool access to SmartEEE functionality
  net: phy: at803x: ar8035: fix EEE support for half duplex links
  net: phy: add PHY specifica flag to signal SmartEEE support
  net: phy: at803x: add PHY_SMART_EEE flag to AR8035
  net: phy: add phy_has_smarteee() helper
  net: fec: add support for PHYs with SmartEEE support
  e1000e: replace EEE ethtool helpers to linkmode variants
  igb: replace EEE ethtool helpers to linkmode variants
  igc: replace EEE ethtool helpers to linkmode variants
  tg3: replace EEE ethtool helpers to linkmode variants
  r8152: replace EEE ethtool helpers to linkmode variants
  net: usb: ax88179_178a: replace EEE ethtool helpers to linkmode
    variants
  net: mdio: drop EEE ethtool helpers in favor to linkmode variants

 drivers/net/dsa/microchip/ksz_common.c       |  66 ++++
 drivers/net/ethernet/broadcom/tg3.c          |   9 +-
 drivers/net/ethernet/freescale/fec_main.c    |  22 +-
 drivers/net/ethernet/intel/e1000e/ethtool.c  |  16 +-
 drivers/net/ethernet/intel/igb/igb_ethtool.c |  23 +-
 drivers/net/ethernet/intel/igc/igc_ethtool.c |  12 +-
 drivers/net/phy/at803x.c                     | 142 ++++++++-
 drivers/net/phy/micrel.c                     |  21 ++
 drivers/net/phy/phy-c45.c                    | 298 ++++++++++++++++++-
 drivers/net/phy/phy.c                        | 155 ++--------
 drivers/net/phy/phy_device.c                 |  26 +-
 drivers/net/usb/ax88179_178a.c               |  24 +-
 drivers/net/usb/r8152.c                      |  34 ++-
 include/linux/mdio.h                         | 136 ++++-----
 include/linux/phy.h                          |  28 ++
 include/uapi/linux/mdio.h                    |   8 +
 16 files changed, 760 insertions(+), 260 deletions(-)

-- 
2.30.2


^ permalink raw reply	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-04  0:14   ` Vladimir Oltean
  2023-02-01 14:58 ` [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function Oleksij Rempel
                   ` (22 subsequent siblings)
  23 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Some of KSZ9477 family switches provides EEE support. To enable it, we
just need to register set_mac_eee/set_mac_eee handlers and validate
supported chip version and port.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/dsa/microchip/ksz_common.c | 66 ++++++++++++++++++++++++++
 1 file changed, 66 insertions(+)

diff --git a/drivers/net/dsa/microchip/ksz_common.c b/drivers/net/dsa/microchip/ksz_common.c
index 46becc0382d6..5ecd74248eee 100644
--- a/drivers/net/dsa/microchip/ksz_common.c
+++ b/drivers/net/dsa/microchip/ksz_common.c
@@ -2673,6 +2673,70 @@ static int ksz_max_mtu(struct dsa_switch *ds, int port)
 	return -EOPNOTSUPP;
 }
 
+static int ksz_validate_eee(struct dsa_switch *ds, int port)
+{
+	struct ksz_device *dev = ds->priv;
+
+	if (!dev->info->internal_phy[port])
+		return -EOPNOTSUPP;
+
+	switch (dev->chip_id) {
+	case KSZ8563_CHIP_ID:
+	case KSZ9477_CHIP_ID:
+	case KSZ9563_CHIP_ID:
+	case KSZ9567_CHIP_ID:
+	case KSZ9893_CHIP_ID:
+	case KSZ9896_CHIP_ID:
+	case KSZ9897_CHIP_ID:
+		return 0;
+	}
+
+	return -EOPNOTSUPP;
+}
+
+static int ksz_get_mac_eee(struct dsa_switch *ds, int port,
+			   struct ethtool_eee *e)
+{
+	int ret;
+
+	ret = ksz_validate_eee(ds, port);
+	if (ret)
+		return ret;
+
+	/* There is no documented control of Tx LPI configuration.
+	 */
+	e->tx_lpi_enabled = true;
+	/* There is no documented control of Tx LPI timer. According to testes
+	 * Tx LPI timer seems to be set by default to minimal value.
+	 */
+	e->tx_lpi_timer = 0;
+
+	return 0;
+}
+
+static int ksz_set_mac_eee(struct dsa_switch *ds, int port,
+			   struct ethtool_eee *e)
+{
+	struct ksz_device *dev = ds->priv;
+	int ret;
+
+	ret = ksz_validate_eee(ds, port);
+	if (ret)
+		return ret;
+
+	if (!e->tx_lpi_enabled) {
+		dev_err(dev->dev, "Disabling EEE Tx LPI is not supported\n");
+		return -EINVAL;
+	}
+
+	if (e->tx_lpi_timer) {
+		dev_err(dev->dev, "Setting EEE Tx LPI timer is not supported\n");
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
 static void ksz_set_xmii(struct ksz_device *dev, int port,
 			 phy_interface_t interface)
 {
@@ -3130,6 +3194,8 @@ static const struct dsa_switch_ops ksz_switch_ops = {
 	.port_txtstamp		= ksz_port_txtstamp,
 	.port_rxtstamp		= ksz_port_rxtstamp,
 	.port_setup_tc		= ksz_setup_tc,
+	.get_mac_eee		= ksz_get_mac_eee,
+	.set_mac_eee		= ksz_set_mac_eee,
 };
 
 struct ksz_device *ksz_switch_alloc(struct device *base, void *priv)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 17:12   ` Andrew Lunn
  2023-02-04  0:54   ` Vladimir Oltean
  2023-02-01 14:58 ` [PATCH net-next v4 03/23] net: phy: micrel: add ksz9477_get_features() Oleksij Rempel
                   ` (21 subsequent siblings)
  23 siblings, 2 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Add generic function for EEE abilities defined by IEEE 802.3
specification. For now following registers are supported:
- IEEE 802.3-2018 45.2.3.10 EEE control and capability 1 (Register 3.20)
- IEEE 802.3cg-2019 45.2.1.186b 10BASE-T1L PMA status register
  (Register 1.2295)

Since I was not able to find any flag signaling support of this
registers, we should detect link mode abilities first and then based on
this abilities doing EEE link modes detection.

Results of EEE ability detection will be stored in to new variable
phydev->supported_eee.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy-c45.c    | 49 ++++++++++++++++++++++++++++++++++++
 drivers/net/phy/phy_device.c | 16 ++++++++++++
 include/linux/mdio.h         | 17 +++++++++++++
 include/linux/phy.h          |  5 ++++
 4 files changed, 87 insertions(+)

diff --git a/drivers/net/phy/phy-c45.c b/drivers/net/phy/phy-c45.c
index 9f9565a4819d..ae87f5856650 100644
--- a/drivers/net/phy/phy-c45.c
+++ b/drivers/net/phy/phy-c45.c
@@ -661,6 +661,55 @@ int genphy_c45_read_mdix(struct phy_device *phydev)
 }
 EXPORT_SYMBOL_GPL(genphy_c45_read_mdix);
 
+/**
+ * genphy_c45_read_eee_abilities - read supported EEE link modes
+ * @phydev: target phy_device struct
+ *
+ * Read supported EEE link modes.
+ */
+int genphy_c45_read_eee_abilities(struct phy_device *phydev)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
+	int val;
+
+	linkmode_and(common, phydev->supported, PHY_EEE_100_10000_FEATURES);
+	/* There is not indicator if optional register
+	 * "EEE control and capability 1" (3.20) is supported. Read it only
+	 * on devices with appropriate linkmodes.
+	 */
+	if (!linkmode_empty(common)) {
+		/* IEEE 802.3-2018 45.2.3.10 EEE control and capability 1
+		 * (Register 3.20)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
+		if (val < 0)
+			return val;
+
+		mii_eee_100_10000_adv_mod_linkmode_t(phydev->supported_eee, val);
+
+		/* Some buggy devices claim not supported EEE link modes */
+		linkmode_and(phydev->supported_eee, phydev->supported_eee,
+			     phydev->supported);
+	}
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+			      phydev->supported)) {
+		/* IEEE 802.3cg-2019 45.2.1.186b 10BASE-T1L PMA status register
+		 * (Register 1.2295)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PMA_10T1L_STAT);
+		if (val < 0)
+			return val;
+
+		linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+				 phydev->supported_eee,
+				 val & MDIO_PMA_10T1L_STAT_EEE);
+	}
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(genphy_c45_read_eee_abilities);
+
 /**
  * genphy_c45_pma_read_abilities - read supported link modes from PMA
  * @phydev: target phy_device struct
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index 9ba8f973f26f..3651f1fd8fc9 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -132,6 +132,18 @@ static const int phy_10gbit_full_features_array[] = {
 	ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
 };
 
+static const int phy_eee_100_10000_features_array[6] = {
+	ETHTOOL_LINK_MODE_100baseT_Full_BIT,
+	ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
+	ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
+	ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
+	ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
+	ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
+};
+
+__ETHTOOL_DECLARE_LINK_MODE_MASK(phy_eee_100_10000_features) __ro_after_init;
+EXPORT_SYMBOL_GPL(phy_eee_100_10000_features);
+
 static void features_init(void)
 {
 	/* 10/100 half/full*/
@@ -213,6 +225,10 @@ static void features_init(void)
 	linkmode_set_bit_array(phy_10gbit_fec_features_array,
 			       ARRAY_SIZE(phy_10gbit_fec_features_array),
 			       phy_10gbit_fec_features);
+	linkmode_set_bit_array(phy_eee_100_10000_features_array,
+			       ARRAY_SIZE(phy_eee_100_10000_features_array),
+			       phy_eee_100_10000_features);
+
 }
 
 void phy_device_free(struct phy_device *phydev)
diff --git a/include/linux/mdio.h b/include/linux/mdio.h
index c0da30d63b1d..77c324f89b66 100644
--- a/include/linux/mdio.h
+++ b/include/linux/mdio.h
@@ -402,6 +402,23 @@ static inline u32 linkmode_adv_to_mii_t1_adv_m_t(unsigned long *advertising)
 	return result;
 }
 
+static inline void mii_eee_100_10000_adv_mod_linkmode_t(unsigned long *adv,
+							u32 val)
+{
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT,
+			 adv, val & MDIO_EEE_100TX);
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
+			 adv, val & MDIO_EEE_1000T);
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
+			 adv, val & MDIO_EEE_10GT);
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
+			 adv, val & MDIO_EEE_1000KX);
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
+			 adv, val & MDIO_EEE_10GKX4);
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
+			 adv, val & MDIO_EEE_10GKR);
+}
+
 int __mdiobus_read(struct mii_bus *bus, int addr, u32 regnum);
 int __mdiobus_write(struct mii_bus *bus, int addr, u32 regnum, u16 val);
 int __mdiobus_modify_changed(struct mii_bus *bus, int addr, u32 regnum,
diff --git a/include/linux/phy.h b/include/linux/phy.h
index fbeba4fee8d4..567810f71fb6 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -52,6 +52,7 @@ extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_gbit_all_ports_features) __ro_after_
 extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_10gbit_features) __ro_after_init;
 extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_10gbit_fec_features) __ro_after_init;
 extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_10gbit_full_features) __ro_after_init;
+extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_eee_100_10000_features) __ro_after_init;
 
 #define PHY_BASIC_FEATURES ((unsigned long *)&phy_basic_features)
 #define PHY_BASIC_T1_FEATURES ((unsigned long *)&phy_basic_t1_features)
@@ -62,6 +63,7 @@ extern __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_10gbit_full_features) __ro_after_ini
 #define PHY_10GBIT_FEATURES ((unsigned long *)&phy_10gbit_features)
 #define PHY_10GBIT_FEC_FEATURES ((unsigned long *)&phy_10gbit_fec_features)
 #define PHY_10GBIT_FULL_FEATURES ((unsigned long *)&phy_10gbit_full_features)
+#define PHY_EEE_100_10000_FEATURES ((unsigned long *)&phy_eee_100_10000_features)
 
 extern const int phy_basic_ports_array[3];
 extern const int phy_fibre_port_array[1];
@@ -676,6 +678,8 @@ struct phy_device {
 	__ETHTOOL_DECLARE_LINK_MODE_MASK(lp_advertising);
 	/* used with phy_speed_down */
 	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv_old);
+	/* used for eee validation */
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(supported_eee);
 
 	/* Host supported PHY interface types. Should be ignored if empty. */
 	DECLARE_PHY_INTERFACE_MASK(host_interfaces);
@@ -1737,6 +1741,7 @@ int genphy_c45_an_config_aneg(struct phy_device *phydev);
 int genphy_c45_an_disable_aneg(struct phy_device *phydev);
 int genphy_c45_read_mdix(struct phy_device *phydev);
 int genphy_c45_pma_read_abilities(struct phy_device *phydev);
+int genphy_c45_read_eee_abilities(struct phy_device *phydev);
 int genphy_c45_pma_baset1_read_master_slave(struct phy_device *phydev);
 int genphy_c45_read_status(struct phy_device *phydev);
 int genphy_c45_baset1_read_status(struct phy_device *phydev);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 03/23] net: phy: micrel: add ksz9477_get_features()
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function Oleksij Rempel
                   ` (20 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

KSZ8563R, which has same PHYID as KSZ9477 family, will change "EEE control
and capability 1" (Register 3.20) content depending on configuration of
"EEE advertisement 1" (Register 7.60). Changes on the 7.60 will affect
3.20 register.

So, instead of depending on register 3.20 driver should set supported_eee.

Proper supported_eee configuration is needed to make use of generic
PHY c45 set/get_eee functions provided by next patches.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/micrel.c | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/drivers/net/phy/micrel.c b/drivers/net/phy/micrel.c
index d5b80c31ab91..767c4111cb18 100644
--- a/drivers/net/phy/micrel.c
+++ b/drivers/net/phy/micrel.c
@@ -1370,6 +1370,26 @@ static int ksz9131_config_aneg(struct phy_device *phydev)
 	return genphy_config_aneg(phydev);
 }
 
+static int ksz9477_get_features(struct phy_device *phydev)
+{
+	int ret;
+
+	ret = genphy_read_abilities(phydev);
+	if (ret)
+		return ret;
+
+	/* The "EEE control and capability 1" (Register 3.20) seems to be
+	 * influenced by the "EEE advertisement 1" (Register 7.60). Changes
+	 * on the 7.60 will affect 3.20. So, we need to construct our own list
+	 * of caps.
+	 * KSZ8563R should have 100BaseTX/Full only.
+	 */
+	linkmode_and(phydev->supported_eee, phydev->supported,
+		     PHY_EEE_100_10000_FEATURES);
+
+	return 0;
+}
+
 #define KSZ8873MLL_GLOBAL_CONTROL_4	0x06
 #define KSZ8873MLL_GLOBAL_CONTROL_4_DUPLEX	BIT(6)
 #define KSZ8873MLL_GLOBAL_CONTROL_4_SPEED	BIT(4)
@@ -3422,6 +3442,7 @@ static struct phy_driver ksphy_driver[] = {
 	.handle_interrupt = kszphy_handle_interrupt,
 	.suspend	= genphy_suspend,
 	.resume		= genphy_resume,
+	.get_features	= ksz9477_get_features,
 } };
 
 module_phy_driver(ksphy_driver);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (2 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 03/23] net: phy: micrel: add ksz9477_get_features() Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 17:15   ` Andrew Lunn
  2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
                   ` (19 subsequent siblings)
  23 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

This function will be needed for genphy_c45_ethtool_get_eee() provided
by next patch.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy.c | 4 ++--
 include/linux/phy.h   | 1 +
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 3378ca4f49b6..41cfb24c48c1 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -242,11 +242,11 @@ unsigned int phy_supported_speeds(struct phy_device *phy,
  *
  * Description: Returns true if there is a valid setting, false otherwise.
  */
-static inline bool phy_check_valid(int speed, int duplex,
-				   unsigned long *features)
+bool phy_check_valid(int speed, int duplex, unsigned long *features)
 {
 	return !!phy_lookup_setting(speed, duplex, features, true);
 }
+EXPORT_SYMBOL(phy_check_valid);
 
 /**
  * phy_sanitize_settings - make sure the PHY is set to supported speed and duplex
diff --git a/include/linux/phy.h b/include/linux/phy.h
index 567810f71fb6..fa8453c48ad1 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -1618,6 +1618,7 @@ int phy_start_aneg(struct phy_device *phydev);
 int phy_aneg_done(struct phy_device *phydev);
 int phy_speed_down(struct phy_device *phydev, bool sync);
 int phy_speed_up(struct phy_device *phydev);
+bool phy_check_valid(int speed, int duplex, unsigned long *features);
 
 int phy_restart_aneg(struct phy_device *phydev);
 int phy_reset_after_clk_enable(struct phy_device *phydev);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (3 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 17:20   ` Andrew Lunn
                     ` (2 more replies)
  2023-02-01 14:58 ` [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv() Oleksij Rempel
                   ` (18 subsequent siblings)
  23 siblings, 3 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Add replacement for phy_ethtool_get/set_eee() functions.

Current phy_ethtool_get/set_eee() implementation is great and it is
possible to make it even better:
- this functionality is for devices implementing parts of IEEE 802.3
  specification beyond Clause 22. The better place for this code is
  phy-c45.c
- currently it is able to do read/write operations on PHYs with
  different abilities to not existing registers. It is better to
  use stored supported_eee abilities to avoid false read/write
  operations.
- the eee_active detection will provide wrong results on not supported
  link modes. It is better to validate speed/duplex properties against
  supported EEE link modes.
- it is able to support only limited amount of link modes. We have more
  EEE link modes...

By refactoring this code I address most of this point except of the last
one. Adding additional EEE link modes will need more work.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy-c45.c | 238 ++++++++++++++++++++++++++++++++++++++
 include/linux/mdio.h      |  36 ++++++
 include/linux/phy.h       |   7 ++
 include/uapi/linux/mdio.h |   8 ++
 4 files changed, 289 insertions(+)

diff --git a/drivers/net/phy/phy-c45.c b/drivers/net/phy/phy-c45.c
index ae87f5856650..9582c8bf74ec 100644
--- a/drivers/net/phy/phy-c45.c
+++ b/drivers/net/phy/phy-c45.c
@@ -661,6 +661,132 @@ int genphy_c45_read_mdix(struct phy_device *phydev)
 }
 EXPORT_SYMBOL_GPL(genphy_c45_read_mdix);
 
+/**
+ * genphy_c45_write_eee_adv - write advertised EEE link modes
+ * @phydev: target phy_device struct
+ */
+int genphy_c45_write_eee_adv(struct phy_device *phydev, unsigned long *adv)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
+	int val, changed;
+
+	linkmode_and(common, phydev->supported_eee, PHY_EEE_100_10000_FEATURES);
+	if (!linkmode_empty(common)) {
+		val = linkmode_adv_to_mii_eee_100_10000_adv_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)
+		 */
+		val = phy_modify_mmd_changed(phydev, MDIO_MMD_AN,
+					     MDIO_AN_EEE_ADV,
+					     MDIO_EEE_100TX | MDIO_EEE_1000T |
+					     MDIO_EEE_10GT | MDIO_EEE_1000KX |
+					     MDIO_EEE_10GKX4 | MDIO_EEE_10GKR,
+					     val);
+		if (val < 0)
+			return val;
+		if (val > 0)
+			changed = 1;
+	}
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+			      phydev->supported_eee)) {
+		val = linkmode_adv_to_mii_10base_t1_t(adv);
+		/* IEEE 802.3cg-2019 45.2.7.25 10BASE-T1 AN control register
+		 * (Register 7.526)
+		 */
+		val = phy_modify_mmd_changed(phydev, MDIO_MMD_AN,
+					     MDIO_AN_10BT1_AN_CTRL,
+					     MDIO_AN_10BT1_AN_CTRL_ADV_EEE_T1L,
+					     val);
+		if (val < 0)
+			return val;
+		if (val > 0)
+			changed = 1;
+	}
+
+	return changed;
+}
+
+/**
+ * genphy_c45_read_eee_adv - read advertised EEE link modes
+ * @phydev: target phy_device struct
+ */
+static int genphy_c45_read_eee_adv(struct phy_device *phydev,
+				   unsigned long *adv)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
+	int val;
+
+	linkmode_and(common, phydev->supported_eee, PHY_EEE_100_10000_FEATURES);
+	if (!linkmode_empty(common)) {
+		/* IEEE 802.3-2018 45.2.7.13 EEE advertisement 1
+		 * (Register 7.60)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
+		if (val < 0)
+			return val;
+
+		mii_eee_100_10000_adv_mod_linkmode_t(adv, val);
+	}
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+			      phydev->supported_eee)) {
+		/* IEEE 802.3cg-2019 45.2.7.25 10BASE-T1 AN control register
+		 * (Register 7.526)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_10BT1_AN_CTRL);
+		if (val < 0)
+			return val;
+
+		mii_10base_t1_adv_mod_linkmode_t(adv, val);
+	}
+
+	return 0;
+}
+
+/**
+ * genphy_c45_read_eee_lpa - read advertised LP EEE link modes
+ * @phydev: target phy_device struct
+ */
+static int genphy_c45_read_eee_lpa(struct phy_device *phydev,
+				   unsigned long *lpa)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
+	int val;
+
+	linkmode_and(common, phydev->supported_eee, PHY_EEE_100_10000_FEATURES);
+	if (!linkmode_empty(common)) {
+		/* IEEE 802.3-2018 45.2.7.14 EEE link partner ability 1
+		 * (Register 7.61)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_LPABLE);
+		if (val < 0)
+			return val;
+
+		mii_eee_100_10000_adv_mod_linkmode_t(lpa, val);
+	}
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+			      phydev->supported_eee)) {
+		/* IEEE 802.3cg-2019 45.2.7.26 10BASE-T1 AN status register
+		 * (Register 7.527)
+		 */
+		val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_10BT1_AN_STAT);
+		if (val < 0)
+			return val;
+
+		mii_10base_t1_adv_mod_linkmode_t(lpa, val);
+	}
+
+	return 0;
+}
+
 /**
  * genphy_c45_read_eee_abilities - read supported EEE link modes
  * @phydev: target phy_device struct
@@ -1173,6 +1299,118 @@ int genphy_c45_plca_get_status(struct phy_device *phydev,
 }
 EXPORT_SYMBOL_GPL(genphy_c45_plca_get_status);
 
+/**
+ * genphy_c45_eee_is_active - get EEE supported and status
+ * @phydev: target phy_device struct
+ * @data: ethtool_eee data
+ *
+ * Description: it reports the possible state of EEE functionality.
+ */
+int genphy_c45_eee_is_active(struct phy_device *phydev, unsigned long *adv,
+			     unsigned long *lp, bool *is_enabled)
+{
+	__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;
+
+	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;
+}
+EXPORT_SYMBOL(genphy_c45_eee_is_active);
+
+/**
+ * genphy_c45_ethtool_get_eee - get EEE supported and status
+ * @phydev: target phy_device struct
+ * @data: ethtool_eee data
+ *
+ * Description: it reports the Supported/Advertisement/LP Advertisement
+ * capabilities.
+ */
+int genphy_c45_ethtool_get_eee(struct phy_device *phydev,
+			       struct ethtool_eee *data)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lp) = {};
+	bool overflow = false, is_enabled;
+	int ret;
+
+	ret = genphy_c45_eee_is_active(phydev, adv, lp, &is_enabled);
+	if (ret < 0)
+		return ret;
+
+	data->eee_enabled = is_enabled;
+	data->eee_active = ret;
+
+	if (!ethtool_convert_link_mode_to_legacy_u32(&data->supported,
+						     phydev->supported_eee))
+		overflow = true;
+	if (!ethtool_convert_link_mode_to_legacy_u32(&data->advertised, adv))
+		overflow = true;
+	if (!ethtool_convert_link_mode_to_legacy_u32(&data->lp_advertised, lp))
+		overflow = true;
+
+	if (overflow)
+		phydev_warn(phydev, "Not all supported or advertised EEE link modes was passed to the user space\n");
+
+	return 0;
+}
+EXPORT_SYMBOL(genphy_c45_ethtool_get_eee);
+
+/**
+ * genphy_c45_ethtool_set_eee - get EEE supported and status
+ * @phydev: target phy_device struct
+ * @data: ethtool_eee data
+ *
+ * Description: it reportes the Supported/Advertisement/LP Advertisement
+ * capabilities.
+ */
+int genphy_c45_ethtool_set_eee(struct phy_device *phydev,
+			       struct ethtool_eee *data)
+{
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	int ret;
+
+	if (data->eee_enabled) {
+		if (data->advertised)
+			adv[0] = data->advertised;
+		else
+			linkmode_copy(adv, phydev->supported_eee);
+	}
+
+	ret = genphy_c45_write_eee_adv(phydev, adv);
+	if (ret < 0)
+		return ret;
+	if (ret > 0)
+		return phy_restart_aneg(phydev);
+
+	return 0;
+}
+EXPORT_SYMBOL(genphy_c45_ethtool_set_eee);
+
 struct phy_driver genphy_c45_driver = {
 	.phy_id         = 0xffffffff,
 	.phy_id_mask    = 0xffffffff,
diff --git a/include/linux/mdio.h b/include/linux/mdio.h
index 77c324f89b66..fcd5492e4993 100644
--- a/include/linux/mdio.h
+++ b/include/linux/mdio.h
@@ -419,6 +419,42 @@ static inline void mii_eee_100_10000_adv_mod_linkmode_t(unsigned long *adv,
 			 adv, val & MDIO_EEE_10GKR);
 }
 
+static inline u32 linkmode_adv_to_mii_eee_100_10000_adv_t(unsigned long *adv)
+{
+	u32 result = 0;
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT, adv))
+		result |= MDIO_EEE_100TX;
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT, adv))
+		result |= MDIO_EEE_1000T;
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT, adv))
+		result |= MDIO_EEE_10GT;
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseKX_Full_BIT, adv))
+		result |= MDIO_EEE_1000KX;
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT, adv))
+		result |= MDIO_EEE_10GKX4;
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT, adv))
+		result |= MDIO_EEE_10GKR;
+
+	return result;
+}
+
+static inline void mii_10base_t1_adv_mod_linkmode_t(unsigned long *adv, u16 val)
+{
+	linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
+			 adv, val & MDIO_AN_10BT1_AN_CTRL_ADV_EEE_T1L);
+}
+
+static inline u32 linkmode_adv_to_mii_10base_t1_t(unsigned long *adv)
+{
+	u32 result = 0;
+
+	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT, adv))
+		result |= MDIO_AN_10BT1_AN_CTRL_ADV_EEE_T1L;
+
+	return result;
+}
+
 int __mdiobus_read(struct mii_bus *bus, int addr, u32 regnum);
 int __mdiobus_write(struct mii_bus *bus, int addr, u32 regnum, u16 val);
 int __mdiobus_modify_changed(struct mii_bus *bus, int addr, u32 regnum,
diff --git a/include/linux/phy.h b/include/linux/phy.h
index fa8453c48ad1..f8fbbf137ece 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -1757,6 +1757,13 @@ int genphy_c45_plca_set_cfg(struct phy_device *phydev,
 			    const struct phy_plca_cfg *plca_cfg);
 int genphy_c45_plca_get_status(struct phy_device *phydev,
 			       struct phy_plca_status *plca_st);
+int genphy_c45_eee_is_active(struct phy_device *phydev, unsigned long *adv,
+			     unsigned long *lp, bool *is_enabled);
+int genphy_c45_ethtool_get_eee(struct phy_device *phydev,
+			       struct ethtool_eee *data);
+int genphy_c45_ethtool_set_eee(struct phy_device *phydev,
+			       struct ethtool_eee *data);
+int genphy_c45_write_eee_adv(struct phy_device *phydev, unsigned long *adv);
 
 /* Generic C45 PHY driver */
 extern struct phy_driver genphy_c45_driver;
diff --git a/include/uapi/linux/mdio.h b/include/uapi/linux/mdio.h
index 75b7257a51e1..256b463e47a6 100644
--- a/include/uapi/linux/mdio.h
+++ b/include/uapi/linux/mdio.h
@@ -79,6 +79,8 @@
 #define MDIO_AN_T1_LP_L		517	/* BASE-T1 AN LP Base Page ability register [15:0] */
 #define MDIO_AN_T1_LP_M		518	/* BASE-T1 AN LP Base Page ability register [31:16] */
 #define MDIO_AN_T1_LP_H		519	/* BASE-T1 AN LP Base Page ability register [47:32] */
+#define MDIO_AN_10BT1_AN_CTRL	526	/* 10BASE-T1 AN control register */
+#define MDIO_AN_10BT1_AN_STAT	527	/* 10BASE-T1 AN status register */
 #define MDIO_PMA_PMD_BT1_CTRL	2100	/* BASE-T1 PMA/PMD control register */
 
 /* LASI (Link Alarm Status Interrupt) registers, defined by XENPAK MSA. */
@@ -340,6 +342,12 @@
 #define MDIO_AN_T1_LP_H_10L_TX_HI_REQ	0x1000	/* 10BASE-T1L High Level LP Transmit Request */
 #define MDIO_AN_T1_LP_H_10L_TX_HI	0x2000	/* 10BASE-T1L High Level LP Transmit Ability */
 
+/* 10BASE-T1 AN control register */
+#define MDIO_AN_10BT1_AN_CTRL_ADV_EEE_T1L	0x4000 /* 10BASE-T1L EEE ability advertisement */
+
+/* 10BASE-T1 AN status register */
+#define MDIO_AN_10BT1_AN_STAT_LPA_EEE_T1L	0x4000 /* 10BASE-T1L LP EEE ability advertisement */
+
 /* BASE-T1 PMA/PMD control register */
 #define MDIO_PMA_PMD_BT1_CTRL_CFG_MST	0x4000 /* MASTER-SLAVE config value */
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv()
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (4 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 17:28   ` Andrew Lunn
  2023-02-01 14:58 ` [PATCH net-next v4 07/23] net: phy: c45: " Oleksij Rempel
                   ` (17 subsequent siblings)
  23 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Migrate from genphy_config_eee_advert() to genphy_c45_write_eee_adv().

It should work as before except write operation to the EEE adv registers
will be done only if some EEE abilities was detected.

If some driver will have a regression, related driver should provide own
.get_features callback. See micrel.c:ksz9477_get_features() as example.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy_device.c | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index 3651f1fd8fc9..0c47fa765b69 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -2231,7 +2231,10 @@ int __genphy_config_aneg(struct phy_device *phydev, bool changed)
 {
 	int err;
 
-	if (genphy_config_eee_advert(phydev))
+	err = genphy_c45_write_eee_adv(phydev, phydev->supported_eee);
+	if (err < 0)
+		return err;
+	else if (err)
 		changed = true;
 
 	err = genphy_setup_master_slave(phydev);
@@ -2653,6 +2656,11 @@ int genphy_read_abilities(struct phy_device *phydev)
 				 phydev->supported, val & ESTATUS_1000_XFULL);
 	}
 
+	/* This is optional functionality. If not supported, we may get an error
+	 * which should be ignored.
+	 */
+	genphy_c45_read_eee_abilities(phydev);
+
 	return 0;
 }
 EXPORT_SYMBOL(genphy_read_abilities);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 07/23] net: phy: c45: migrate to genphy_c45_write_eee_adv()
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (5 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv() Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active() Oleksij Rempel
                   ` (16 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Migrate from genphy_config_eee_advert() to genphy_c45_write_eee_adv().

It should work as before except write operation to the EEE adv registers
will be done only if some EEE abilities was detected.

If some driver will have a regression, related driver should provide own
.get_features callback. See micrel.c:ksz9477_get_features() as example.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy-c45.c | 11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)

diff --git a/drivers/net/phy/phy-c45.c b/drivers/net/phy/phy-c45.c
index 9582c8bf74ec..6149e8c3243f 100644
--- a/drivers/net/phy/phy-c45.c
+++ b/drivers/net/phy/phy-c45.c
@@ -262,7 +262,11 @@ int genphy_c45_an_config_aneg(struct phy_device *phydev)
 	linkmode_and(phydev->advertising, phydev->advertising,
 		     phydev->supported);
 
-	changed = genphy_config_eee_advert(phydev);
+	ret = genphy_c45_write_eee_adv(phydev, phydev->supported_eee);
+	if (ret < 0)
+		return ret;
+	else if (ret)
+		changed = true;
 
 	if (genphy_c45_baset1_able(phydev))
 		return genphy_c45_baset1_an_config_aneg(phydev);
@@ -950,6 +954,11 @@ int genphy_c45_pma_read_abilities(struct phy_device *phydev)
 		}
 	}
 
+	/* This is optional functionality. If not supported, we may get an error
+	 * which should be ignored.
+	 */
+	genphy_c45_read_eee_abilities(phydev);
+
 	return 0;
 }
 EXPORT_SYMBOL_GPL(genphy_c45_pma_read_abilities);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active()
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (6 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 07/23] net: phy: c45: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 16:41   ` Andrew Lunn
  2023-02-01 14:58 ` [PATCH net-next v4 09/23] net: phy: start using genphy_c45_ethtool_get/set_eee() Oleksij Rempel
                   ` (15 subsequent siblings)
  23 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Reduce code duplicated by migrating phy_init_eee() to
genphy_c45_eee_is_active().

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy.c | 89 +++++++------------------------------------
 1 file changed, 14 insertions(+), 75 deletions(-)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 41cfb24c48c1..36533746630e 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -1457,30 +1457,6 @@ void phy_mac_interrupt(struct phy_device *phydev)
 }
 EXPORT_SYMBOL(phy_mac_interrupt);
 
-static void mmd_eee_adv_to_linkmode(unsigned long *advertising, u16 eee_adv)
-{
-	linkmode_zero(advertising);
-
-	if (eee_adv & MDIO_EEE_100TX)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT,
-				 advertising);
-	if (eee_adv & MDIO_EEE_1000T)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
-				 advertising);
-	if (eee_adv & MDIO_EEE_10GT)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
-				 advertising);
-	if (eee_adv & MDIO_EEE_1000KX)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
-				 advertising);
-	if (eee_adv & MDIO_EEE_10GKX4)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
-				 advertising);
-	if (eee_adv & MDIO_EEE_10GKR)
-		linkmode_set_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
-				 advertising);
-}
-
 /**
  * phy_init_eee - init and check the EEE feature
  * @phydev: target phy_device struct
@@ -1493,62 +1469,25 @@ static void mmd_eee_adv_to_linkmode(unsigned long *advertising, u16 eee_adv)
  */
 int phy_init_eee(struct phy_device *phydev, bool clk_stop_enable)
 {
+	int ret;
+
 	if (!phydev->drv)
 		return -EIO;
 
-	/* According to 802.3az,the EEE is supported only in full duplex-mode.
-	 */
-	if (phydev->duplex == DUPLEX_FULL) {
-		__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
-		__ETHTOOL_DECLARE_LINK_MODE_MASK(lp);
-		__ETHTOOL_DECLARE_LINK_MODE_MASK(adv);
-		int eee_lp, eee_cap, eee_adv;
-		int status;
-		u32 cap;
-
-		/* Read phy status to properly get the right settings */
-		status = phy_read_status(phydev);
-		if (status)
-			return status;
-
-		/* First check if the EEE ability is supported */
-		eee_cap = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
-		if (eee_cap <= 0)
-			goto eee_exit_err;
-
-		cap = mmd_eee_cap_to_ethtool_sup_t(eee_cap);
-		if (!cap)
-			goto eee_exit_err;
-
-		/* Check which link settings negotiated and verify it in
-		 * the EEE advertising registers.
-		 */
-		eee_lp = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_LPABLE);
-		if (eee_lp <= 0)
-			goto eee_exit_err;
-
-		eee_adv = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
-		if (eee_adv <= 0)
-			goto eee_exit_err;
-
-		mmd_eee_adv_to_linkmode(adv, eee_adv);
-		mmd_eee_adv_to_linkmode(lp, eee_lp);
-		linkmode_and(common, adv, lp);
-
-		if (!phy_check_valid(phydev->speed, phydev->duplex, common))
-			goto eee_exit_err;
+	ret = genphy_c45_eee_is_active(phydev, NULL, NULL, NULL);
+	if (ret < 0)
+		return ret;
+	if (!ret)
+		return -EPROTONOSUPPORT;
 
-		if (clk_stop_enable)
-			/* Configure the PHY to stop receiving xMII
-			 * clock while it is signaling LPI.
-			 */
-			phy_set_bits_mmd(phydev, MDIO_MMD_PCS, MDIO_CTRL1,
-					 MDIO_PCS_CTRL1_CLKSTOP_EN);
+	if (clk_stop_enable)
+		/* Configure the PHY to stop receiving xMII
+		 * clock while it is signaling LPI.
+		 */
+		ret = phy_set_bits_mmd(phydev, MDIO_MMD_PCS, MDIO_CTRL1,
+				       MDIO_PCS_CTRL1_CLKSTOP_EN);
 
-		return 0; /* EEE supported */
-	}
-eee_exit_err:
-	return -EPROTONOSUPPORT;
+	return ret < 0 ? ret : 0;
 }
 EXPORT_SYMBOL(phy_init_eee);
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 09/23] net: phy: start using genphy_c45_ethtool_get/set_eee()
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (7 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active() Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 10/23] net: phy: add driver specific get/set_eee support Oleksij Rempel
                   ` (14 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

All preparations are done. Now we can start using new functions and remove
the old code.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy.c | 60 ++-----------------------------------------
 1 file changed, 2 insertions(+), 58 deletions(-)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 36533746630e..2f1041a7211e 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -1517,33 +1517,10 @@ EXPORT_SYMBOL(phy_get_eee_err);
  */
 int phy_ethtool_get_eee(struct phy_device *phydev, struct ethtool_eee *data)
 {
-	int val;
-
 	if (!phydev->drv)
 		return -EIO;
 
-	/* Get Supported EEE */
-	val = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
-	if (val < 0)
-		return val;
-	data->supported = mmd_eee_cap_to_ethtool_sup_t(val);
-
-	/* Get advertisement EEE */
-	val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
-	if (val < 0)
-		return val;
-	data->advertised = mmd_eee_adv_to_ethtool_adv_t(val);
-	data->eee_enabled = !!data->advertised;
-
-	/* Get LP advertisement EEE */
-	val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_LPABLE);
-	if (val < 0)
-		return val;
-	data->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(val);
-
-	data->eee_active = !!(data->advertised & data->lp_advertised);
-
-	return 0;
+	return genphy_c45_ethtool_get_eee(phydev, data);
 }
 EXPORT_SYMBOL(phy_ethtool_get_eee);
 
@@ -1556,43 +1533,10 @@ EXPORT_SYMBOL(phy_ethtool_get_eee);
  */
 int phy_ethtool_set_eee(struct phy_device *phydev, struct ethtool_eee *data)
 {
-	int cap, old_adv, adv = 0, ret;
-
 	if (!phydev->drv)
 		return -EIO;
 
-	/* Get Supported EEE */
-	cap = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
-	if (cap < 0)
-		return cap;
-
-	old_adv = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
-	if (old_adv < 0)
-		return old_adv;
-
-	if (data->eee_enabled) {
-		adv = !data->advertised ? cap :
-		      ethtool_adv_to_mmd_eee_adv_t(data->advertised) & cap;
-		/* Mask prohibited EEE modes */
-		adv &= ~phydev->eee_broken_modes;
-	}
-
-	if (old_adv != adv) {
-		ret = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV, adv);
-		if (ret < 0)
-			return ret;
-
-		/* Restart autonegotiation so the new modes get sent to the
-		 * link partner.
-		 */
-		if (phydev->autoneg == AUTONEG_ENABLE) {
-			ret = phy_restart_aneg(phydev);
-			if (ret < 0)
-				return ret;
-		}
-	}
-
-	return 0;
+	return genphy_c45_ethtool_set_eee(phydev, data);
 }
 EXPORT_SYMBOL(phy_ethtool_set_eee);
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 10/23] net: phy: add driver specific get/set_eee support
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (8 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 09/23] net: phy: start using genphy_c45_ethtool_get/set_eee() Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 11/23] net: phy: at803x: implement ethtool access to SmartEEE functionality Oleksij Rempel
                   ` (13 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Not all PHYs can be handled by generic phy_ethtool_get/set_eee()
functions. So, add driver specific get/set_eee support.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/phy.c | 6 ++++++
 include/linux/phy.h   | 5 +++++
 2 files changed, 11 insertions(+)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 2f1041a7211e..c42df62df302 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -1520,6 +1520,9 @@ int phy_ethtool_get_eee(struct phy_device *phydev, struct ethtool_eee *data)
 	if (!phydev->drv)
 		return -EIO;
 
+	if (phydev->drv->get_eee)
+		return phydev->drv->get_eee(phydev, data);
+
 	return genphy_c45_ethtool_get_eee(phydev, data);
 }
 EXPORT_SYMBOL(phy_ethtool_get_eee);
@@ -1536,6 +1539,9 @@ int phy_ethtool_set_eee(struct phy_device *phydev, struct ethtool_eee *data)
 	if (!phydev->drv)
 		return -EIO;
 
+	if (phydev->drv->set_eee)
+		return phydev->drv->set_eee(phydev, data);
+
 	return genphy_c45_ethtool_set_eee(phydev, data);
 }
 EXPORT_SYMBOL(phy_ethtool_set_eee);
diff --git a/include/linux/phy.h b/include/linux/phy.h
index f8fbbf137ece..89556cb2c555 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -1051,6 +1051,11 @@ struct phy_driver {
 	/** @get_plca_status: Return the current PLCA status info */
 	int (*get_plca_status)(struct phy_device *dev,
 			       struct phy_plca_status *plca_st);
+
+	/** @get_eee: Return the current EEE configuration */
+	int (*get_eee)(struct phy_device *phydev, struct ethtool_eee *e);
+	/** @set_eee: Set the EEE configuration */
+	int (*set_eee)(struct phy_device *phydev, struct ethtool_eee *e);
 };
 #define to_phy_driver(d) container_of(to_mdio_common_driver(d),		\
 				      struct phy_driver, mdiodrv)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 11/23] net: phy: at803x: implement ethtool access to SmartEEE functionality
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (9 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 10/23] net: phy: add driver specific get/set_eee support Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 12/23] net: phy: at803x: ar8035: fix EEE support for half duplex links Oleksij Rempel
                   ` (12 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

If AR8035 PHY is used with a MAC without EEE support
(iMX6, etc), then we need to process ethtool_eee::tx_lpi_timer and
tx_lpi_enabled by the PHY driver. So, add get/set_eee support for this
functionality.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/at803x.c | 109 +++++++++++++++++++++++++++++++++++++--
 1 file changed, 104 insertions(+), 5 deletions(-)

diff --git a/drivers/net/phy/at803x.c b/drivers/net/phy/at803x.c
index 22f4458274aa..9eb4439b0afc 100644
--- a/drivers/net/phy/at803x.c
+++ b/drivers/net/phy/at803x.c
@@ -166,8 +166,18 @@
 
 #define AT803X_MMD3_SMARTEEE_CTL1		0x805b
 #define AT803X_MMD3_SMARTEEE_CTL2		0x805c
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_LOW	GENMASK(15, 0)
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_15_0	GENMASK(15, 0)
 #define AT803X_MMD3_SMARTEEE_CTL3		0x805d
 #define AT803X_MMD3_SMARTEEE_CTL3_LPI_EN	BIT(8)
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH	GENMASK(7, 0)
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_23_16	GENMASK(23, 16)
+/* Tx LPI timer resolution */
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_RESOL_NS	163840
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_MAX_US	\
+	((GENMASK(23, 0) * AT803X_MMD3_SMARTEEE_LPI_TIME_RESOL_NS) / \
+	       NSEC_PER_USEC)
+#define AT803X_MMD3_SMARTEEE_LPI_TIME_DEF_US	335544
 
 #define ATH9331_PHY_ID				0x004dd041
 #define ATH8030_PHY_ID				0x004dd076
@@ -951,17 +961,26 @@ static int at803x_get_features(struct phy_device *phydev)
 	return 0;
 }
 
-static int at803x_smarteee_config(struct phy_device *phydev)
+static int at803x_smarteee_config(struct phy_device *phydev, bool enable,
+				  u32 tx_lpi_timer_us)
 {
 	struct at803x_priv *priv = phydev->priv;
+	u64 tx_lpi_timer_raw;
+	u64 tx_lpi_timer_ns;
 	u16 mask = 0, val = 0;
 	int ret;
 
-	if (priv->flags & AT803X_DISABLE_SMARTEEE)
+	if (priv->flags & AT803X_DISABLE_SMARTEEE || !enable)
 		return phy_modify_mmd(phydev, MDIO_MMD_PCS,
 				      AT803X_MMD3_SMARTEEE_CTL3,
 				      AT803X_MMD3_SMARTEEE_CTL3_LPI_EN, 0);
 
+	if (tx_lpi_timer_us > AT803X_MMD3_SMARTEEE_LPI_TIME_MAX_US) {
+		phydev_err(phydev, "Max LPI timer is %lu microsecs\n",
+			   AT803X_MMD3_SMARTEEE_LPI_TIME_MAX_US);
+		return -EINVAL;
+	}
+
 	if (priv->smarteee_lpi_tw_1g) {
 		mask |= 0xff00;
 		val |= priv->smarteee_lpi_tw_1g << 8;
@@ -978,9 +997,27 @@ static int at803x_smarteee_config(struct phy_device *phydev)
 	if (ret)
 		return ret;
 
+	tx_lpi_timer_ns = tx_lpi_timer_us * NSEC_PER_USEC;
+	tx_lpi_timer_raw =
+		DIV_ROUND_CLOSEST_ULL(tx_lpi_timer_ns,
+				      AT803X_MMD3_SMARTEEE_LPI_TIME_RESOL_NS);
+	val = FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_LOW,
+			 FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_15_0,
+				   tx_lpi_timer_raw));
+
+	ret = phy_write_mmd(phydev, MDIO_MMD_PCS, AT803X_MMD3_SMARTEEE_CTL2,
+			    val);
+	if (ret)
+		return ret;
+
+	val = AT803X_MMD3_SMARTEEE_CTL3_LPI_EN |
+		FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH,
+			   FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_23_16,
+				     tx_lpi_timer_raw));
+
 	return phy_modify_mmd(phydev, MDIO_MMD_PCS, AT803X_MMD3_SMARTEEE_CTL3,
-			      AT803X_MMD3_SMARTEEE_CTL3_LPI_EN,
-			      AT803X_MMD3_SMARTEEE_CTL3_LPI_EN);
+			      AT803X_MMD3_SMARTEEE_CTL3_LPI_EN |
+			      AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH, val);
 }
 
 static int at803x_clk_out_config(struct phy_device *phydev)
@@ -1067,7 +1104,8 @@ static int at803x_config_init(struct phy_device *phydev)
 	if (ret < 0)
 		return ret;
 
-	ret = at803x_smarteee_config(phydev);
+	ret = at803x_smarteee_config(phydev, true,
+				     AT803X_MMD3_SMARTEEE_LPI_TIME_DEF_US);
 	if (ret < 0)
 		return ret;
 
@@ -1612,6 +1650,65 @@ static int at803x_cable_test_start(struct phy_device *phydev)
 	return 0;
 }
 
+static int at803x_get_eee(struct phy_device *phydev, struct ethtool_eee *data)
+{
+	struct at803x_priv *priv = phydev->priv;
+	u32 tx_timer_raw;
+	u64 tx_timer_ns;
+	int ret;
+
+	/* If SmartEEE is not enabled, it is expected that tx_lpi_* fields
+	 * are processed by the MAC driver.
+	 */
+	if (priv->flags & AT803X_DISABLE_SMARTEEE)
+		return genphy_c45_ethtool_get_eee(phydev, data);
+
+	ret = phy_read_mmd(phydev, MDIO_MMD_PCS,
+			   AT803X_MMD3_SMARTEEE_CTL2);
+	tx_timer_raw = FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_15_0,
+				  FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_LOW,
+					    ret));
+	if (ret < 0)
+		return ret;
+
+	ret = phy_read_mmd(phydev, MDIO_MMD_PCS,
+			   AT803X_MMD3_SMARTEEE_CTL3);
+	if (ret < 0)
+		return ret;
+
+	tx_timer_raw |= FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_23_16,
+				   FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH,
+					     ret));
+	tx_timer_ns = tx_timer_raw * AT803X_MMD3_SMARTEEE_LPI_TIME_RESOL_NS;
+	data->tx_lpi_timer = DIV_ROUND_CLOSEST_ULL(tx_timer_ns, NSEC_PER_USEC);
+
+	data->tx_lpi_enabled = !!(ret & AT803X_MMD3_SMARTEEE_CTL3_LPI_EN);
+
+	return genphy_c45_ethtool_get_eee(phydev, data);
+}
+
+static int at803x_set_eee(struct phy_device *phydev, struct ethtool_eee *data)
+{
+	struct at803x_priv *priv = phydev->priv;
+	int ret;
+
+	/* If SmartEEE is not enabled, it is expected that tx_lpi_* fields
+	 * are processed by the MAC driver.
+	 */
+	if (priv->flags & AT803X_DISABLE_SMARTEEE)
+		return genphy_c45_ethtool_set_eee(phydev, data);
+
+	/* Changing Tx LPI on/off or Tx LPI timer settings
+	 * do not require link reset.
+	 */
+	ret = at803x_smarteee_config(phydev, data->tx_lpi_enabled,
+				     data->tx_lpi_timer);
+	if (ret)
+		return ret;
+
+	return genphy_c45_ethtool_set_eee(phydev, data);
+}
+
 static int qca83xx_config_init(struct phy_device *phydev)
 {
 	u8 switch_revision;
@@ -2038,6 +2135,8 @@ static struct phy_driver at803x_driver[] = {
 	.set_tunable		= at803x_set_tunable,
 	.cable_test_start	= at803x_cable_test_start,
 	.cable_test_get_status	= at803x_cable_test_get_status,
+	.get_eee		= at803x_get_eee,
+	.set_eee		= at803x_set_eee,
 }, {
 	/* Qualcomm Atheros AR8030 */
 	.phy_id			= ATH8030_PHY_ID,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 12/23] net: phy: at803x: ar8035: fix EEE support for half duplex links
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (10 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 11/23] net: phy: at803x: implement ethtool access to SmartEEE functionality Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 13/23] net: phy: add PHY specifica flag to signal SmartEEE support Oleksij Rempel
                   ` (11 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

If AR8035 is running with enabled EEE and LPI, it will not be able to
establish an 100BaseTX/Half or 1000BaseT/Half link. Similar issue we
will have with 100BaseTX/Full and LPI TX timer configured to less then
80msec.

To avoid this issue, we need to keep LPI disabled before link is
establish and enable it only we detected supported link configuration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/at803x.c | 41 +++++++++++++++++++++++++++++++++++-----
 1 file changed, 36 insertions(+), 5 deletions(-)

diff --git a/drivers/net/phy/at803x.c b/drivers/net/phy/at803x.c
index 9eb4439b0afc..5ab43eb63581 100644
--- a/drivers/net/phy/at803x.c
+++ b/drivers/net/phy/at803x.c
@@ -313,6 +313,7 @@ struct at803x_priv {
 	u8 smarteee_lpi_tw_100m;
 	bool is_fiber;
 	bool is_1000basex;
+	bool tx_lpi_on;
 	struct regulator_dev *vddio_rdev;
 	struct regulator_dev *vddh_rdev;
 	struct regulator *vddio;
@@ -970,6 +971,8 @@ static int at803x_smarteee_config(struct phy_device *phydev, bool enable,
 	u16 mask = 0, val = 0;
 	int ret;
 
+	priv->tx_lpi_on = enable;
+
 	if (priv->flags & AT803X_DISABLE_SMARTEEE || !enable)
 		return phy_modify_mmd(phydev, MDIO_MMD_PCS,
 				      AT803X_MMD3_SMARTEEE_CTL3,
@@ -1010,10 +1013,15 @@ static int at803x_smarteee_config(struct phy_device *phydev, bool enable,
 	if (ret)
 		return ret;
 
-	val = AT803X_MMD3_SMARTEEE_CTL3_LPI_EN |
-		FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH,
-			   FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_23_16,
-				     tx_lpi_timer_raw));
+	val = FIELD_PREP(AT803X_MMD3_SMARTEEE_LPI_TIME_HIGH,
+			 FIELD_GET(AT803X_MMD3_SMARTEEE_LPI_TIME_23_16,
+				   tx_lpi_timer_raw));
+
+	if (phydev->state == PHY_RUNNING &&
+	    phy_check_valid(phydev->speed, phydev->duplex,
+			    phydev->supported_eee)) {
+		val |= AT803X_MMD3_SMARTEEE_CTL3_LPI_EN;
+	}
 
 	return phy_modify_mmd(phydev, MDIO_MMD_PCS, AT803X_MMD3_SMARTEEE_CTL3,
 			      AT803X_MMD3_SMARTEEE_CTL3_LPI_EN |
@@ -1682,7 +1690,7 @@ static int at803x_get_eee(struct phy_device *phydev, struct ethtool_eee *data)
 	tx_timer_ns = tx_timer_raw * AT803X_MMD3_SMARTEEE_LPI_TIME_RESOL_NS;
 	data->tx_lpi_timer = DIV_ROUND_CLOSEST_ULL(tx_timer_ns, NSEC_PER_USEC);
 
-	data->tx_lpi_enabled = !!(ret & AT803X_MMD3_SMARTEEE_CTL3_LPI_EN);
+	data->tx_lpi_enabled = priv->tx_lpi_on;
 
 	return genphy_c45_ethtool_get_eee(phydev, data);
 }
@@ -1709,6 +1717,28 @@ static int at803x_set_eee(struct phy_device *phydev, struct ethtool_eee *data)
 	return genphy_c45_ethtool_set_eee(phydev, data);
 }
 
+static void at8035_link_change_notify(struct phy_device *phydev)
+{
+	struct at803x_priv *priv = phydev->priv;
+
+	if (priv->flags & AT803X_DISABLE_SMARTEEE)
+		return;
+
+	if (phydev->state == PHY_RUNNING) {
+		if (priv->tx_lpi_on && phy_check_valid(phydev->speed,
+						       phydev->duplex,
+						       phydev->supported_eee))
+			phy_set_bits_mmd(phydev, MDIO_MMD_PCS,
+					 AT803X_MMD3_SMARTEEE_CTL3,
+					 AT803X_MMD3_SMARTEEE_CTL3_LPI_EN);
+	} else {
+		if (priv->tx_lpi_on)
+			phy_clear_bits_mmd(phydev, MDIO_MMD_PCS,
+					   AT803X_MMD3_SMARTEEE_CTL3,
+					   AT803X_MMD3_SMARTEEE_CTL3_LPI_EN);
+	}
+}
+
 static int qca83xx_config_init(struct phy_device *phydev)
 {
 	u8 switch_revision;
@@ -2137,6 +2167,7 @@ static struct phy_driver at803x_driver[] = {
 	.cable_test_get_status	= at803x_cable_test_get_status,
 	.get_eee		= at803x_get_eee,
 	.set_eee		= at803x_set_eee,
+	.link_change_notify	= at8035_link_change_notify,
 }, {
 	/* Qualcomm Atheros AR8030 */
 	.phy_id			= ATH8030_PHY_ID,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 13/23] net: phy: add PHY specifica flag to signal SmartEEE support
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (11 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 12/23] net: phy: at803x: ar8035: fix EEE support for half duplex links Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 14/23] net: phy: at803x: add PHY_SMART_EEE flag to AR8035 Oleksij Rempel
                   ` (10 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Typical EEE support need cooperation of MAC and PHY, so both parts should
be able to do EEE. But, there also PHYs compatible with normal 802.3az
standard working with legacy MAC without EEE ability, acting as a complete
EEE power saving system.

To identify this PHYs we need a PHY specific flag. Since the PHY
specification implementing this functionality calls it SmartEEE, use
the same flag name - PHY_SMART_EEE.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 include/linux/phy.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/include/linux/phy.h b/include/linux/phy.h
index 89556cb2c555..6063b0c7a06e 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -85,6 +85,7 @@ extern const int phy_10gbit_features_array[1];
 #define PHY_IS_INTERNAL		0x00000001
 #define PHY_RST_AFTER_CLK_EN	0x00000002
 #define PHY_POLL_CABLE_TEST	0x00000004
+#define PHY_SMART_EEE		0x00000008 /* EEE done by PHY without MAC */
 #define MDIO_DEVICE_IS_PHY	0x80000000
 
 /**
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 14/23] net: phy: at803x: add PHY_SMART_EEE flag to AR8035
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (12 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 13/23] net: phy: add PHY specifica flag to signal SmartEEE support Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 15/23] net: phy: add phy_has_smarteee() helper Oleksij Rempel
                   ` (9 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

AR8035 is one of the PHYs with SmartEEE functionality. This flag will be
used by one of next patches on the i.MX FEC driver.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/phy/at803x.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/net/phy/at803x.c b/drivers/net/phy/at803x.c
index 5ab43eb63581..94dbec0a992c 100644
--- a/drivers/net/phy/at803x.c
+++ b/drivers/net/phy/at803x.c
@@ -2147,7 +2147,7 @@ static struct phy_driver at803x_driver[] = {
 	/* Qualcomm Atheros AR8035 */
 	PHY_ID_MATCH_EXACT(ATH8035_PHY_ID),
 	.name			= "Qualcomm Atheros AR8035",
-	.flags			= PHY_POLL_CABLE_TEST,
+	.flags			= PHY_POLL_CABLE_TEST | PHY_SMART_EEE,
 	.probe			= at803x_probe,
 	.remove			= at803x_remove,
 	.config_aneg		= at803x_config_aneg,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 15/23] net: phy: add phy_has_smarteee() helper
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (13 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 14/23] net: phy: at803x: add PHY_SMART_EEE flag to AR8035 Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 16/23] net: fec: add support for PHYs with SmartEEE support Oleksij Rempel
                   ` (8 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Add helper to identify PHYs with SmartEEE support.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 include/linux/phy.h | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/include/linux/phy.h b/include/linux/phy.h
index 6063b0c7a06e..c85187897115 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -1407,6 +1407,15 @@ static inline bool phy_polling_mode(struct phy_device *phydev)
 	return phydev->irq == PHY_POLL;
 }
 
+/**
+ * phy_has_rxtstamp - Tests whether a PHY supports SmartEEE.
+ * @phydev: the phy_device struct
+ */
+static inline bool phy_has_smarteee(struct phy_device *phydev)
+{
+	return phydev && phydev->drv && !!(phydev->drv->flags & PHY_SMART_EEE);
+}
+
 /**
  * phy_has_hwtstamp - Tests whether a PHY time stamp configuration.
  * @phydev: the phy_device struct
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 16/23] net: fec: add support for PHYs with SmartEEE support
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (14 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 15/23] net: phy: add phy_has_smarteee() helper Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 17/23] e1000e: replace EEE ethtool helpers to linkmode variants Oleksij Rempel
                   ` (7 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Ethernet controller in i.MX6*/i.MX7* series do not provide EEE support.
But this chips are used sometimes in combinations with SmartEEE capable
PHYs.
So, instead of aborting get/set_eee access on MACs without EEE support,
ask PHY if it is able to do the EEE job by using SmartEEE.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/ethernet/freescale/fec_main.c | 22 ++++++++++++++++++----
 1 file changed, 18 insertions(+), 4 deletions(-)

diff --git a/drivers/net/ethernet/freescale/fec_main.c b/drivers/net/ethernet/freescale/fec_main.c
index 5ff45b1a74a5..fb5c050f3fd3 100644
--- a/drivers/net/ethernet/freescale/fec_main.c
+++ b/drivers/net/ethernet/freescale/fec_main.c
@@ -3102,8 +3102,15 @@ fec_enet_get_eee(struct net_device *ndev, struct ethtool_eee *edata)
 	struct fec_enet_private *fep = netdev_priv(ndev);
 	struct ethtool_eee *p = &fep->eee;
 
-	if (!(fep->quirks & FEC_QUIRK_HAS_EEE))
-		return -EOPNOTSUPP;
+	if (!(fep->quirks & FEC_QUIRK_HAS_EEE)) {
+		if (!netif_running(ndev))
+			return -ENETDOWN;
+
+		if (!phy_has_smarteee(ndev->phydev))
+			return -EOPNOTSUPP;
+
+		return phy_ethtool_get_eee(ndev->phydev, edata);
+	}
 
 	if (!netif_running(ndev))
 		return -ENETDOWN;
@@ -3123,8 +3130,15 @@ fec_enet_set_eee(struct net_device *ndev, struct ethtool_eee *edata)
 	struct ethtool_eee *p = &fep->eee;
 	int ret = 0;
 
-	if (!(fep->quirks & FEC_QUIRK_HAS_EEE))
-		return -EOPNOTSUPP;
+	if (!(fep->quirks & FEC_QUIRK_HAS_EEE)) {
+		if (!netif_running(ndev))
+			return -ENETDOWN;
+
+		if (!phy_has_smarteee(ndev->phydev))
+			return -EOPNOTSUPP;
+
+		return phy_ethtool_set_eee(ndev->phydev, edata);
+	}
 
 	if (!netif_running(ndev))
 		return -ENETDOWN;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 17/23] e1000e: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (15 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 16/23] net: fec: add support for PHYs with SmartEEE support Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 18/23] igb: " Oleksij Rempel
                   ` (6 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/ethernet/intel/e1000e/ethtool.c | 16 ++++++++++++----
 1 file changed, 12 insertions(+), 4 deletions(-)

diff --git a/drivers/net/ethernet/intel/e1000e/ethtool.c b/drivers/net/ethernet/intel/e1000e/ethtool.c
index 721f86fd5802..7285e93b34ce 100644
--- a/drivers/net/ethernet/intel/e1000e/ethtool.c
+++ b/drivers/net/ethernet/intel/e1000e/ethtool.c
@@ -2188,6 +2188,9 @@ static int e1000_get_rxnfc(struct net_device *netdev,
 static int e1000e_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 {
 	struct e1000_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_able) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_lp) = {};
 	struct e1000_hw *hw = &adapter->hw;
 	u16 cap_addr, lpa_addr, pcs_stat_addr, phy_data;
 	u32 ret_val;
@@ -2222,16 +2225,19 @@ static int e1000e_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 	ret_val = e1000_read_emi_reg_locked(hw, cap_addr, &phy_data);
 	if (ret_val)
 		goto release;
-	edata->supported = mmd_eee_cap_to_ethtool_sup_t(phy_data);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_able, phy_data);
+	ethtool_convert_link_mode_to_legacy_u32(&edata->supported, lm_able);
 
 	/* EEE Advertised */
-	edata->advertised = mmd_eee_adv_to_ethtool_adv_t(adapter->eee_advert);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_adv, adapter->eee_advert);
+	ethtool_convert_link_mode_to_legacy_u32(&edata->advertised, lm_adv);
 
 	/* EEE Link Partner Advertised */
 	ret_val = e1000_read_emi_reg_locked(hw, lpa_addr, &phy_data);
 	if (ret_val)
 		goto release;
-	edata->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(phy_data);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_lp, phy_data);
+	ethtool_convert_link_mode_to_legacy_u32(&edata->lp_advertised, lm_lp);
 
 	/* EEE PCS Status */
 	ret_val = e1000_read_emi_reg_locked(hw, pcs_stat_addr, &phy_data);
@@ -2264,6 +2270,7 @@ static int e1000e_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 static int e1000e_set_eee(struct net_device *netdev, struct ethtool_eee *edata)
 {
 	struct e1000_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
 	struct e1000_hw *hw = &adapter->hw;
 	struct ethtool_eee eee_curr;
 	s32 ret_val;
@@ -2287,7 +2294,8 @@ static int e1000e_set_eee(struct net_device *netdev, struct ethtool_eee *edata)
 		return -EINVAL;
 	}
 
-	adapter->eee_advert = ethtool_adv_to_mmd_eee_adv_t(edata->advertised);
+	adv[0] = edata->advertised;
+	adapter->eee_advert = linkmode_adv_to_mii_eee_100_10000_adv_t(adv);
 
 	hw->dev_spec.ich8lan.eee_disable = !edata->eee_enabled;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 18/23] igb: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (16 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 17/23] e1000e: replace EEE ethtool helpers to linkmode variants Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 19/23] igc: " Oleksij Rempel
                   ` (5 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/ethernet/intel/igb/igb_ethtool.c | 23 +++++++++++++++-----
 1 file changed, 17 insertions(+), 6 deletions(-)

diff --git a/drivers/net/ethernet/intel/igb/igb_ethtool.c b/drivers/net/ethernet/intel/igb/igb_ethtool.c
index 7d60da1b7bf4..f7a633f0d6a6 100644
--- a/drivers/net/ethernet/intel/igb/igb_ethtool.c
+++ b/drivers/net/ethernet/intel/igb/igb_ethtool.c
@@ -3026,6 +3026,8 @@ static int igb_set_rxnfc(struct net_device *dev, struct ethtool_rxnfc *cmd)
 static int igb_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 {
 	struct igb_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lp) = {};
 	struct e1000_hw *hw = &adapter->hw;
 	u32 ret_val;
 	u16 phy_data;
@@ -3036,9 +3038,12 @@ static int igb_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 
 	edata->supported = (SUPPORTED_1000baseT_Full |
 			    SUPPORTED_100baseT_Full);
-	if (!hw->dev_spec._82575.eee_disable)
-		edata->advertised =
-			mmd_eee_adv_to_ethtool_adv_t(adapter->eee_advert);
+
+	if (!hw->dev_spec._82575.eee_disable) {
+		mii_eee_100_10000_adv_mod_linkmode_t(adv, adapter->eee_advert);
+		ethtool_convert_link_mode_to_legacy_u32(&edata->advertised,
+							adv);
+	}
 
 	/* The IPCNFG and EEER registers are not supported on I354. */
 	if (hw->mac.type == e1000_i354) {
@@ -3064,7 +3069,9 @@ static int igb_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 		if (ret_val)
 			return -ENODATA;
 
-		edata->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(phy_data);
+		mii_eee_100_10000_adv_mod_linkmode_t(lp, phy_data);
+		ethtool_convert_link_mode_to_legacy_u32(&edata->lp_advertised,
+							lp);
 		break;
 	case e1000_i354:
 	case e1000_i210:
@@ -3075,7 +3082,9 @@ static int igb_get_eee(struct net_device *netdev, struct ethtool_eee *edata)
 		if (ret_val)
 			return -ENODATA;
 
-		edata->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(phy_data);
+		mii_eee_100_10000_adv_mod_linkmode_t(lp, phy_data);
+		ethtool_convert_link_mode_to_legacy_u32(&edata->lp_advertised,
+							lp);
 
 		break;
 	default:
@@ -3105,6 +3114,7 @@ static int igb_set_eee(struct net_device *netdev,
 		       struct ethtool_eee *edata)
 {
 	struct igb_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
 	struct e1000_hw *hw = &adapter->hw;
 	struct ethtool_eee eee_curr;
 	bool adv1g_eee = true, adv100m_eee = true;
@@ -3149,7 +3159,8 @@ static int igb_set_eee(struct net_device *netdev,
 		return -EINVAL;
 	}
 
-	adapter->eee_advert = ethtool_adv_to_mmd_eee_adv_t(edata->advertised);
+	adv[0] = edata->advertised;
+	adapter->eee_advert = linkmode_adv_to_mii_eee_100_10000_adv_t(adv);
 	if (hw->dev_spec._82575.eee_disable != !edata->eee_enabled) {
 		hw->dev_spec._82575.eee_disable = !edata->eee_enabled;
 		adapter->flags |= IGB_FLAG_EEE;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 19/23] igc: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (17 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 18/23] igb: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 20/23] tg3: " Oleksij Rempel
                   ` (4 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/ethernet/intel/igc/igc_ethtool.c | 12 ++++++++----
 1 file changed, 8 insertions(+), 4 deletions(-)

diff --git a/drivers/net/ethernet/intel/igc/igc_ethtool.c b/drivers/net/ethernet/intel/igc/igc_ethtool.c
index 5a26a7805ef8..b23e904fc347 100644
--- a/drivers/net/ethernet/intel/igc/igc_ethtool.c
+++ b/drivers/net/ethernet/intel/igc/igc_ethtool.c
@@ -1582,12 +1582,14 @@ static int igc_ethtool_get_eee(struct net_device *netdev,
 			       struct ethtool_eee *edata)
 {
 	struct igc_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
 	struct igc_hw *hw = &adapter->hw;
 	u32 eeer;
 
-	if (hw->dev_spec._base.eee_enable)
-		edata->advertised =
-			mmd_eee_adv_to_ethtool_adv_t(adapter->eee_advert);
+	if (hw->dev_spec._base.eee_enable) {
+		mii_eee_100_10000_adv_mod_linkmode_t(adv, adapter->eee_advert);
+		ethtool_convert_link_mode_to_legacy_u32(&edata->advertised, adv);
+	}
 
 	*edata = adapter->eee;
 	edata->supported = SUPPORTED_Autoneg;
@@ -1623,6 +1625,7 @@ static int igc_ethtool_set_eee(struct net_device *netdev,
 			       struct ethtool_eee *edata)
 {
 	struct igc_adapter *adapter = netdev_priv(netdev);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
 	struct igc_hw *hw = &adapter->hw;
 	struct ethtool_eee eee_curr;
 	s32 ret_val;
@@ -1655,7 +1658,8 @@ static int igc_ethtool_set_eee(struct net_device *netdev,
 		return -EINVAL;
 	}
 
-	adapter->eee_advert = ethtool_adv_to_mmd_eee_adv_t(edata->advertised);
+	adv[0] = edata->advertised;
+	adapter->eee_advert = linkmode_adv_to_mii_eee_100_10000_adv_t(adv);
 	if (hw->dev_spec._base.eee_enable != edata->eee_enabled) {
 		hw->dev_spec._base.eee_enable = edata->eee_enabled;
 		adapter->flags |= IGC_FLAG_EEE;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 20/23] tg3: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (18 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 19/23] igc: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 21/23] r8152: " Oleksij Rempel
                   ` (3 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/ethernet/broadcom/tg3.c | 9 +++++++--
 1 file changed, 7 insertions(+), 2 deletions(-)

diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c
index 58747292521d..a3764e360d23 100644
--- a/drivers/net/ethernet/broadcom/tg3.c
+++ b/drivers/net/ethernet/broadcom/tg3.c
@@ -2339,6 +2339,8 @@ static void tg3_phy_apply_otp(struct tg3 *tp)
 
 static void tg3_eee_pull_config(struct tg3 *tp, struct ethtool_eee *eee)
 {
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lp) = {};
 	u32 val;
 	struct ethtool_eee *dest = &tp->eee;
 
@@ -2361,13 +2363,16 @@ static void tg3_eee_pull_config(struct tg3 *tp, struct ethtool_eee *eee)
 	/* Pull lp advertised settings */
 	if (tg3_phy_cl45_read(tp, MDIO_MMD_AN, MDIO_AN_EEE_LPABLE, &val))
 		return;
-	dest->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lp, val);
+	ethtool_convert_link_mode_to_legacy_u32(&dest->lp_advertised, lp);
+
 
 	/* Pull advertised and eee_enabled settings */
 	if (tg3_phy_cl45_read(tp, MDIO_MMD_AN, MDIO_AN_EEE_ADV, &val))
 		return;
 	dest->eee_enabled = !!val;
-	dest->advertised = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(adv, val);
+	ethtool_convert_link_mode_to_legacy_u32(&dest->advertised, adv);
 
 	/* Pull tx_lpi_enabled */
 	val = tr32(TG3_CPMU_EEE_MODE);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 21/23] r8152: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (19 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 20/23] tg3: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 22/23] net: usb: ax88179_178a: " Oleksij Rempel
                   ` (2 subsequent siblings)
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/usb/r8152.c | 34 +++++++++++++++++++++++++---------
 1 file changed, 25 insertions(+), 9 deletions(-)

diff --git a/drivers/net/usb/r8152.c b/drivers/net/usb/r8152.c
index decb5ba56a25..dbfde0aec003 100644
--- a/drivers/net/usb/r8152.c
+++ b/drivers/net/usb/r8152.c
@@ -8745,17 +8745,23 @@ static void rtl8152_get_strings(struct net_device *dev, u32 stringset, u8 *data)
 
 static int r8152_get_eee(struct r8152 *tp, struct ethtool_eee *eee)
 {
-	u32 lp, adv, supported = 0;
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_able) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_lp) = {};
+	u32 lp, adv, supported;
 	u16 val;
 
 	val = r8152_mmd_read(tp, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
-	supported = mmd_eee_cap_to_ethtool_sup_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_able, val);
+	ethtool_convert_link_mode_to_legacy_u32(&supported, lm_able);
 
 	val = r8152_mmd_read(tp, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
-	adv = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_adv, val);
+	ethtool_convert_link_mode_to_legacy_u32(&adv, lm_adv);
 
 	val = r8152_mmd_read(tp, MDIO_MMD_AN, MDIO_AN_EEE_LPABLE);
-	lp = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_lp, val);
+	ethtool_convert_link_mode_to_legacy_u32(&lp, lm_lp);
 
 	eee->eee_enabled = tp->eee_en;
 	eee->eee_active = !!(supported & adv & lp);
@@ -8768,7 +8774,11 @@ static int r8152_get_eee(struct r8152 *tp, struct ethtool_eee *eee)
 
 static int r8152_set_eee(struct r8152 *tp, struct ethtool_eee *eee)
 {
-	u16 val = ethtool_adv_to_mmd_eee_adv_t(eee->advertised);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	u16 val;
+
+	adv[0] = eee->advertised;
+	val = linkmode_adv_to_mii_eee_100_10000_adv_t(adv);
 
 	tp->eee_en = eee->eee_enabled;
 	tp->eee_adv = val;
@@ -8780,17 +8790,23 @@ static int r8152_set_eee(struct r8152 *tp, struct ethtool_eee *eee)
 
 static int r8153_get_eee(struct r8152 *tp, struct ethtool_eee *eee)
 {
-	u32 lp, adv, supported = 0;
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_able) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_lp) = {};
+	u32 lp, adv, supported;
 	u16 val;
 
 	val = ocp_reg_read(tp, OCP_EEE_ABLE);
-	supported = mmd_eee_cap_to_ethtool_sup_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_able, val);
+	ethtool_convert_link_mode_to_legacy_u32(&supported, lm_able);
 
 	val = ocp_reg_read(tp, OCP_EEE_ADV);
-	adv = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_adv, val);
+	ethtool_convert_link_mode_to_legacy_u32(&adv, lm_adv);
 
 	val = ocp_reg_read(tp, OCP_EEE_LPABLE);
-	lp = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_lp, val);
+	ethtool_convert_link_mode_to_legacy_u32(&lp, lm_lp);
 
 	eee->eee_enabled = tp->eee_en;
 	eee->eee_active = !!(supported & adv & lp);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 22/23] net: usb: ax88179_178a: replace EEE ethtool helpers to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (20 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 21/23] r8152: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-01 14:58 ` [PATCH net-next v4 23/23] net: mdio: drop EEE ethtool helpers in favor " Oleksij Rempel
  2023-02-04  0:13 ` [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Vladimir Oltean
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

Replace EEE ethtool helpers with linkmode variants. This will
reduce similar code snippets and prepare ethtool EEE interface to linkmode
migration.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 drivers/net/usb/ax88179_178a.c | 24 +++++++++++++++++-------
 1 file changed, 17 insertions(+), 7 deletions(-)

diff --git a/drivers/net/usb/ax88179_178a.c b/drivers/net/usb/ax88179_178a.c
index aff39bf3161d..7e8b5f174184 100644
--- a/drivers/net/usb/ax88179_178a.c
+++ b/drivers/net/usb/ax88179_178a.c
@@ -652,6 +652,9 @@ static int ax88179_set_link_ksettings(struct net_device *net,
 static int
 ax88179_ethtool_get_eee(struct usbnet *dev, struct ethtool_eee *data)
 {
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_able) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_adv) = {};
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(lm_lp) = {};
 	int val;
 
 	/* Get Supported EEE */
@@ -659,21 +662,24 @@ ax88179_ethtool_get_eee(struct usbnet *dev, struct ethtool_eee *data)
 					    MDIO_MMD_PCS);
 	if (val < 0)
 		return val;
-	data->supported = mmd_eee_cap_to_ethtool_sup_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_able, val);
+	ethtool_convert_link_mode_to_legacy_u32(&data->supported, lm_able);
 
 	/* Get advertisement EEE */
 	val = ax88179_phy_read_mmd_indirect(dev, MDIO_AN_EEE_ADV,
 					    MDIO_MMD_AN);
 	if (val < 0)
 		return val;
-	data->advertised = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_adv, val);
+	ethtool_convert_link_mode_to_legacy_u32(&data->advertised, lm_adv);
 
 	/* Get LP advertisement EEE */
 	val = ax88179_phy_read_mmd_indirect(dev, MDIO_AN_EEE_LPABLE,
 					    MDIO_MMD_AN);
 	if (val < 0)
 		return val;
-	data->lp_advertised = mmd_eee_adv_to_ethtool_adv_t(val);
+	mii_eee_100_10000_adv_mod_linkmode_t(lm_lp, val);
+	ethtool_convert_link_mode_to_legacy_u32(&data->lp_advertised, lm_lp);
 
 	return 0;
 }
@@ -681,7 +687,11 @@ ax88179_ethtool_get_eee(struct usbnet *dev, struct ethtool_eee *data)
 static int
 ax88179_ethtool_set_eee(struct usbnet *dev, struct ethtool_eee *data)
 {
-	u16 tmp16 = ethtool_adv_to_mmd_eee_adv_t(data->advertised);
+	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
+	u16 tmp16;
+
+	adv[0] = data->advertised;
+	tmp16 = linkmode_adv_to_mii_eee_100_10000_adv_t(adv);
 
 	return ax88179_phy_write_mmd_indirect(dev, MDIO_AN_EEE_ADV,
 					      MDIO_MMD_AN, tmp16);
@@ -706,7 +716,7 @@ static int ax88179_chk_eee(struct usbnet *dev)
 			return false;
 		}
 
-		cap = mmd_eee_cap_to_ethtool_sup_t(eee_cap);
+		cap = eee_cap & (MDIO_EEE_100TX | MDIO_EEE_1000T);
 		if (!cap) {
 			priv->eee_active = 0;
 			return false;
@@ -729,8 +739,8 @@ static int ax88179_chk_eee(struct usbnet *dev)
 			return false;
 		}
 
-		adv = mmd_eee_adv_to_ethtool_adv_t(eee_adv);
-		lp = mmd_eee_adv_to_ethtool_adv_t(eee_lp);
+		adv = eee_adv & (MDIO_EEE_100TX | MDIO_EEE_1000T);
+		lp = eee_lp & (MDIO_EEE_100TX | MDIO_EEE_1000T);
 		supported = (ecmd.speed == SPEED_1000) ?
 			     SUPPORTED_1000baseT_Full :
 			     SUPPORTED_100baseT_Full;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH net-next v4 23/23] net: mdio: drop EEE ethtool helpers in favor to linkmode variants
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (21 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 22/23] net: usb: ax88179_178a: " Oleksij Rempel
@ 2023-02-01 14:58 ` Oleksij Rempel
  2023-02-04  0:13 ` [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Vladimir Oltean
  23 siblings, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-01 14:58 UTC (permalink / raw)
  To: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit
  Cc: Oleksij Rempel, kernel, linux-kernel, netdev, Arun.Ramadoss,
	intel-wired-lan

IEEE 802.3 specification provides more EEE capable link modes as this helpers
will be able to handle. So, remove them in favor of:
mii_eee_100_10000_adv_mod_linkmode_t
linkmode_adv_to_mii_eee_100_10000_adv_t

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
 include/linux/mdio.h | 83 --------------------------------------------
 1 file changed, 83 deletions(-)

diff --git a/include/linux/mdio.h b/include/linux/mdio.h
index fcd5492e4993..492ec2de24ac 100644
--- a/include/linux/mdio.h
+++ b/include/linux/mdio.h
@@ -205,89 +205,6 @@ mdio45_ethtool_ksettings_get(const struct mdio_if_info *mdio,
 extern int mdio_mii_ioctl(const struct mdio_if_info *mdio,
 			  struct mii_ioctl_data *mii_data, int cmd);
 
-/**
- * mmd_eee_cap_to_ethtool_sup_t
- * @eee_cap: value of the MMD EEE Capability register
- *
- * A small helper function that translates MMD EEE Capability (3.20) bits
- * to ethtool supported settings.
- */
-static inline u32 mmd_eee_cap_to_ethtool_sup_t(u16 eee_cap)
-{
-	u32 supported = 0;
-
-	if (eee_cap & MDIO_EEE_100TX)
-		supported |= SUPPORTED_100baseT_Full;
-	if (eee_cap & MDIO_EEE_1000T)
-		supported |= SUPPORTED_1000baseT_Full;
-	if (eee_cap & MDIO_EEE_10GT)
-		supported |= SUPPORTED_10000baseT_Full;
-	if (eee_cap & MDIO_EEE_1000KX)
-		supported |= SUPPORTED_1000baseKX_Full;
-	if (eee_cap & MDIO_EEE_10GKX4)
-		supported |= SUPPORTED_10000baseKX4_Full;
-	if (eee_cap & MDIO_EEE_10GKR)
-		supported |= SUPPORTED_10000baseKR_Full;
-
-	return supported;
-}
-
-/**
- * mmd_eee_adv_to_ethtool_adv_t
- * @eee_adv: value of the MMD EEE Advertisement/Link Partner Ability registers
- *
- * A small helper function that translates the MMD EEE Advertisment (7.60)
- * and MMD EEE Link Partner Ability (7.61) bits to ethtool advertisement
- * settings.
- */
-static inline u32 mmd_eee_adv_to_ethtool_adv_t(u16 eee_adv)
-{
-	u32 adv = 0;
-
-	if (eee_adv & MDIO_EEE_100TX)
-		adv |= ADVERTISED_100baseT_Full;
-	if (eee_adv & MDIO_EEE_1000T)
-		adv |= ADVERTISED_1000baseT_Full;
-	if (eee_adv & MDIO_EEE_10GT)
-		adv |= ADVERTISED_10000baseT_Full;
-	if (eee_adv & MDIO_EEE_1000KX)
-		adv |= ADVERTISED_1000baseKX_Full;
-	if (eee_adv & MDIO_EEE_10GKX4)
-		adv |= ADVERTISED_10000baseKX4_Full;
-	if (eee_adv & MDIO_EEE_10GKR)
-		adv |= ADVERTISED_10000baseKR_Full;
-
-	return adv;
-}
-
-/**
- * ethtool_adv_to_mmd_eee_adv_t
- * @adv: the ethtool advertisement settings
- *
- * A small helper function that translates ethtool advertisement settings
- * to EEE advertisements for the MMD EEE Advertisement (7.60) and
- * MMD EEE Link Partner Ability (7.61) registers.
- */
-static inline u16 ethtool_adv_to_mmd_eee_adv_t(u32 adv)
-{
-	u16 reg = 0;
-
-	if (adv & ADVERTISED_100baseT_Full)
-		reg |= MDIO_EEE_100TX;
-	if (adv & ADVERTISED_1000baseT_Full)
-		reg |= MDIO_EEE_1000T;
-	if (adv & ADVERTISED_10000baseT_Full)
-		reg |= MDIO_EEE_10GT;
-	if (adv & ADVERTISED_1000baseKX_Full)
-		reg |= MDIO_EEE_1000KX;
-	if (adv & ADVERTISED_10000baseKX4_Full)
-		reg |= MDIO_EEE_10GKX4;
-	if (adv & ADVERTISED_10000baseKR_Full)
-		reg |= MDIO_EEE_10GKR;
-
-	return reg;
-}
-
 /**
  * linkmode_adv_to_mii_10gbt_adv_t
  * @advertising: the linkmode advertisement settings
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active()
  2023-02-01 14:58 ` [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active() Oleksij Rempel
@ 2023-02-01 16:41   ` Andrew Lunn
  0 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-01 16:41 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Vivien Didelot, Florian Fainelli,
	Vladimir Oltean, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

>  int phy_init_eee(struct phy_device *phydev, bool clk_stop_enable)
>  {
> +	int ret;
> +
>  	if (!phydev->drv)
>  		return -EIO;
>  
> -	/* According to 802.3az,the EEE is supported only in full duplex-mode.
> -	 */
> -	if (phydev->duplex == DUPLEX_FULL) {

This got me for a while, where did the duplex check go?

But you now compare the local advertised EEE and the link peer EEE.
Since it is impossible to advertise a half duplex mode, the result can
never contain a half duplex mode.

I've done the work now, but a comment about this in the commit message
would of been nice.

FYI: Thanks for converting all users of the old functions. I was not
expecting that.

	Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-01 14:58 ` [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function Oleksij Rempel
@ 2023-02-01 17:12   ` Andrew Lunn
  2023-02-04  0:54   ` Vladimir Oltean
  1 sibling, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-01 17:12 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Vivien Didelot, Florian Fainelli,
	Vladimir Oltean, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:24PM +0100, Oleksij Rempel wrote:
> Add generic function for EEE abilities defined by IEEE 802.3
> specification. For now following registers are supported:
> - IEEE 802.3-2018 45.2.3.10 EEE control and capability 1 (Register 3.20)
> - IEEE 802.3cg-2019 45.2.1.186b 10BASE-T1L PMA status register
>   (Register 1.2295)
> 
> Since I was not able to find any flag signaling support of this
> registers, we should detect link mode abilities first and then based on
> this abilities doing EEE link modes detection.

Hi Oleksij

There was a discussion along these lines with Chris Healy
recently. The meson-gxl PHYs don't have these registers, and reads
return 0xffff. The 802.3 2018 standard says the top 2 bits are
reserved and should read as 0. Also, it seems unlikely anybody will
build a PHY which supports 100GBASE-R deep sleep all the way down to
100BASE-TX EEE. So i would suggest adding a check when reading
MDIO_PCS_EEE_ABLE and if it is 0xffff assume EEE is not supported.

> +		val = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
> +		if (val < 0)
> +			return val;
> +
> +		mii_eee_100_10000_adv_mod_linkmode_t(phydev->supported_eee, val);
> +
> +		/* Some buggy devices claim not supported EEE link modes */
> +		linkmode_and(phydev->supported_eee, phydev->supported_eee,
> +			     phydev->supported);

That comment could be improved. What i think you mean is

/* Some buggy devices indicate EEE link modes in MDIO_PCS_EEE_ABLE
   which they don't support as indicated by BMSR, ESTATUS etc. */

   Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function
  2023-02-01 14:58 ` [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function Oleksij Rempel
@ 2023-02-01 17:15   ` Andrew Lunn
  0 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-01 17:15 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Vivien Didelot, Florian Fainelli,
	Vladimir Oltean, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:26PM +0100, Oleksij Rempel wrote:
> This function will be needed for genphy_c45_ethtool_get_eee() provided
> by next patch.
> 
> Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>

Reviewed-by: Andrew Lunn <andrew@lunn.ch>

    Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support
  2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
@ 2023-02-01 17:20   ` Andrew Lunn
  2023-02-01 20:18   ` Jakub Kicinski
  2023-02-04  1:11   ` Vladimir Oltean
  2 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-01 17:20 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Vivien Didelot, Florian Fainelli,
	Vladimir Oltean, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:27PM +0100, Oleksij Rempel wrote:
> Add replacement for phy_ethtool_get/set_eee() functions.
> 
> Current phy_ethtool_get/set_eee() implementation is great and it is
> possible to make it even better:
> - this functionality is for devices implementing parts of IEEE 802.3
>   specification beyond Clause 22. The better place for this code is
>   phy-c45.c
> - currently it is able to do read/write operations on PHYs with
>   different abilities to not existing registers. It is better to
>   use stored supported_eee abilities to avoid false read/write
>   operations.
> - the eee_active detection will provide wrong results on not supported
>   link modes. It is better to validate speed/duplex properties against
>   supported EEE link modes.
> - it is able to support only limited amount of link modes. We have more
>   EEE link modes...
> 
> By refactoring this code I address most of this point except of the last
> one. Adding additional EEE link modes will need more work.

phydev->eee_broken_modes in particular is an issue. Anybody with
broken 10baseT1L will not be able to work around it currently.

Not that i'm saying this need fixing now.

    Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv()
  2023-02-01 14:58 ` [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv() Oleksij Rempel
@ 2023-02-01 17:28   ` Andrew Lunn
  0 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-01 17:28 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Vivien Didelot, Florian Fainelli,
	Vladimir Oltean, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

> +	/* This is optional functionality. If not supported, we may get an error
> +	 * which should be ignored.
> +	 */
> +	genphy_c45_read_eee_abilities(phydev);

Humm, philosophic discussion. Would it be better for
genphy_c45_read_eee_abilities() to silently ignore the error? Errors
like -ETIMEDOUT should probably be returned, but -EOPNOTSUPP should be
ignored.

	Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support
  2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
  2023-02-01 17:20   ` Andrew Lunn
@ 2023-02-01 20:18   ` Jakub Kicinski
  2023-02-04  1:11   ` Vladimir Oltean
  2 siblings, 0 replies; 43+ messages in thread
From: Jakub Kicinski @ 2023-02-01 20:18 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, Vladimir Oltean, David S. Miller, Eric Dumazet,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed,  1 Feb 2023 15:58:27 +0100 Oleksij Rempel wrote:
> +/**
> + * genphy_c45_write_eee_adv - write advertised EEE link modes
> + * @phydev: target phy_device struct
> + */
> +int genphy_c45_write_eee_adv(struct phy_device *phydev, unsigned long *adv)

nit: most functions added by this patch are missing kdoc for second
argument

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
                   ` (22 preceding siblings ...)
  2023-02-01 14:58 ` [PATCH net-next v4 23/23] net: mdio: drop EEE ethtool helpers in favor " Oleksij Rempel
@ 2023-02-04  0:13 ` Vladimir Oltean
  2023-02-06  5:47   ` Oleksij Rempel
  23 siblings, 1 reply; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-04  0:13 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:22PM +0100, Oleksij Rempel wrote:
> With this patch series we provide EEE control for KSZ9477 family of switches and
> AR8035 with i.MX6 configuration.
> According to my tests, on a system with KSZ8563 switch and 100Mbit idle link,
> we consume 0,192W less power per port if EEE is enabled.

What is the code flow through the kernel with EEE? I wasn't able to find
a good explanation about it.

Is it advertised by default, if supported? I guess phy_advertise_supported()
does that.

But is that desirable? Doesn't EEE cause undesired latency for MAC-level
PTP timestamping on an otherwise idle link?

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support
  2023-02-01 14:58 ` [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support Oleksij Rempel
@ 2023-02-04  0:14   ` Vladimir Oltean
  0 siblings, 0 replies; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-04  0:14 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:23PM +0100, Oleksij Rempel wrote:
> +static int ksz_get_mac_eee(struct dsa_switch *ds, int port,
> +			   struct ethtool_eee *e)
> +{
> +	int ret;
> +
> +	ret = ksz_validate_eee(ds, port);
> +	if (ret)
> +		return ret;
> +
> +	/* There is no documented control of Tx LPI configuration.
> +	 */

comment fits on a single line

> +	e->tx_lpi_enabled = true;
> +	/* There is no documented control of Tx LPI timer. According to testes

according to tests, I hope, not testes

> +	 * Tx LPI timer seems to be set by default to minimal value.
> +	 */
> +	e->tx_lpi_timer = 0;
> +
> +	return 0;
> +}

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-01 14:58 ` [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function Oleksij Rempel
  2023-02-01 17:12   ` Andrew Lunn
@ 2023-02-04  0:54   ` Vladimir Oltean
  2023-02-06 10:49     ` Oleksij Rempel
  1 sibling, 1 reply; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-04  0:54 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:24PM +0100, Oleksij Rempel wrote:
> Add generic function for EEE abilities defined by IEEE 802.3
> specification. For now following registers are supported:
> - IEEE 802.3-2018 45.2.3.10 EEE control and capability 1 (Register 3.20)
> - IEEE 802.3cg-2019 45.2.1.186b 10BASE-T1L PMA status register
>   (Register 1.2295)
> 
> Since I was not able to find any flag signaling support of this

these registers

> registers, we should detect link mode abilities first and then based on
> this abilities doing EEE link modes detection.

these abilities

> 
> Results of EEE ability detection will be stored in to new variable

stored into

> phydev->supported_eee.
> 
> Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
> ---
>  drivers/net/phy/phy-c45.c    | 49 ++++++++++++++++++++++++++++++++++++
>  drivers/net/phy/phy_device.c | 16 ++++++++++++
>  include/linux/mdio.h         | 17 +++++++++++++
>  include/linux/phy.h          |  5 ++++
>  4 files changed, 87 insertions(+)
> 
> diff --git a/drivers/net/phy/phy-c45.c b/drivers/net/phy/phy-c45.c
> index 9f9565a4819d..ae87f5856650 100644
> --- a/drivers/net/phy/phy-c45.c
> +++ b/drivers/net/phy/phy-c45.c
> @@ -661,6 +661,55 @@ int genphy_c45_read_mdix(struct phy_device *phydev)
>  }
>  EXPORT_SYMBOL_GPL(genphy_c45_read_mdix);
>  
> +/**
> + * genphy_c45_read_eee_abilities - read supported EEE link modes
> + * @phydev: target phy_device struct
> + *
> + * Read supported EEE link modes.
> + */
> +int genphy_c45_read_eee_abilities(struct phy_device *phydev)
> +{
> +	__ETHTOOL_DECLARE_LINK_MODE_MASK(common);
> +	int val;
> +
> +	linkmode_and(common, phydev->supported, PHY_EEE_100_10000_FEATURES);
> +	/* There is not indicator if optional register

no indicator whether

> +	 * "EEE control and capability 1" (3.20) is supported. Read it only
> +	 * on devices with appropriate linkmodes.
> +	 */
> +	if (!linkmode_empty(common)) {

if (linkmode_intersects(phydev->supported, PHY_EEE_100_10000_FEATURES))?

> +		/* IEEE 802.3-2018 45.2.3.10 EEE control and capability 1
> +		 * (Register 3.20)
> +		 */
> +		val = phy_read_mmd(phydev, MDIO_MMD_PCS, MDIO_PCS_EEE_ABLE);
> +		if (val < 0)
> +			return val;

Might the PHY also return 0xffff for an unsupported register? That would
be interpreted as "EEE is supported for all link modes", no?

> +
> +		mii_eee_100_10000_adv_mod_linkmode_t(phydev->supported_eee, val);
> +
> +		/* Some buggy devices claim not supported EEE link modes */

unsupported

> +		linkmode_and(phydev->supported_eee, phydev->supported_eee,
> +			     phydev->supported);
> +	}
> +
> +	if (linkmode_test_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
> +			      phydev->supported)) {
> +		/* IEEE 802.3cg-2019 45.2.1.186b 10BASE-T1L PMA status register
> +		 * (Register 1.2295)
> +		 */
> +		val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PMA_10T1L_STAT);
> +		if (val < 0)
> +			return val;
> +
> +		linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT1L_Full_BIT,
> +				 phydev->supported_eee,
> +				 val & MDIO_PMA_10T1L_STAT_EEE);
> +	}
> +
> +	return 0;
> +}
> +EXPORT_SYMBOL_GPL(genphy_c45_read_eee_abilities);
> +
>  /**
>   * genphy_c45_pma_read_abilities - read supported link modes from PMA
>   * @phydev: target phy_device struct
> diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
> index 9ba8f973f26f..3651f1fd8fc9 100644
> --- a/drivers/net/phy/phy_device.c
> +++ b/drivers/net/phy/phy_device.c
> @@ -132,6 +132,18 @@ static const int phy_10gbit_full_features_array[] = {
>  	ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
>  };
>  
> +static const int phy_eee_100_10000_features_array[6] = {

Don't need array length unless the array is sparse, which isn't the case here.

> +	ETHTOOL_LINK_MODE_100baseT_Full_BIT,
> +	ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
> +	ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
> +	ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
> +	ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
> +	ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,

Why stop at 10GBase-KR? Register 3.20 defines EEE abilities up to 100G
(for speeds >10G, there seem to be 2 modes, "deep sleep" or "fast wake",
with "deep sleep" being essentially equivalent to the only mode
available for <=10G modes).

> +};
> +
> +__ETHTOOL_DECLARE_LINK_MODE_MASK(phy_eee_100_10000_features) __ro_after_init;
> +EXPORT_SYMBOL_GPL(phy_eee_100_10000_features);
> +
>  static void features_init(void)
>  {
>  	/* 10/100 half/full*/
> @@ -213,6 +225,10 @@ static void features_init(void)
>  	linkmode_set_bit_array(phy_10gbit_fec_features_array,
>  			       ARRAY_SIZE(phy_10gbit_fec_features_array),
>  			       phy_10gbit_fec_features);
> +	linkmode_set_bit_array(phy_eee_100_10000_features_array,
> +			       ARRAY_SIZE(phy_eee_100_10000_features_array),
> +			       phy_eee_100_10000_features);
> +
>  }
>  
>  void phy_device_free(struct phy_device *phydev)

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support
  2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
  2023-02-01 17:20   ` Andrew Lunn
  2023-02-01 20:18   ` Jakub Kicinski
@ 2023-02-04  1:11   ` Vladimir Oltean
  2 siblings, 0 replies; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-04  1:11 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Wed, Feb 01, 2023 at 03:58:27PM +0100, Oleksij Rempel wrote:
> Add replacement for phy_ethtool_get/set_eee() functions.
> 
> - it is able to support only limited amount of link modes. We have more
>   EEE link modes...
> 
> By refactoring this code I address most of this point except of the last
> one. Adding additional EEE link modes will need more work.

> +/**
> + * genphy_c45_ethtool_get_eee - get EEE supported and status
> + * @phydev: target phy_device struct
> + * @data: ethtool_eee data
> + *
> + * Description: it reports the Supported/Advertisement/LP Advertisement
> + * capabilities.
> + */
> +int genphy_c45_ethtool_get_eee(struct phy_device *phydev,
> +			       struct ethtool_eee *data)
> +{
> +	__ETHTOOL_DECLARE_LINK_MODE_MASK(adv) = {};
> +	__ETHTOOL_DECLARE_LINK_MODE_MASK(lp) = {};
> +	bool overflow = false, is_enabled;
> +	int ret;
> +
> +	ret = genphy_c45_eee_is_active(phydev, adv, lp, &is_enabled);
> +	if (ret < 0)
> +		return ret;
> +
> +	data->eee_enabled = is_enabled;
> +	data->eee_active = ret;
> +
> +	if (!ethtool_convert_link_mode_to_legacy_u32(&data->supported,
> +						     phydev->supported_eee))
> +		overflow = true;
> +	if (!ethtool_convert_link_mode_to_legacy_u32(&data->advertised, adv))
> +		overflow = true;
> +	if (!ethtool_convert_link_mode_to_legacy_u32(&data->lp_advertised, lp))
> +		overflow = true;

ah, ok, so since struct ethtool_eee stores the link modes in the old u32
format, link modes equal to ETHTOOL_LINK_MODE_25000baseKR_Full_BIT or
higher would truncate. Makes sense.

> +
> +	if (overflow)
> +		phydev_warn(phydev, "Not all supported or advertised EEE link modes was passed to the user space\n");

were passed

> +
> +	return 0;
> +}
> +EXPORT_SYMBOL(genphy_c45_ethtool_get_eee);

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-04  0:13 ` [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Vladimir Oltean
@ 2023-02-06  5:47   ` Oleksij Rempel
  2023-02-06 14:10     ` Vladimir Oltean
  0 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-06  5:47 UTC (permalink / raw)
  To: Vladimir Oltean
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Sat, Feb 04, 2023 at 02:13:32AM +0200, Vladimir Oltean wrote:
> On Wed, Feb 01, 2023 at 03:58:22PM +0100, Oleksij Rempel wrote:
> > With this patch series we provide EEE control for KSZ9477 family of switches and
> > AR8035 with i.MX6 configuration.
> > According to my tests, on a system with KSZ8563 switch and 100Mbit idle link,
> > we consume 0,192W less power per port if EEE is enabled.
> 
> What is the code flow through the kernel with EEE? I wasn't able to find
> a good explanation about it.
> 
> Is it advertised by default, if supported? I guess phy_advertise_supported()
> does that.

Ack.

> But is that desirable? Doesn't EEE cause undesired latency for MAC-level
> PTP timestamping on an otherwise idle link?

Theoretically, MAC controls Low Power Idle states and even with some
"Wake" latency should be fully aware of actual ingress and egress time
stamps.

Practically, right now I do not have such HW to confirm it. My project
is affected by EEE in different ways:
- with EEE PTP has too much jitter
- without EEE, the devices consumes too much power in standby mode with
  WoL enabled. Even switching to 10BaseT less power as 100BaseTX with
  EEE would do.

My view is probably biased by my environment - PTP is relatively rare
use case. EEE saves power (0,2W+0,2W per link in my case). Summary power
saving of all devices is potentially equal to X amount of power plants. 
So, EEE should be enabled by default.

Beside, flow control (enabled by default) affects PTP in some cases too.

May be ptp4l should warn about this options? We should be able to detect
it from user space.

Regards,
Oleksij
-- 
Pengutronix e.K.                           |                             |
Steuerwalder Str. 21                       | http://www.pengutronix.de/  |
31137 Hildesheim, Germany                  | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-04  0:54   ` Vladimir Oltean
@ 2023-02-06 10:49     ` Oleksij Rempel
  2023-02-06 11:22       ` Vladimir Oltean
  0 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-06 10:49 UTC (permalink / raw)
  To: Vladimir Oltean
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

Hi Vladimir,

On Sat, Feb 04, 2023 at 02:54:18AM +0200, Vladimir Oltean wrote:
> On Wed, Feb 01, 2023 at 03:58:24PM +0100, Oleksij Rempel wrote:

[....]

> > +static const int phy_eee_100_10000_features_array[6] = {
> 
> Don't need array length unless the array is sparse, which isn't the case here.
> 
> > +	ETHTOOL_LINK_MODE_100baseT_Full_BIT,
> > +	ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
> > +	ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
> > +	ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
> > +	ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
> > +	ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
> 
> Why stop at 10GBase-KR? Register 3.20 defines EEE abilities up to 100G
> (for speeds >10G, there seem to be 2 modes, "deep sleep" or "fast wake",
> with "deep sleep" being essentially equivalent to the only mode
> available for <=10G modes).

Hm,

If i take only deep sleep, missing modes are:
3.20.13 100GBASE-R deep sleep
       family of Physical Layer devices using 100GBASE-R encoding:
       100000baseCR4_Full
       100000baseKR4_Full
       100000baseCR10_Full (missing)
       100000baseSR4_Full
       100000baseSR10_Full (missing)
       100000baseLR4_ER4_Full

3.20.11 25GBASE-R deep sleep
       family of Physical Layer devices using 25GBASE-R encoding:
       25000baseCR_Full
       25000baseER_Full (missing)
       25000baseKR_Full
       25000baseLR_Full (missing)
       25000baseSR_Full

3.20.9 40GBASE-R deep sleep
       family of Physical Layer devices using 40GBASE-R encoding:
       40000baseKR4_Full
       40000baseCR4_Full
       40000baseSR4_Full
       40000baseLR4_Full

3.20.7 40GBASE-T
       40000baseT_Full (missing)

I have no experience with modes > 1Gbit. Do all of them correct? What
should we do with missing modes? Or may be it make sense to implement >
10G modes separately?

Regards,
Oleksij
-- 
Pengutronix e.K.                           |                             |
Steuerwalder Str. 21                       | http://www.pengutronix.de/  |
31137 Hildesheim, Germany                  | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-06 10:49     ` Oleksij Rempel
@ 2023-02-06 11:22       ` Vladimir Oltean
  2023-02-06 15:42         ` Andrew Lunn
  0 siblings, 1 reply; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-06 11:22 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Mon, Feb 06, 2023 at 11:49:55AM +0100, Oleksij Rempel wrote:
> > Why stop at 10GBase-KR? Register 3.20 defines EEE abilities up to 100G
> > (for speeds >10G, there seem to be 2 modes, "deep sleep" or "fast wake",
> > with "deep sleep" being essentially equivalent to the only mode
> > available for <=10G modes).
> 
> Hm,
> 
> If i take only deep sleep, missing modes are:
> 3.20.13 100GBASE-R deep sleep
>        family of Physical Layer devices using 100GBASE-R encoding:
>        100000baseCR4_Full
>        100000baseKR4_Full
>        100000baseCR10_Full (missing)
>        100000baseSR4_Full
>        100000baseSR10_Full (missing)
>        100000baseLR4_ER4_Full
> 
> 3.20.11 25GBASE-R deep sleep
>        family of Physical Layer devices using 25GBASE-R encoding:
>        25000baseCR_Full
>        25000baseER_Full (missing)
>        25000baseKR_Full
>        25000baseLR_Full (missing)
>        25000baseSR_Full
> 
> 3.20.9 40GBASE-R deep sleep
>        family of Physical Layer devices using 40GBASE-R encoding:
>        40000baseKR4_Full
>        40000baseCR4_Full
>        40000baseSR4_Full
>        40000baseLR4_Full
> 
> 3.20.7 40GBASE-T
>        40000baseT_Full (missing)
> 
> I have no experience with modes > 1Gbit. Do all of them correct? What
> should we do with missing modes? Or may be it make sense to implement >
> 10G modes separately?

Given the fact that UAPI needs an extension to cover supported/advertisement
bits > 31, I think it makes sense to add these separately. I had not
realized this when I commented on this patch. I don't think we want the
kernel to advertise EEE for some link modes without user space seeing it.

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-06  5:47   ` Oleksij Rempel
@ 2023-02-06 14:10     ` Vladimir Oltean
  2023-02-06 15:39       ` Andrew Lunn
  2023-02-06 18:25       ` Oleksij Rempel
  0 siblings, 2 replies; 43+ messages in thread
From: Vladimir Oltean @ 2023-02-06 14:10 UTC (permalink / raw)
  To: Oleksij Rempel, Richard Cochran
  Cc: Woojung Huh, UNGLinuxDriver, Andrew Lunn, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Mon, Feb 06, 2023 at 06:47:13AM +0100, Oleksij Rempel wrote:
> On Sat, Feb 04, 2023 at 02:13:32AM +0200, Vladimir Oltean wrote:
> > On Wed, Feb 01, 2023 at 03:58:22PM +0100, Oleksij Rempel wrote:
> > > With this patch series we provide EEE control for KSZ9477 family of switches and
> > > AR8035 with i.MX6 configuration.
> > > According to my tests, on a system with KSZ8563 switch and 100Mbit idle link,
> > > we consume 0,192W less power per port if EEE is enabled.
> > 
> > What is the code flow through the kernel with EEE? I wasn't able to find
> > a good explanation about it.
> > 
> > Is it advertised by default, if supported? I guess phy_advertise_supported()
> > does that.
> 
> Ack.
> 
> > But is that desirable? Doesn't EEE cause undesired latency for MAC-level
> > PTP timestamping on an otherwise idle link?
> 
> Theoretically, MAC controls Low Power Idle states and even with some
> "Wake" latency should be fully aware of actual ingress and egress time
> stamps.

I'm not sure if this is also true with Atheros SmartEEE, where the PHY
is the one who enters LPI mode and buffers packets until it wakes up?

> 
> Practically, right now I do not have such HW to confirm it. My project
> is affected by EEE in different ways:

Doesn't FEC support PTP?

> - with EEE PTP has too much jitter
> - without EEE, the devices consumes too much power in standby mode with
>   WoL enabled. Even switching to 10BaseT less power as 100BaseTX with
>   EEE would do.
> 
> My view is probably biased by my environment - PTP is relatively rare
> use case. EEE saves power (0,2W+0,2W per link in my case). Summary power
> saving of all devices is potentially equal to X amount of power plants. 
> So, EEE should be enabled by default.

I'm not contesting the value of EEE. Just wondering whether it's best
for the kernel, rather than user space, to enable it by default.

> 
> Beside, flow control (enabled by default) affects PTP in some cases too.

You are probably talking about the fact that flow control may affect
end-to-end delay measurements (across switches in a LAN). Yes, but EEE
(or at least SmartEEE) may affect peer-to-peer delay measurements, which
I see as worse.

> 
> May be ptp4l should warn about this options? We should be able to detect
> it from user space.

This isn't necessarily a bad idea, even though it would end up
renegotiating and losing the link.

Maybe it would be good to drag Richard Cochran into the discussion too.
After all he's the one who should agree what should and what shouldn't
ptp4l be concerned with.

> 
> Regards,
> Oleksij
> -- 
> Pengutronix e.K.                           |                             |
> Steuerwalder Str. 21                       | http://www.pengutronix.de/  |
> 31137 Hildesheim, Germany                  | Phone: +49-5121-206917-0    |
> Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-06 14:10     ` Vladimir Oltean
@ 2023-02-06 15:39       ` Andrew Lunn
  2023-02-06 18:37         ` Oleksij Rempel
  2023-02-06 18:25       ` Oleksij Rempel
  1 sibling, 1 reply; 43+ messages in thread
From: Andrew Lunn @ 2023-02-06 15:39 UTC (permalink / raw)
  To: Vladimir Oltean
  Cc: Oleksij Rempel, Richard Cochran, Woojung Huh, UNGLinuxDriver,
	Vivien Didelot, Florian Fainelli, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit, kernel,
	linux-kernel, netdev, Arun.Ramadoss, intel-wired-lan

> > > What is the code flow through the kernel with EEE? I wasn't able to find
> > > a good explanation about it.
> > > 
> > > Is it advertised by default, if supported? I guess phy_advertise_supported()
> > > does that.

The old flow is poorly defined. If the MAC supports EEE, it should
call phy_init_eee(). That looks at the results of auto-neg and returns
if EEE has been negotiated or not.

However, i'm not aware of any code which disables by default the
advertisement of EEE, or actually enables the negotiation of EEE. So
there are probably a number of PHYs which are EEE capable, connected
to a MAC driver which does not call phy_init_eee() and are advertising
EEE and negotiating EEE. There might also be a subset of that which
are actually doing EEE, despite not calling phy_init_eee().

So the current code is not good, and there is a danger we introduce
power regressions as we sort this out.

The current MAC/PHY API is pretty broken. We probably should be
handling this similar to pause. A MAC which supports pause should call
phy_support_asym_pause() or phy_support_sym_pause() which will cause
the PHY to advertise its supported Pause modes. So we might want to
add a phy_support_eee()? We then want the result of EEE negotiation
available in phydev for when the link_adjust() callback is called.

A quick look at a few MAC drivers seems to indicate many are getting
it wrong and don't actually wait for the result of the auto-neg....

   Andrew


^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function
  2023-02-06 11:22       ` Vladimir Oltean
@ 2023-02-06 15:42         ` Andrew Lunn
  0 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-06 15:42 UTC (permalink / raw)
  To: Vladimir Oltean
  Cc: Oleksij Rempel, Woojung Huh, UNGLinuxDriver, Vivien Didelot,
	Florian Fainelli, David S. Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni, Wei Fang, Heiner Kallweit, kernel, linux-kernel,
	netdev, Arun.Ramadoss, intel-wired-lan

On Mon, Feb 06, 2023 at 01:22:46PM +0200, Vladimir Oltean wrote:
> On Mon, Feb 06, 2023 at 11:49:55AM +0100, Oleksij Rempel wrote:
> > > Why stop at 10GBase-KR? Register 3.20 defines EEE abilities up to 100G
> > > (for speeds >10G, there seem to be 2 modes, "deep sleep" or "fast wake",
> > > with "deep sleep" being essentially equivalent to the only mode
> > > available for <=10G modes).
> > 
> > Hm,
> > 
> > If i take only deep sleep, missing modes are:
> > 3.20.13 100GBASE-R deep sleep
> >        family of Physical Layer devices using 100GBASE-R encoding:
> >        100000baseCR4_Full
> >        100000baseKR4_Full
> >        100000baseCR10_Full (missing)
> >        100000baseSR4_Full
> >        100000baseSR10_Full (missing)
> >        100000baseLR4_ER4_Full
> > 
> > 3.20.11 25GBASE-R deep sleep
> >        family of Physical Layer devices using 25GBASE-R encoding:
> >        25000baseCR_Full
> >        25000baseER_Full (missing)
> >        25000baseKR_Full
> >        25000baseLR_Full (missing)
> >        25000baseSR_Full
> > 
> > 3.20.9 40GBASE-R deep sleep
> >        family of Physical Layer devices using 40GBASE-R encoding:
> >        40000baseKR4_Full
> >        40000baseCR4_Full
> >        40000baseSR4_Full
> >        40000baseLR4_Full
> > 
> > 3.20.7 40GBASE-T
> >        40000baseT_Full (missing)
> > 
> > I have no experience with modes > 1Gbit. Do all of them correct? What
> > should we do with missing modes? Or may be it make sense to implement >
> > 10G modes separately?
> 
> Given the fact that UAPI needs an extension to cover supported/advertisement
> bits > 31, I think it makes sense to add these separately. I had not
> realized this when I commented on this patch. I don't think we want the
> kernel to advertise EEE for some link modes without user space seeing it.

We also don't currently support any PHYs which do more than 10G. So i
don't see any need for 40GB and above at the moment.

      Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-06 14:10     ` Vladimir Oltean
  2023-02-06 15:39       ` Andrew Lunn
@ 2023-02-06 18:25       ` Oleksij Rempel
  1 sibling, 0 replies; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-06 18:25 UTC (permalink / raw)
  To: Vladimir Oltean
  Cc: Richard Cochran, Woojung Huh, Andrew Lunn, Arun.Ramadoss,
	Florian Fainelli, netdev, linux-kernel, Vivien Didelot,
	Eric Dumazet, Paolo Abeni, Wei Fang, kernel, intel-wired-lan,
	Jakub Kicinski, UNGLinuxDriver, David S. Miller, Heiner Kallweit

On Mon, Feb 06, 2023 at 04:10:38PM +0200, Vladimir Oltean wrote:
> On Mon, Feb 06, 2023 at 06:47:13AM +0100, Oleksij Rempel wrote:
> > On Sat, Feb 04, 2023 at 02:13:32AM +0200, Vladimir Oltean wrote:
> > > On Wed, Feb 01, 2023 at 03:58:22PM +0100, Oleksij Rempel wrote:
> > > > With this patch series we provide EEE control for KSZ9477 family of switches and
> > > > AR8035 with i.MX6 configuration.
> > > > According to my tests, on a system with KSZ8563 switch and 100Mbit idle link,
> > > > we consume 0,192W less power per port if EEE is enabled.
> > > 
> > > What is the code flow through the kernel with EEE? I wasn't able to find
> > > a good explanation about it.
> > > 
> > > Is it advertised by default, if supported? I guess phy_advertise_supported()
> > > does that.
> > 
> > Ack.
> > 
> > > But is that desirable? Doesn't EEE cause undesired latency for MAC-level
> > > PTP timestamping on an otherwise idle link?
> > 
> > Theoretically, MAC controls Low Power Idle states and even with some
> > "Wake" latency should be fully aware of actual ingress and egress time
> > stamps.
> 
> I'm not sure if this is also true with Atheros SmartEEE, where the PHY
> is the one who enters LPI mode and buffers packets until it wakes up?

Yes, you right. With SmartEEE without MAC assistance, PTP will be
broken. At the same time, if MAC is PTP and EEE capable, the same PHY
with SmartEEE disabled should work just fine.

> > Practically, right now I do not have such HW to confirm it. My project
> > is affected by EEE in different ways:
> 
> Doesn't FEC support PTP?

FEC do supports PTP, but do not support EEE on i.MX6/7 variants.

> > - with EEE PTP has too much jitter
> > - without EEE, the devices consumes too much power in standby mode with
> >   WoL enabled. Even switching to 10BaseT less power as 100BaseTX with
> >   EEE would do.
> > 
> > My view is probably biased by my environment - PTP is relatively rare
> > use case. EEE saves power (0,2W+0,2W per link in my case). Summary power
> > saving of all devices is potentially equal to X amount of power plants. 
> > So, EEE should be enabled by default.
> 
> I'm not contesting the value of EEE. Just wondering whether it's best
> for the kernel, rather than user space, to enable it by default.

I woulds say, at the end the switch will decide what functionality will
be advertised. Other nodes should just tell what capabilities they
support.

> > 
> > Beside, flow control (enabled by default) affects PTP in some cases too.
> 
> You are probably talking about the fact that flow control may affect
> end-to-end delay measurements (across switches in a LAN). Yes, but EEE
> (or at least SmartEEE) may affect peer-to-peer delay measurements, which
> I see as worse.

I agree. User space should be notified some how about SmartEEE
functionality. Especially if it is incompatible with some other
functionality like PTP. It took me some time to understand why my PTP sync was
so unstable. SmartEEE was just silently enabled by HW and no EEE related
information was provided to user space.

> > May be ptp4l should warn about this options? We should be able to detect
> > it from user space.
> 
> This isn't necessarily a bad idea, even though it would end up
> renegotiating and losing the link.

My idea was to inform the user, not actively do what ever is needed. It
can conflict with other services or make system administrator scratch the
head without understanding why things magically happen.

> Maybe it would be good to drag Richard Cochran into the discussion too.
> After all he's the one who should agree what should and what shouldn't
> ptp4l be concerned with.

ACK.

Regards,
Oleksij
-- 
Pengutronix e.K.                           |                             |
Steuerwalder Str. 21                       | http://www.pengutronix.de/  |
31137 Hildesheim, Germany                  | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-06 15:39       ` Andrew Lunn
@ 2023-02-06 18:37         ` Oleksij Rempel
  2023-02-06 20:21           ` Andrew Lunn
  0 siblings, 1 reply; 43+ messages in thread
From: Oleksij Rempel @ 2023-02-06 18:37 UTC (permalink / raw)
  To: Andrew Lunn
  Cc: Vladimir Oltean, Richard Cochran, Woojung Huh, UNGLinuxDriver,
	Vivien Didelot, Florian Fainelli, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit, kernel,
	linux-kernel, netdev, Arun.Ramadoss, intel-wired-lan

On Mon, Feb 06, 2023 at 04:39:52PM +0100, Andrew Lunn wrote:
> > > > What is the code flow through the kernel with EEE? I wasn't able to find
> > > > a good explanation about it.
> > > > 
> > > > Is it advertised by default, if supported? I guess phy_advertise_supported()
> > > > does that.
> 
> The old flow is poorly defined. If the MAC supports EEE, it should
> call phy_init_eee(). That looks at the results of auto-neg and returns
> if EEE has been negotiated or not.
> 
> However, i'm not aware of any code which disables by default the
> advertisement of EEE, or actually enables the negotiation of EEE. So
> there are probably a number of PHYs which are EEE capable, connected
> to a MAC driver which does not call phy_init_eee() and are advertising
> EEE and negotiating EEE. There might also be a subset of that which
> are actually doing EEE, despite not calling phy_init_eee().
> 
> So the current code is not good, and there is a danger we introduce
> power regressions as we sort this out.
> 
> The current MAC/PHY API is pretty broken. We probably should be
> handling this similar to pause. A MAC which supports pause should call
> phy_support_asym_pause() or phy_support_sym_pause() which will cause
> the PHY to advertise its supported Pause modes. So we might want to
> add a phy_support_eee()? We then want the result of EEE negotiation
> available in phydev for when the link_adjust() callback is called.

Good point.

SmartEEE will be probably a bit more challenging. If MAC do not
advertise EEE support, SmartEEE can be enabled. But it would break PTP
if SmartEEE is active. Except SmartEEE capable PHY implements own PTP
support. In any case, user space will need extra information to
identify potential issues.

> A quick look at a few MAC drivers seems to indicate many are getting
> it wrong and don't actually wait for the result of the auto-neg....

Some ethernet driver trying to do own EEE state detection, and doing
false positive detection on not supported states - for example half
duplex.

-- 
Pengutronix e.K.                           |                             |
Steuerwalder Str. 21                       | http://www.pengutronix.de/  |
31137 Hildesheim, Germany                  | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6
  2023-02-06 18:37         ` Oleksij Rempel
@ 2023-02-06 20:21           ` Andrew Lunn
  0 siblings, 0 replies; 43+ messages in thread
From: Andrew Lunn @ 2023-02-06 20:21 UTC (permalink / raw)
  To: Oleksij Rempel
  Cc: Vladimir Oltean, Richard Cochran, Woojung Huh, UNGLinuxDriver,
	Vivien Didelot, Florian Fainelli, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, Wei Fang, Heiner Kallweit, kernel,
	linux-kernel, netdev, Arun.Ramadoss, intel-wired-lan

> SmartEEE will be probably a bit more challenging. If MAC do not
> advertise EEE support, SmartEEE can be enabled. But it would break PTP
> if SmartEEE is active. Except SmartEEE capable PHY implements own PTP
> support. In any case, user space will need extra information to
> identify potential issues.

If we have a MAC driver which does not implement the ethtool set_eee()
and get_eee() ops, and a dev->phydev with the SmartEEE flag set, we
could have net/ethtool/eee.c call direct into phylib.

As for PTP and EEE, maybe we want the core PTP code to try calling
get_eee() and at minimum issue a warning if it is enabled, if it
thinks MAC PTP is being used?

       Andrew

^ permalink raw reply	[flat|nested] 43+ messages in thread

end of thread, other threads:[~2023-02-06 20:22 UTC | newest]

Thread overview: 43+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-02-01 14:58 [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 01/23] net: dsa: microchip: enable EEE support Oleksij Rempel
2023-02-04  0:14   ` Vladimir Oltean
2023-02-01 14:58 ` [PATCH net-next v4 02/23] net: phy: add genphy_c45_read_eee_abilities() function Oleksij Rempel
2023-02-01 17:12   ` Andrew Lunn
2023-02-04  0:54   ` Vladimir Oltean
2023-02-06 10:49     ` Oleksij Rempel
2023-02-06 11:22       ` Vladimir Oltean
2023-02-06 15:42         ` Andrew Lunn
2023-02-01 14:58 ` [PATCH net-next v4 03/23] net: phy: micrel: add ksz9477_get_features() Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 04/23] net: phy: export phy_check_valid() function Oleksij Rempel
2023-02-01 17:15   ` Andrew Lunn
2023-02-01 14:58 ` [PATCH net-next v4 05/23] net: phy: add genphy_c45_ethtool_get/set_eee() support Oleksij Rempel
2023-02-01 17:20   ` Andrew Lunn
2023-02-01 20:18   ` Jakub Kicinski
2023-02-04  1:11   ` Vladimir Oltean
2023-02-01 14:58 ` [PATCH net-next v4 06/23] net: phy: c22: migrate to genphy_c45_write_eee_adv() Oleksij Rempel
2023-02-01 17:28   ` Andrew Lunn
2023-02-01 14:58 ` [PATCH net-next v4 07/23] net: phy: c45: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 08/23] net: phy: migrate phy_init_eee() to genphy_c45_eee_is_active() Oleksij Rempel
2023-02-01 16:41   ` Andrew Lunn
2023-02-01 14:58 ` [PATCH net-next v4 09/23] net: phy: start using genphy_c45_ethtool_get/set_eee() Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 10/23] net: phy: add driver specific get/set_eee support Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 11/23] net: phy: at803x: implement ethtool access to SmartEEE functionality Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 12/23] net: phy: at803x: ar8035: fix EEE support for half duplex links Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 13/23] net: phy: add PHY specifica flag to signal SmartEEE support Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 14/23] net: phy: at803x: add PHY_SMART_EEE flag to AR8035 Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 15/23] net: phy: add phy_has_smarteee() helper Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 16/23] net: fec: add support for PHYs with SmartEEE support Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 17/23] e1000e: replace EEE ethtool helpers to linkmode variants Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 18/23] igb: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 19/23] igc: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 20/23] tg3: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 21/23] r8152: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 22/23] net: usb: ax88179_178a: " Oleksij Rempel
2023-02-01 14:58 ` [PATCH net-next v4 23/23] net: mdio: drop EEE ethtool helpers in favor " Oleksij Rempel
2023-02-04  0:13 ` [PATCH net-next v4 00/23] net: add EEE support for KSZ9477 and AR8035 with i.MX6 Vladimir Oltean
2023-02-06  5:47   ` Oleksij Rempel
2023-02-06 14:10     ` Vladimir Oltean
2023-02-06 15:39       ` Andrew Lunn
2023-02-06 18:37         ` Oleksij Rempel
2023-02-06 20:21           ` Andrew Lunn
2023-02-06 18:25       ` Oleksij Rempel

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).