From 2e507f2edc585bd2f68286fd9d2c29f82170191e Mon Sep 17 00:00:00 2001 From: Markus Stockhausen Date: Wed, 18 Feb 2026 08:12:06 +0100 Subject: [PATCH] realtek: mdio: taker over RTL931x PHY polling from DSA PHY polling setup has found a home in the mdio driver. For RTL931x there still exists a setup sequence for polling type (serdes/mdio) in the DSA driver. Put it where it belongs. Signed-off-by: Markus Stockhausen Link: https://github.com/openwrt/openwrt/pull/22075 Signed-off-by: Robert Marko --- .../files-6.12/drivers/net/dsa/rtl83xx/dsa.c | 5 ---- .../drivers/net/dsa/rtl83xx/rtl83xx.h | 1 - .../drivers/net/dsa/rtl83xx/rtl931x.c | 29 ------------------- .../drivers/net/mdio/mdio-realtek-otto.c | 25 ++++++++++------ 4 files changed, 16 insertions(+), 44 deletions(-) diff --git a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/dsa.c b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/dsa.c index 5612ba8e40..abc0179496 100644 --- a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/dsa.c +++ b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/dsa.c @@ -607,11 +607,6 @@ static int rtldsa_93xx_setup(struct dsa_switch *ds) } } priv->r->traffic_set(priv->cpu_port, BIT_ULL(priv->cpu_port)); - - /* Configure how MAC gets PHY ability for each port */ - if (priv->family_id == RTL9310_FAMILY_ID) - rtldsa_931x_config_phy_ability_source(priv); - priv->r->print_matrix(); /* TODO: Initialize statistics */ diff --git a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl83xx.h b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl83xx.h index cee9968670..3e68114277 100644 --- a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl83xx.h +++ b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl83xx.h @@ -177,7 +177,6 @@ void rtldsa_930x_print_matrix(void); /* RTL931x-specific */ irqreturn_t rtl931x_switch_irq(int irq, void *dev_id); void rtldsa_931x_print_matrix(void); -void rtldsa_931x_config_phy_ability_source(struct rtl838x_switch_priv *priv); int rtl83xx_lag_add(struct dsa_switch *ds, int group, int port, struct netdev_lag_upper_info *info); int rtl83xx_lag_del(struct dsa_switch *ds, int group, int port); diff --git a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl931x.c b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl931x.c index b367436bee..74d1b613f0 100644 --- a/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl931x.c +++ b/target/linux/realtek/files-6.12/drivers/net/dsa/rtl83xx/rtl931x.c @@ -25,11 +25,6 @@ #define RTL931X_VLAN_PORT_TAG_ITPID_IDX_MASK GENMASK(2, 1) #define RTL931X_VLAN_PORT_TAG_ITPID_KEEP_MASK GENMASK(0, 0) -#define RTLDSA_931X_SMI_PHY_ABLTY_GET_SEL 0x0cac -#define RTLDSA_931X_PHY_ABLTY_OUTBAND_MDIO 0x0 -#define RTLDSA_931X_PHY_ABLTY_INBAND_SDS_POLL 0x1 -#define RTLDSA_931X_PHY_ABLTY_SDS_ABLTY_BUS 0x2 - /* Definition of the RTL931X-specific template field IDs as used in the PIE */ enum template_field_id { TEMPLATE_FIELD_SPM0 = 1, @@ -1776,30 +1771,6 @@ static void rtldsa_931x_qos_init(struct rtl838x_switch_priv *priv) rtldsa_931x_qos_set_scheduling_queue_weights(priv); } -void rtldsa_931x_config_phy_ability_source(struct rtl838x_switch_priv *priv) -{ - u32 phy_ablty_sel[4] = {0}; - - for (int port = 0; port < priv->cpu_port; port++) { - u32 val = RTLDSA_931X_PHY_ABLTY_OUTBAND_MDIO; - - /* port driven by SerDes */ - if (!priv->ports[port].phy && priv->pcs[port]) - val = RTLDSA_931X_PHY_ABLTY_SDS_ABLTY_BUS; - - phy_ablty_sel[port / 16] |= (val & 0x3) << ((port % 16) * 2); - } - - pr_debug("%s: phy_ablty_sel [0] %x [1] %x [2] %x [3] %x\n", __func__, - phy_ablty_sel[0], phy_ablty_sel[1], phy_ablty_sel[2], - phy_ablty_sel[3]); - - sw_w32(phy_ablty_sel[0], RTLDSA_931X_SMI_PHY_ABLTY_GET_SEL); - sw_w32(phy_ablty_sel[1], RTLDSA_931X_SMI_PHY_ABLTY_GET_SEL + 0x4); - sw_w32(phy_ablty_sel[2], RTLDSA_931X_SMI_PHY_ABLTY_GET_SEL + 0x8); - sw_w32(phy_ablty_sel[3], RTLDSA_931X_SMI_PHY_ABLTY_GET_SEL + 0xc); -} - const struct rtldsa_config rtldsa_931x_cfg = { .mask_port_reg_be = rtl839x_mask_port_reg_be, .set_port_reg_be = rtl839x_set_port_reg_be, diff --git a/target/linux/realtek/files-6.12/drivers/net/mdio/mdio-realtek-otto.c b/target/linux/realtek/files-6.12/drivers/net/mdio/mdio-realtek-otto.c index f008c59b4f..1a70e5d3a0 100644 --- a/target/linux/realtek/files-6.12/drivers/net/mdio/mdio-realtek-otto.c +++ b/target/linux/realtek/files-6.12/drivers/net/mdio/mdio-realtek-otto.c @@ -95,7 +95,9 @@ #define RTMDIO_931X_SMI_INDRT_ACCESS_CTRL_2 (0x0C08) #define RTMDIO_931X_SMI_INDRT_ACCESS_CTRL_3 (0x0C10) #define RTMDIO_931X_SMI_INDRT_ACCESS_MMD_CTRL (0x0C18) -#define RTMDIO_931X_MAC_L2_GLOBAL_CTRL2 (0x1358) +#define RTMDIO_931X_SMI_PHY_ABLTY_GET_SEL (0x0CAC) +#define RTMDIO_931X_SMY_PHY_ABLTY_MDIO 0x0 +#define RTMDIO_931X_SMI_PHY_ABLTY_SDS 0x2 #define RTMDIO_931X_SMI_PORT_POLLING_SEL (0x0C9C) #define RTMDIO_931X_SMI_PORT_ADDR_CTRL (0x0C74) #define RTMDIO_931X_SMI_10GPHY_POLLING_SEL0 (0x0CF0) @@ -715,6 +717,7 @@ static void rtmdio_930x_setup_polling(struct mii_bus *bus) struct rtmdio_phy_info phyinfo; unsigned int mask, val; + /* reset all ports to "SerDes driven" */ regmap_write(ctrl->map, RTMDIO_930X_SMI_MAC_TYPE_CTRL, 0); /* Define PHY specific polling parameters */ @@ -722,7 +725,7 @@ static void rtmdio_930x_setup_polling(struct mii_bus *bus) if (rtmdio_get_phy_info(bus, addr, &phyinfo)) continue; - /* port MAC type */ + /* set port to "PHY driven" */ mask = addr > 23 ? 0x7 << ((addr - 24) * 3 + 12): 0x3 << ((addr / 4) * 2); val = phyinfo.mac_type << (ffs(mask) - 1); regmap_update_bits(ctrl->map, RTMDIO_930X_SMI_MAC_TYPE_CTRL, mask, val); @@ -789,13 +792,12 @@ static void rtmdio_931x_setup_polling(struct mii_bus *bus) struct rtmdio_phy_info phyinfo; u32 val; - /* Define PHY specific polling parameters - * - * Those are applied per port here but the SoC only supports them - * per SMI bus or for all GPHY/10GPHY. This should be guarded by - * the existing hardware designs (i.e. only equally polled PHYs on - * the same SMI bus or kind of PHYs). - */ + /* reset all ports to "SerDes driven" */ + for (int reg = 0; reg < 4; reg++) + regmap_write(ctrl->map, RTMDIO_931X_SMI_PHY_ABLTY_GET_SEL + reg * 4, + RTMDIO_931X_SMI_PHY_ABLTY_SDS * 0x55555555U); + + /* Define PHY specific polling parameters */ for_each_port(ctrl, addr) { int smi = ctrl->smi_bus[addr]; unsigned int mask, val; @@ -803,6 +805,11 @@ static void rtmdio_931x_setup_polling(struct mii_bus *bus) if (rtmdio_get_phy_info(bus, addr, &phyinfo)) continue; + /* set port to "PHY driven" */ + mask = GENMASK(1, 0) << ((addr % 16) * 2); + val = RTMDIO_931X_SMY_PHY_ABLTY_MDIO << (ffs(mask) - 1); + regmap_update_bits(ctrl->map, RTMDIO_931X_SMI_PHY_ABLTY_GET_SEL + (addr / 16) * 4, + mask, val); mask = val = 0; /* PRVTE0 polling */