]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
net: ti: icssg-prueth: Fix ping failure after offload mode setup when link speed...
authorMD Danish Anwar <danishanwar@ti.com>
Thu, 26 Feb 2026 10:23:56 +0000 (15:53 +0530)
committerJakub Kicinski <kuba@kernel.org>
Sat, 28 Feb 2026 21:41:35 +0000 (13:41 -0800)
When both eth interfaces with links up are added to a bridge or hsr
interface, ping fails if the link speed is not 1Gbps (e.g., 100Mbps).

The issue is seen because when switching to offload (bridge/hsr) mode,
prueth_emac_restart() restarts the firmware and clears DRAM with
memset_io(), setting all memory to 0. This includes PORT_LINK_SPEED_OFFSET
which firmware reads for link speed. The value 0 corresponds to
FW_LINK_SPEED_1G (0x00), so for 1Gbps links the default value is correct
and ping works. For 100Mbps links, the firmware needs FW_LINK_SPEED_100M
(0x01) but gets 0 instead, causing ping to fail. The function
emac_adjust_link() is called to reconfigure, but it detects no state change
(emac->link is still 1, speed/duplex match PHY) so new_state remains false
and icssg_config_set_speed() is never called to correct the firmware speed
value.

The fix resets emac->link to 0 before calling emac_adjust_link() in
prueth_emac_common_start(). This forces new_state=true, ensuring
icssg_config_set_speed() is called to write the correct speed value to
firmware memory.

Fixes: 06feac15406f ("net: ti: icssg-prueth: Fix emac link speed handling")
Signed-off-by: MD Danish Anwar <danishanwar@ti.com>
Link: https://patch.msgid.link/20260226102356.2141871-1-danishanwar@ti.com
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
drivers/net/ethernet/ti/icssg/icssg_prueth.c

index 0939994c932f5322eebbaa1b2fe43e20d3dca5ae..42a881bee10923bb7ad674cfd58015e66592af7c 100644 (file)
@@ -273,6 +273,14 @@ static int prueth_emac_common_start(struct prueth *prueth)
                if (ret)
                        goto disable_class;
 
+               /* Reset link state to force reconfiguration in
+                * emac_adjust_link(). Without this, if the link was already up
+                * before restart, emac_adjust_link() won't detect any state
+                * change and will skip critical configuration like writing
+                * speed to firmware.
+                */
+               emac->link = 0;
+
                mutex_lock(&emac->ndev->phydev->lock);
                emac_adjust_link(emac->ndev);
                mutex_unlock(&emac->ndev->phydev->lock);