diff options
author | Ricardo Ribalda <ricardo.ribalda@gmail.com> | 2011-11-07 23:31:58 +0000 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2011-11-09 15:37:38 -0500 |
commit | 50ec1538fac0e39078d45ca5f8a5186621830058 (patch) | |
tree | 0cf86765fed469bbfd5be682321cf5a895b1ae30 /drivers/net/ethernet/xilinx/ll_temac_main.c | |
parent | 2bc8ca40f951163b3bb75949479e2755c12c1b96 (diff) | |
download | linux-stable-50ec1538fac0e39078d45ca5f8a5186621830058.tar.gz linux-stable-50ec1538fac0e39078d45ca5f8a5186621830058.tar.bz2 linux-stable-50ec1538fac0e39078d45ca5f8a5186621830058.zip |
net/temac: FIX segfault when process old irqs
Do not enable the irq until the scatter gather registers are ready to
handle the data. Otherwise an irq from a packet send/received before
last close can lead to an access to an invalid memory region on the irq
handler.
Also, stop the dma engine on close.
Signed-off-by: Ricardo Ribalda Delgado <ricardo.ribalda@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/xilinx/ll_temac_main.c')
-rw-r--r-- | drivers/net/ethernet/xilinx/ll_temac_main.c | 6 |
1 files changed, 5 insertions, 1 deletions
diff --git a/drivers/net/ethernet/xilinx/ll_temac_main.c b/drivers/net/ethernet/xilinx/ll_temac_main.c index caf3659e173c..05a1ffad20d2 100644 --- a/drivers/net/ethernet/xilinx/ll_temac_main.c +++ b/drivers/net/ethernet/xilinx/ll_temac_main.c @@ -203,6 +203,9 @@ static void temac_dma_bd_release(struct net_device *ndev) struct temac_local *lp = netdev_priv(ndev); int i; + /* Reset Local Link (DMA) */ + lp->dma_out(lp, DMA_CONTROL_REG, DMA_CONTROL_RST); + for (i = 0; i < RX_BD_NUM; i++) { if (!lp->rx_skb[i]) break; @@ -860,6 +863,8 @@ static int temac_open(struct net_device *ndev) phy_start(lp->phy_dev); } + temac_device_reset(ndev); + rc = request_irq(lp->tx_irq, ll_temac_tx_irq, 0, ndev->name, ndev); if (rc) goto err_tx_irq; @@ -867,7 +872,6 @@ static int temac_open(struct net_device *ndev) if (rc) goto err_rx_irq; - temac_device_reset(ndev); return 0; err_rx_irq: |