From 2e1cd495466d14c7d92e10d709f27161afe44b15 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Mon, 8 Apr 2013 00:04:10 +0200 Subject: [PATCH] ath9k: improve dma map failure handling Instead of leaving the buffer without skb and breaking out of the loop (which could leak the rx buffer), use the common error path. Signed-off-by: Felix Fietkau Signed-off-by: John W. Linville --- drivers/net/wireless/ath/ath9k/recv.c | 30 ++++++++++++--------------- 1 file changed, 13 insertions(+), 17 deletions(-) diff --git a/drivers/net/wireless/ath/ath9k/recv.c b/drivers/net/wireless/ath/ath9k/recv.c index d7c06af1778d..3d0f02ddcf5b 100644 --- a/drivers/net/wireless/ath/ath9k/recv.c +++ b/drivers/net/wireless/ath/ath9k/recv.c @@ -1166,6 +1166,7 @@ int ath_rx_tasklet(struct ath_softc *sc, int flush, bool hp) u64 tsf = 0; u32 tsf_lower = 0; unsigned long flags; + dma_addr_t new_buf_addr; if (edma) dma_type = DMA_BIDIRECTIONAL; @@ -1264,10 +1265,20 @@ int ath_rx_tasklet(struct ath_softc *sc, int flush, bool hp) goto requeue_drop_frag; } + /* We will now give hardware our shiny new allocated skb */ + new_buf_addr = dma_map_single(sc->dev, requeue_skb->data, + common->rx_bufsize, dma_type); + if (unlikely(dma_mapping_error(sc->dev, new_buf_addr))) { + dev_kfree_skb_any(requeue_skb); + goto requeue_drop_frag; + } + + bf->bf_mpdu = requeue_skb; + bf->bf_buf_addr = new_buf_addr; + /* Unmap the frame */ dma_unmap_single(sc->dev, bf->bf_buf_addr, - common->rx_bufsize, - dma_type); + common->rx_bufsize, dma_type); skb_put(skb, rs.rs_datalen + ah->caps.rx_status_len); if (ah->caps.rx_status_len) @@ -1277,21 +1288,6 @@ int ath_rx_tasklet(struct ath_softc *sc, int flush, bool hp) ath9k_rx_skb_postprocess(common, hdr_skb, &rs, rxs, decrypt_error); - /* We will now give hardware our shiny new allocated skb */ - bf->bf_mpdu = requeue_skb; - bf->bf_buf_addr = dma_map_single(sc->dev, requeue_skb->data, - common->rx_bufsize, - dma_type); - if (unlikely(dma_mapping_error(sc->dev, - bf->bf_buf_addr))) { - dev_kfree_skb_any(requeue_skb); - bf->bf_mpdu = NULL; - bf->bf_buf_addr = 0; - ath_err(common, "dma_mapping_error() on RX\n"); - ieee80211_rx(hw, skb); - break; - } - if (rs.rs_more) { RX_STAT_INC(rx_frags); /* -- 2.20.1