b.liu | e958203 | 2025-04-17 19:18:16 +0800 | [diff] [blame] | 1 | From ca6be00ca1d3a2f5b8794894e2dae175e63768f5 Mon Sep 17 00:00:00 2001 |
| 2 | From: Sieng Piaw Liew <liew.s.piaw@gmail.com> |
| 3 | Date: Tue, 16 Feb 2021 16:23:08 +0800 |
| 4 | Subject: [PATCH] bcm63xx_enet: Fix sporadic kernel panic |
| 5 | |
| 6 | In ndo_stop functions, netdev_completed_queue() is called during forced |
| 7 | tx reclaim, after netdev_reset_queue(). This may trigger kernel panic if |
| 8 | there is any tx skb left. |
| 9 | |
| 10 | This patch moves netdev_reset_queue() to after tx reclaim, so BQL can |
| 11 | complete successfully then reset. |
| 12 | |
| 13 | Signed-off-by: Sieng Piaw Liew <liew.s.piaw@gmail.com> |
| 14 | --- |
| 15 | drivers/net/ethernet/broadcom/bcm63xx_enet.c | 8 ++++++-- |
| 16 | 1 file changed, 6 insertions(+), 2 deletions(-) |
| 17 | |
| 18 | --- a/drivers/net/ethernet/broadcom/bcm63xx_enet.c |
| 19 | +++ b/drivers/net/ethernet/broadcom/bcm63xx_enet.c |
| 20 | @@ -1193,7 +1193,6 @@ static int bcm_enet_stop(struct net_devi |
| 21 | kdev = &priv->pdev->dev; |
| 22 | |
| 23 | netif_stop_queue(dev); |
| 24 | - netdev_reset_queue(dev); |
| 25 | napi_disable(&priv->napi); |
| 26 | if (priv->has_phy) |
| 27 | phy_stop(dev->phydev); |
| 28 | @@ -1232,6 +1231,9 @@ static int bcm_enet_stop(struct net_devi |
| 29 | if (priv->has_phy) |
| 30 | phy_disconnect(dev->phydev); |
| 31 | |
| 32 | + /* reset BQL after forced tx reclaim to not kernel panic */ |
| 33 | + netdev_reset_queue(dev); |
| 34 | + |
| 35 | return 0; |
| 36 | } |
| 37 | |
| 38 | @@ -2348,7 +2350,6 @@ static int bcm_enetsw_stop(struct net_de |
| 39 | |
| 40 | del_timer_sync(&priv->swphy_poll); |
| 41 | netif_stop_queue(dev); |
| 42 | - netdev_reset_queue(dev); |
| 43 | napi_disable(&priv->napi); |
| 44 | del_timer_sync(&priv->rx_timeout); |
| 45 | |
| 46 | @@ -2376,6 +2377,9 @@ static int bcm_enetsw_stop(struct net_de |
| 47 | free_irq(priv->irq_tx, dev); |
| 48 | free_irq(priv->irq_rx, dev); |
| 49 | |
| 50 | + /* reset BQL after forced tx reclaim to not kernel panic */ |
| 51 | + netdev_reset_queue(dev); |
| 52 | + |
| 53 | return 0; |
| 54 | } |
| 55 | |