mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Sasha Levin <Alexander.Levin@microsoft.com>
To: "linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"stable@vger.kernel.org" <stable@vger.kernel.org>
Cc: Alexander Kochetkov <al.kochet@gmail.com>,
	"David S . Miller" <davem@davemloft.net>,
	Sasha Levin <Alexander.Levin@microsoft.com>
Subject: [PATCH AUTOSEL for 3.18 06/24] net: arc_emac: fix arc_emac_rx() error paths
Date: Sat, 3 Feb 2018 18:05:00 +0000	[thread overview]
Message-ID: <20180203180444.10801-6-alexander.levin@microsoft.com> (raw)
In-Reply-To: <20180203180444.10801-1-alexander.levin@microsoft.com>

From: Alexander Kochetkov <al.kochet@gmail.com>

[ Upstream commit e688822d035b494071ecbadcccbd6f3325fb0f59 ]

arc_emac_rx() has some issues found by code review.

In case netdev_alloc_skb_ip_align() or dma_map_single() failure
rx fifo entry will not be returned to EMAC.

In case dma_map_single() failure previously allocated skb became
lost to driver. At the same time address of newly allocated skb
will not be provided to EMAC.

Signed-off-by: Alexander Kochetkov <al.kochet@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Signed-off-by: Sasha Levin <alexander.levin@microsoft.com>
---
 drivers/net/ethernet/arc/emac_main.c | 53 +++++++++++++++++++++---------------
 1 file changed, 31 insertions(+), 22 deletions(-)

diff --git a/drivers/net/ethernet/arc/emac_main.c b/drivers/net/ethernet/arc/emac_main.c
index abe1eabc0171..9cc5daed13ed 100644
--- a/drivers/net/ethernet/arc/emac_main.c
+++ b/drivers/net/ethernet/arc/emac_main.c
@@ -250,39 +250,48 @@ static int arc_emac_rx(struct net_device *ndev, int budget)
 			continue;
 		}
 
