Instituto Nacional de ciberseguridad. Sección Incibe
Instituto Nacional de Ciberseguridad. Sección INCIBE-CERT

Vulnerabilidad en kernel de Linux (CVE-2025-37945)

Gravedad CVSS v3.1:
MEDIA
Tipo:
CWE-476 Desreferencia a puntero nulo (NULL)
Fecha de publicación:
20/05/2025
Última modificación:
17/11/2025

Descripción

En el kernel de Linux, se ha resuelto la siguiente vulnerabilidad: net: phy: permite que las operaciones PM del bus MDIO inicien o detengan la máquina de estados para PHY controlada por phylink DSA tiene 2 tipos de controladores: 1. Los que llaman a dsa_switch_suspend() y dsa_switch_resume() desde las operaciones PM de su dispositivo: qca8k-8xxx, bcm_sf2, microchip ksz 2. Los que no lo hacen: todos los demás. Los métodos anteriores deberían ser opcionales. Para el tipo 1, dsa_switch_suspend() llama a dsa_user_suspend() -> phylink_stop() y dsa_switch_resume() llama a dsa_user_resume() -> phylink_start(). Estos parecen buenos candidatos para establecer mac_managed_pm = true porque esa es esencialmente su definición [1], pero ese no parece ser el mayor problema por ahora y no es en lo que se centra este cambio. Hablando estrictamente sobre la segunda categoría de controladores DSA (que no tienen PM administrado por MAC, lo que significa que para sus PHYs conectados, mdio_bus_phy_suspend() y mdio_bus_phy_resume() deben ejecutarse por completo), he notado que se activa la siguiente advertencia de mdio_bus_phy_resume(): WARN_ON(phydev->state != PHY_HALTED && phydev->state != PHY_READY && phydev->state != PHY_UP); porque la máquina de estados PHY está en ejecución. Se está ejecutando como resultado de un dsa_user_open() -> ... -> phylink_start() -> phy_start() previo iniciado por el usuario. El mdio_bus_phy_suspend() anterior debería haber llamado a phy_stop_machine(), pero no lo hizo. Por eso, el PHY está en estado PHY_NOLINK cuando se ejecuta mdio_bus_phy_resume(). mdio_bus_phy_suspend() no llamó a phy_stop_machine() porque, para phylink, el puntero a la función phydev->adjust_link es NULL. Esto parece ser un tecnicismo introducido por el commit fddd91016d16 ("phylib: corrección del reinicio de la máquina de estados PAL al reanudar"). Esta confirmación se escribió antes de que existiera phylink y su objetivo era evitar fallos con controladores de consumidor que no utilizan la máquina de estados PHY; phylink siempre lo hace al usar una PHY. Sin embargo, phylink no se ha desarrollado históricamente con la suspensión/reanudación en mente, y aparentemente no se ha probado demasiado en ese escenario, lo que ha permitido que este error pase desapercibido durante tanto tiempo. Además, antes de WARN_ON(), probablemente habría sido invisible. De hecho, este problema no se limita a los controladores DSA de tipo 2 (según la clasificación ad hoc anterior), sino que se puede extrapolar a cualquier controlador MAC con phylink y operaciones de PM PHY gestionadas por bus MDIO. DSA es justo donde se reportó el problema. Suponiendo que mac_managed_pm esté configurado correctamente, una búsqueda rápida indica que los siguientes controladores podrían estar afectados: $ grep -Zlr PHYLINK_NETDEV drivers/ | xargs -0 grep -L mac_managed_pm drivers/net/ethernet/atheros/ag71xx.c drivers/net/ethernet/microchip/sparx5/sparx5_main.c drivers/net/ethernet/microchip/lan966x/lan966x_main.c drivers/net/ethernet/freescale/dpaa2/dpaa2-mac.c drivers/net/ethernet/freescale/fs_enet/fs_enet-main.c drivers/net/ethernet/freescale/dpaa/dpaa_eth.c drivers/net/ethernet/freescale/ucc_geth.c drivers/net/ethernet/freescale/enetc/enetc_pf_common.c drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c drivers/net/ethernet/marvell/mvneta.c Haga que las condiciones existentes dependan de que el dispositivo PHY tenga una implementación de phydev->phy_link_change() igual al phy_link_change() predeterminado proporcionado por phylib. De lo contrario, sabemos implícitamente que phydev cuenta con la función de devolución de llamada phylink_phy_change() proporcionada por phylink, y cuando se usa phylink, la máquina de estados PHY siempre debe detenerse/iniciar en la ruta de suspensión/reinicio. El código está estructurado de tal manera que, si phydev->phy_link_change() no está presente, es cuestión de tiempo hasta que el kernel se bloquee; no es necesario complicar aún más la prueba. Por lo tanto, si el PM no se gestiona, se trunca.

Productos y versiones vulnerables

CPE Desde Hasta
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 5.15.63 (incluyendo) 5.16 (excluyendo)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 5.19.4 (incluyendo) 6.12.24 (excluyendo)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 6.13 (incluyendo) 6.13.12 (excluyendo)
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* 6.14 (incluyendo) 6.14.3 (excluyendo)
cpe:2.3:o:linux:linux_kernel:6.15:rc1:*:*:*:*:*:*