aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBen Hutchings <ben.hutchings@codethink.co.uk>2015-01-22 07:41:34 -0500
committerDavid S. Miller <davem@davemloft.net>2015-01-26 19:13:15 -0500
commit084236d8c53952f14b5cb1741311c80c7fbe8289 (patch)
tree358670a294b84b7523197607bca7efd27f73bc76
parentbd8889163a7f392f89de5bb01ad00f5772c7ea25 (diff)
sh_eth: Fix crash or memory leak when resizing rings on device that is down
If the device is down then no packet buffers should be allocated. We also must not touch its registers as it may be powered off. Signed-off-by: Ben Hutchings <ben.hutchings@codethink.co.uk> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--drivers/net/ethernet/renesas/sh_eth.c34
1 files changed, 18 insertions, 16 deletions
diff --git a/drivers/net/ethernet/renesas/sh_eth.c b/drivers/net/ethernet/renesas/sh_eth.c
index fa8a7b775b4a..7facda1328f8 100644
--- a/drivers/net/ethernet/renesas/sh_eth.c
+++ b/drivers/net/ethernet/renesas/sh_eth.c
@@ -1976,29 +1976,31 @@ static int sh_eth_set_ringparam(struct net_device *ndev,
1976 sh_eth_write(ndev, 0, EDTRR); 1976 sh_eth_write(ndev, 0, EDTRR);
1977 sh_eth_write(ndev, 0, EDRRR); 1977 sh_eth_write(ndev, 0, EDRRR);
1978 synchronize_irq(ndev->irq); 1978 synchronize_irq(ndev->irq);
1979 }
1980 1979
1981 /* Free all the skbuffs in the Rx queue. */ 1980 /* Free all the skbuffs in the Rx queue. */
1982 sh_eth_ring_free(ndev); 1981 sh_eth_ring_free(ndev);
1983 /* Free DMA buffer */ 1982 /* Free DMA buffer */
1984 sh_eth_free_dma_buffer(mdp); 1983 sh_eth_free_dma_buffer(mdp);
1984 }
1985 1985
1986 /* Set new parameters */ 1986 /* Set new parameters */
1987 mdp->num_rx_ring = ring->rx_pending; 1987 mdp->num_rx_ring = ring->rx_pending;
1988 mdp->num_tx_ring = ring->tx_pending; 1988 mdp->num_tx_ring = ring->tx_pending;
1989 1989
1990 ret = sh_eth_ring_init(ndev);
1991 if (ret < 0) {
1992 netdev_err(ndev, "%s: sh_eth_ring_init failed.\n", __func__);
1993 return ret;
1994 }
1995 ret = sh_eth_dev_init(ndev, false);
1996 if (ret < 0) {
1997 netdev_err(ndev, "%s: sh_eth_dev_init failed.\n", __func__);
1998 return ret;
1999 }
2000
2001 if (netif_running(ndev)) { 1990 if (netif_running(ndev)) {
1991 ret = sh_eth_ring_init(ndev);
1992 if (ret < 0) {
1993 netdev_err(ndev, "%s: sh_eth_ring_init failed.\n",
1994 __func__);
1995 return ret;
1996 }
1997 ret = sh_eth_dev_init(ndev, false);
1998 if (ret < 0) {
1999 netdev_err(ndev, "%s: sh_eth_dev_init failed.\n",
2000 __func__);
2001 return ret;
2002 }
2003
2002 sh_eth_write(ndev, mdp->cd->eesipr_value, EESIPR); 2004 sh_eth_write(ndev, mdp->cd->eesipr_value, EESIPR);
2003 /* Setting the Rx mode will start the Rx process. */ 2005 /* Setting the Rx mode will start the Rx process. */
2004 sh_eth_write(ndev, EDRRR_R, EDRRR); 2006 sh_eth_write(ndev, EDRRR_R, EDRRR);