CVE-2025-37945

Severity CVSS v4.0:
Pending analysis
Type:
CWE-476 NULL Pointer Dereference
Publication date:
20/05/2025
Last modified:
06/04/2026

Description

In the Linux kernel, the following vulnerability has been resolved:<br /> <br /> net: phy: allow MDIO bus PM ops to start/stop state machine for phylink-controlled PHY<br /> <br /> DSA has 2 kinds of drivers:<br /> <br /> 1. Those who call dsa_switch_suspend() and dsa_switch_resume() from<br /> their device PM ops: qca8k-8xxx, bcm_sf2, microchip ksz<br /> 2. Those who don&amp;#39;t: all others. The above methods should be optional.<br /> <br /> For type 1, dsa_switch_suspend() calls dsa_user_suspend() -&gt; phylink_stop(),<br /> and dsa_switch_resume() calls dsa_user_resume() -&gt; phylink_start().<br /> These seem good candidates for setting mac_managed_pm = true because<br /> that is essentially its definition [1], but that does not seem to be the<br /> biggest problem for now, and is not what this change focuses on.<br /> <br /> Talking strictly about the 2nd category of DSA drivers here (which<br /> do not have MAC managed PM, meaning that for their attached PHYs,<br /> mdio_bus_phy_suspend() and mdio_bus_phy_resume() should run in full),<br /> I have noticed that the following warning from mdio_bus_phy_resume() is<br /> triggered:<br /> <br /> WARN_ON(phydev-&gt;state != PHY_HALTED &amp;&amp; phydev-&gt;state != PHY_READY &amp;&amp;<br /> phydev-&gt;state != PHY_UP);<br /> <br /> because the PHY state machine is running.<br /> <br /> It&amp;#39;s running as a result of a previous dsa_user_open() -&gt; ... -&gt;<br /> phylink_start() -&gt; phy_start() having been initiated by the user.<br /> <br /> The previous mdio_bus_phy_suspend() was supposed to have called<br /> phy_stop_machine(), but it didn&amp;#39;t. So this is why the PHY is in state<br /> PHY_NOLINK by the time mdio_bus_phy_resume() runs.<br /> <br /> mdio_bus_phy_suspend() did not call phy_stop_machine() because for<br /> phylink, the phydev-&gt;adjust_link function pointer is NULL. This seems a<br /> technicality introduced by commit fddd91016d16 ("phylib: fix PAL state<br /> machine restart on resume"). That commit was written before phylink<br /> existed, and was intended to avoid crashing with consumer drivers which<br /> don&amp;#39;t use the PHY state machine - phylink always does, when using a PHY.<br /> But phylink itself has historically not been developed with<br /> suspend/resume in mind, and apparently not tested too much in that<br /> scenario, allowing this bug to exist unnoticed for so long. Plus, prior<br /> to the WARN_ON(), it would have likely been invisible.<br /> <br /> This issue is not in fact restricted to type 2 DSA drivers (according to<br /> the above ad-hoc classification), but can be extrapolated to any MAC<br /> driver with phylink and MDIO-bus-managed PHY PM ops. DSA is just where<br /> the issue was reported. Assuming mac_managed_pm is set correctly, a<br /> quick search indicates the following other drivers might be affected:<br /> <br /> $ grep -Zlr PHYLINK_NETDEV drivers/ | xargs -0 grep -L mac_managed_pm<br /> drivers/net/ethernet/atheros/ag71xx.c<br /> drivers/net/ethernet/microchip/sparx5/sparx5_main.c<br /> drivers/net/ethernet/microchip/lan966x/lan966x_main.c<br /> drivers/net/ethernet/freescale/dpaa2/dpaa2-mac.c<br /> drivers/net/ethernet/freescale/fs_enet/fs_enet-main.c<br /> drivers/net/ethernet/freescale/dpaa/dpaa_eth.c<br /> drivers/net/ethernet/freescale/ucc_geth.c<br /> drivers/net/ethernet/freescale/enetc/enetc_pf_common.c<br /> drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c<br /> drivers/net/ethernet/marvell/mvneta.c<br /> drivers/net/ethernet/marvell/prestera/prestera_main.c<br /> drivers/net/ethernet/mediatek/mtk_eth_soc.c<br /> drivers/net/ethernet/altera/altera_tse_main.c<br /> drivers/net/ethernet/wangxun/txgbe/txgbe_phy.c<br /> drivers/net/ethernet/meta/fbnic/fbnic_phylink.c<br /> drivers/net/ethernet/tehuti/tn40_phy.c<br /> drivers/net/ethernet/mscc/ocelot_net.c<br /> <br /> Make the existing conditions dependent on the PHY device having a<br /> phydev-&gt;phy_link_change() implementation equal to the default<br /> phy_link_change() provided by phylib. Otherwise, we implicitly know that<br /> the phydev has the phylink-provided phylink_phy_change() callback, and<br /> when phylink is used, the PHY state machine always needs to be stopped/<br /> started on the suspend/resume path. The code is structured as such that<br /> if phydev-&gt;phy_link_change() is absent, it is a matter of time until the<br /> kernel will crash - no need to further complicate the test.<br /> <br /> Thus, for the situation where the PM is not managed b<br /> ---truncated---

Vulnerable products and versions

CPE From Up to
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 5.15.63 (including) 5.16 (excluding)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 5.19.4 (including) 6.12.24 (excluding)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 6.13 (including) 6.13.12 (excluding)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 6.14 (including) 6.14.3 (excluding)
cpe:2.3:o:linux:linux_kernel:6.15:rc1:*:*:*:*:*:*