mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [PATCH net] net: stmmac: request the MDIO reset GPIO only once
@ 2026-09-17 12:54 Linkui Xiao
  2026-09-17 16:10 ` Maxime Chevallier
  0 siblings, 1 reply; 3+ messages in thread
From: Linkui Xiao @ 2026-09-17 12:54 UTC (permalink / raw)
  To: maxime.chevallier, andrew+netdev, davem, edumazet, kuba, pabeni,
	mcoquelin.stm32, alexandre.torgue
  Cc: netdev, linux-stm32, linux-arm-kernel, linux-kernel, Linkui Xiao, stable

From: Linkui Xiao <xiaolinkui@kylinos.cn>

stmmac_mdio_reset() calls devm_gpiod_get_optional() every time it runs.
A GPIO line can only be requested once per consumer, so from the second
call on gpiod_request_commit() returns -EBUSY. devm_gpiod_get_optional()
only turns -ENOENT into NULL, hence the error is passed straight back
and stmmac_mdio_reset() bails out before pulsing "snps,reset" and before
running the STE101P MDC workaround.

The first call, made by mdiobus_register(), succeeds, so the failure is
only visible later on: every resume that does not use WoL goes through
stmmac_resume() -> stmmac_mdio_reset() and returns without resetting the
PHY. Boards needing a hard PHY reset after power down then come back
with a dead or badly negotiated link, and nothing reports it because
both callers ignore the return value.

The descriptor used to be cached in stmmac_mdio_bus_data::reset_gpio so
that it was requested exactly once. Commit ae26c1c6cb9b ("stmmac: fix
PHY reset during resume") relies on that cache to reuse the line on
every call. Dropping the cache removed the protection without replacing
it and reintroduced the very bug it had been fixed for.

Cache the descriptor in struct stmmac_priv instead and only look it up
while it is still unknown. It is devm-managed against the platform
device, so it stays valid for the whole lifetime of the driver.

Fixes: 7e770b252a62 ("net: stmmac: drop the reset GPIO from struct stmmac_mdio_bus_data")
Cc: stable@vger.kernel.org
Signed-off-by: Linkui Xiao <xiaolinkui@kylinos.cn>
---
 drivers/net/ethernet/stmicro/stmmac/stmmac.h  |  2 ++
 .../net/ethernet/stmicro/stmmac/stmmac_mdio.c | 20 ++++++++++++++-----
 2 files changed, 17 insertions(+), 5 deletions(-)

diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac.h b/drivers/net/ethernet/stmicro/stmmac/stmmac.h
index 7582fca63741..986fb43db45f 100644
--- a/drivers/net/ethernet/stmicro/stmmac/stmmac.h
+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac.h
@@ -25,6 +25,7 @@
 #include <net/xdp.h>
 #include <uapi/linux/bpf.h>
 
+struct gpio_desc;
 struct stmmac_pcs;
 
 struct stmmac_resources {
@@ -287,6 +288,7 @@ struct stmmac_priv {
 
 	unsigned int pause_time;
 	struct mii_bus *mii;
+	struct gpio_desc *mdio_reset_gpio;
 
 	struct stmmac_pcs *integrated_pcs;
 
diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
index afe98ff5bdcb..5f99d7db39f7 100644
--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
@@ -389,11 +389,21 @@ int stmmac_mdio_reset(struct mii_bus *bus)
 		struct gpio_desc *reset_gpio;
 		u32 delays[3] = { 0, 0, 0 };
 
-		reset_gpio = devm_gpiod_get_optional(priv->device,
-						     "snps,reset",
-						     GPIOD_OUT_LOW);
-		if (IS_ERR(reset_gpio))
-			return PTR_ERR(reset_gpio);
+		/* Request the reset line only once and reuse the descriptor
+		 * afterwards. A second request of the very same line makes
+		 * gpiolib fail with -EBUSY, which devm_gpiod_get_optional()
+		 * passes through because it only filters out -ENOENT. The
+		 * reset would then abort early and leave the PHY un-reset.
+		 */
+		if (!priv->mdio_reset_gpio) {
+			priv->mdio_reset_gpio =
+				devm_gpiod_get_optional(priv->device,
+							"snps,reset",
+							GPIOD_OUT_LOW);
+			if (IS_ERR(priv->mdio_reset_gpio))
+				return PTR_ERR(priv->mdio_reset_gpio);
+		}
+		reset_gpio = priv->mdio_reset_gpio;
 
 		device_property_read_u32_array(priv->device,
 					       "snps,reset-delays-us",
-- 
2.25.1


^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2026-09-18  8:42 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-09-17 12:54 [PATCH net] net: stmmac: request the MDIO reset GPIO only once Linkui Xiao
2026-09-17 16:10 ` Maxime Chevallier
2026-09-18  8:41   ` Linkui Xiao

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®