Messages in this thread Patch in this message | | | From | Sasha Levin <> | Subject | [PATCH AUTOSEL 5.4 11/73] net: phy: avoid clearing PHY interrupts twice in irq handler | Date | Wed, 18 Mar 2020 16:52:35 -0400 |
| |
From: Heiner Kallweit <hkallweit1@gmail.com>
[ Upstream commit 249bc9744e165abe74ae326f43e9d70bad54c3b7 ]
On all PHY drivers that implement did_interrupt() reading the interrupt status bits clears them. This means we may loose an interrupt that is triggered between calling did_interrupt() and phy_clear_interrupt(). As part of the fix make it a requirement that did_interrupt() clears the interrupt.
The Fixes tag refers to the first commit where the patch applies cleanly.
Fixes: 49644e68f472 ("net: phy: add callback for custom interrupt handler to struct phy_driver") Reported-by: Michael Walle <michael@walle.cc> Signed-off-by: Heiner Kallweit <hkallweit1@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net> Signed-off-by: Sasha Levin <sashal@kernel.org> --- drivers/net/phy/phy.c | 3 ++- include/linux/phy.h | 1 + 2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c index 105d389b58e74..ea890d802ffe5 100644 --- a/drivers/net/phy/phy.c +++ b/drivers/net/phy/phy.c @@ -761,7 +761,8 @@ static irqreturn_t phy_interrupt(int irq, void *phy_dat) phy_trigger_machine(phydev); } - if (phy_clear_interrupt(phydev)) + /* did_interrupt() may have cleared the interrupt already */ + if (!phydev->drv->did_interrupt && phy_clear_interrupt(phydev)) goto phy_err; return IRQ_HANDLED; diff --git a/include/linux/phy.h b/include/linux/phy.h index 3d5d53313e6c0..bf87c59a98bb3 100644 --- a/include/linux/phy.h +++ b/include/linux/phy.h @@ -524,6 +524,7 @@ struct phy_driver { /* * Checks if the PHY generated an interrupt. * For multi-PHY devices with shared PHY interrupt pin + * Set interrupt bits have to be cleared. */ int (*did_interrupt)(struct phy_device *phydev); -- 2.20.1
| |