net: phy: c45: add genphy_c45_pma_read_ext_abilities() function
authorOleksij Rempel <o.rempel@pengutronix.de>
Tue, 12 Dec 2023 05:41:43 +0000 (06:41 +0100)
committerJakub Kicinski <kuba@kernel.org>
Thu, 14 Dec 2023 02:01:07 +0000 (18:01 -0800)
Move part of the genphy_c45_pma_read_abilities() code to a separate
function.

Some PHYs do not implement PMA/PMD status 2 register (Register 1.8) but
do implement PMA/PMD extended ability register (Register 1.11). To make
use of it, we need to be able to access this part of code separately.

Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
Reviewed-by: Andrew Lunn <andrew@lunn.ch>
Reviewed-by: Russell King (Oracle) <rmk+kernel@armlinux.org.uk>
Link: https://lore.kernel.org/r/20231212054144.87527-2-o.rempel@pengutronix.de
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
drivers/net/phy/phy-c45.c
include/linux/phy.h

index 8e6fd4962c4869550293daf5cdc9f4e279c80a8b..747d14bf152c37e341ec11e64e8be58ccba749c3 100644 (file)
@@ -919,6 +919,79 @@ int genphy_c45_pma_baset1_read_abilities(struct phy_device *phydev)
 }
 EXPORT_SYMBOL_GPL(genphy_c45_pma_baset1_read_abilities);
 
+/**
+ * genphy_c45_pma_read_ext_abilities - read supported link modes from PMA
+ * @phydev: target phy_device struct
+ *
+ * Read the supported link modes from the PMA/PMD extended ability register
+ * (Register 1.11).
+ */
+int genphy_c45_pma_read_ext_abilities(struct phy_device *phydev)
+{
+       int val;
+
+       val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PMA_EXTABLE);
+       if (val < 0)
+               return val;
+
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseLRM_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10GBLRM);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10GBT);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10GBKX4);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10GBKR);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_1000BT);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_1000BKX);
+
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_100BTX);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Half_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_100BTX);
+
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Full_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10BT);
+       linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Half_BIT,
+                        phydev->supported,
+                        val & MDIO_PMA_EXTABLE_10BT);
+
+       if (val & MDIO_PMA_EXTABLE_NBT) {
+               val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD,
+                                  MDIO_PMA_NG_EXTABLE);
+               if (val < 0)
+                       return val;
+
+               linkmode_mod_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
+                                phydev->supported,
+                                val & MDIO_PMA_NG_EXTABLE_2_5GBT);
+
+               linkmode_mod_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT,
+                                phydev->supported,
+                                val & MDIO_PMA_NG_EXTABLE_5GBT);
+       }
+
+       if (val & MDIO_PMA_EXTABLE_BT1) {
+               val = genphy_c45_pma_baset1_read_abilities(phydev);
+               if (val < 0)
+                       return val;
+       }
+
+       return 0;
+}
+EXPORT_SYMBOL_GPL(genphy_c45_pma_read_ext_abilities);
+
 /**
  * genphy_c45_pma_read_abilities - read supported link modes from PMA
  * @phydev: target phy_device struct
@@ -962,63 +1035,9 @@ int genphy_c45_pma_read_abilities(struct phy_device *phydev)
                         val & MDIO_PMA_STAT2_10GBER);
 
        if (val & MDIO_PMA_STAT2_EXTABLE) {
-               val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PMA_EXTABLE);
+               val = genphy_c45_pma_read_ext_abilities(phydev);
                if (val < 0)
                        return val;
-
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseLRM_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10GBLRM);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10GBT);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10GBKX4);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10GBKR);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_1000BT);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_1000BKX);
-
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_100BTX);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Half_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_100BTX);
-
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Full_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10BT);
-               linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Half_BIT,
-                                phydev->supported,
-                                val & MDIO_PMA_EXTABLE_10BT);
-
-               if (val & MDIO_PMA_EXTABLE_NBT) {
-                       val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD,
-                                          MDIO_PMA_NG_EXTABLE);
-                       if (val < 0)
-                               return val;
-
-                       linkmode_mod_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
-                                        phydev->supported,
-                                        val & MDIO_PMA_NG_EXTABLE_2_5GBT);
-
-                       linkmode_mod_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT,
-                                        phydev->supported,
-                                        val & MDIO_PMA_NG_EXTABLE_5GBT);
-               }
-
-               if (val & MDIO_PMA_EXTABLE_BT1) {
-                       val = genphy_c45_pma_baset1_read_abilities(phydev);
-                       if (val < 0)
-                               return val;
-               }
        }
 
        /* This is optional functionality. If not supported, we may get an error
index 6e7ebcc50b859a80f733d10bcdf48f90c8ce9c03..dbb5e13e3e1bf045ec1730578fd164bbb0c5bf30 100644 (file)
@@ -1866,6 +1866,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_pma_read_ext_abilities(struct phy_device *phydev);
 int genphy_c45_pma_baset1_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);