-		pktlen = info & LEN_MASK;
-		stats->rx_packets++;
-		stats->rx_bytes += pktlen;
-		skb = rx_buff->skb;
-		skb_put(skb, pktlen);
-		skb->dev = ndev;
-		skb->protocol = eth_type_trans(skb, ndev);
-
-		dma_unmap_single(&ndev->dev, dma_unmap_addr(rx_buff, addr),
-				 dma_unmap_len(rx_buff, len), DMA_FROM_DEVICE);
-
-		/* Prepare the BD for next cycle */
-		rx_buff->skb = netdev_alloc_skb_ip_align(ndev,
-							 EMAC_BUFFER_SIZE);
-		if (unlikely(!rx_buff->skb)) {
+		/* Prepare the BD for next cycle. netif_receive_skb()
+		 * only if new skb was allocated and mapped to avoid holes
+		 * in the RX fifo.
+		 */
+		skb = netdev_alloc_skb_ip_align(ndev, EMAC_BUFFER_SIZE);
+		if (unlikely(!skb)) {
+			if (net_ratelimit())
+				netdev_err(ndev, "cannot allocate skb\n");
+			/* Return ownership to EMAC */
+			rxbd->info = cpu_to_le32(FOR_EMAC | EMAC_BUFFER_SIZE);
 			stats->rx_errors++;
-			/* Because receive_skb is below, increment rx_dropped */
 			stats->rx_dropped++;
 			continue;
 		}
 
-		/* receive_skb only if new skb was allocated to avoid holes */
-		netif_receive_skb(skb);
-
-		addr = dma_map_single(&ndev->dev, (void *)rx_buff->skb->data,
+		addr = dma_map_single(&ndev->dev, (void *)skb->data,
 				      EMAC_BUFFER_SIZE, DMA_FROM_DEVICE);
 		if (dma_mapping_error(&ndev->dev, addr)) {
 			if (net_ratelimit())
-				netdev_err(ndev, "cannot dma map\n");
-			dev_kfree_skb(rx_buff->skb);
+				netdev_err(ndev, "cannot map dma buffer\n");
+			dev_kfree_skb(skb);
+			/* Return ownership to EMAC */
+			rxbd->info = cpu_to_le32(FOR_EMAC | EMAC_BUFFER_SIZE);
 			stats->rx_errors++;
+			stats->rx_dropped++;
 			continue;
 		}
+
+		/* unmap previosly mapped skb */
+		dma_unmap_single(&ndev->dev, dma_unmap_addr(rx_buff, addr),
+				 dma_unmap_len(rx_buff, len), DMA_FROM_DEVICE);
+
+		pktlen = info & LEN_MASK;
+		stats->rx_packets++;
+		stats->rx_bytes += pktlen;
+		skb_put(rx_buff->skb, pktlen);
+		rx_buff->skb->dev = ndev;
+		rx_buff->skb->protocol = eth_type_trans(rx_buff->skb, ndev);
+
+		netif_receive_skb(rx_buff->skb);
+
+		rx_buff->skb = skb;
 		dma_unmap_addr_set(rx_buff, addr, addr);
 		dma_unmap_len_set(rx_buff, len, EMAC_BUFFER_SIZE);
 
-- 
2.11.0

  parent reply	other threads:[~2018-02-03 18:19 UTC|newest]

Thread overview: 24+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-02-03 18:04 [PATCH AUTOSEL for 3.18 01/24] mtd: nand: gpmi: Fix failure when a erased page has a bitflip at BBM Sasha Levin
2018-02-03 18:04 ` [PATCH AUTOSEL for 3.18 03/24] mm,vmscan: Make unregister_shrinker() no-op if register_shrinker() failed Sasha Levin
2018-02-03 18:04 ` [PATCH AUTOSEL for 3.18 02/24] ipv6: icmp6: Allow icmp messages to be looped back Sasha Levin
2018-02-03 18:04 ` [PATCH AUTOSEL for 3.18 04/24] sget(): handle failures of register_shrinker() Sasha Levin
2018-02-03 18:05 ` Sasha Levin [this message]
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 05/24] spi: atmel: fixed spin_lock usage inside atmel_spi_remove Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 07/24] scsi: storvsc: Fix scsi_cmd error assignments in storvsc_handle_error Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 09/24] tg3: Enable PHY reset in MTU change path for 5720 Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 08/24] tg3: Add workaround to restrict 5762 MRRS to 2048 Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 10/24] bnx2x: Improve reliability in case of nested PCI errors Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 12/24] s390/dasd: fix wrongly assigned configuration data Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 11/24] led: core: Fix brightness setting when setting delay_off=0 Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 14/24] xfs: quota: check result of register_shrinker() Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 13/24] xfs: quota: fix missed destroy of qi_tree_lock Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 16/24] drm/ttm: check the return value of kzalloc Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 15/24] e1000: fix disabling already-disabled warning Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 17/24] loop: fix concurrent lo_open/lo_release Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 18/24] xen-netfront: enable device after manual module load Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 19/24] mdio-sun4i: Fix a memory leak Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 21/24] xen/gntdev: Fix off-by-one error when unmapping with holes Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 20/24] SolutionEngine771x: fix Ether platform data Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 22/24] xen/gntdev: Fix partial gntdev_mmap() cleanup Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 23/24] sctp: make use of pre-calculated len Sasha Levin
2018-02-03 18:05 ` [PATCH AUTOSEL for 3.18 24/24] net: gianfar_ptp: move set_fipers() to spinlock protecting area Sasha Levin

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20180203180444.10801-6-alexander.levin@microsoft.com \
    --to=alexander.levin@microsoft.com \
    --cc=al.kochet@gmail.com \
    --cc=davem@davemloft.net \
    --cc=linux-kernel@vger.kernel.org \
    --cc=stable@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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®