From 027b90d5af1ea5c61de6825b6f037f9641e63a83 Mon Sep 17 00:00:00 2001 From: Vasanthakumar Thiagarajan Date: Tue, 4 Feb 2014 15:22:28 +0530 Subject: txrx: Fix invalid memory access during ll_pause buf flush Make sure to set adf_nbuf next to NULL before freeing the buffer using adf_nbuf_tx_free() to free only the buffer not the chain, the remaining buffers in the chain will be freed anyway in the while loop. This change fixes potential access to the freed buffer. Also make sure to unmap the DMA mapped buffer before free. Change-Id: Ib1efde5afcaf897f53d4fd8813874edc83f3a11f CRs-Fixed: 610802 --- CORE/CLD_TXRX/TXRX/ol_tx.c | 2 ++ CORE/CLD_TXRX/TXRX/ol_tx_queue.c | 3 +++ CORE/CLD_TXRX/TXRX/ol_txrx.c | 3 +++ 3 files changed, 8 insertions(+) diff --git a/CORE/CLD_TXRX/TXRX/ol_tx.c b/CORE/CLD_TXRX/TXRX/ol_tx.c index 4f8aee6f6b3c..5ca4117fb552 100644 --- a/CORE/CLD_TXRX/TXRX/ol_tx.c +++ b/CORE/CLD_TXRX/TXRX/ol_tx.c @@ -159,6 +159,7 @@ ol_tx_vdev_ll_pause_queue_send_base(struct ol_txrx_vdev_t *vdev) * For simplicity, just drop the frame. */ if (tx_msdu) { + adf_nbuf_unmap(vdev->pdev->osdev, tx_msdu, ADF_OS_DMA_TO_DEVICE); adf_nbuf_tx_free(tx_msdu, 1 /* error */); } } @@ -305,6 +306,7 @@ ol_tx_pdev_ll_pause_queue_send_all(struct ol_txrx_pdev_t *pdev) * For simplicity, just drop the frame. */ if (tx_msdu) { + adf_nbuf_unmap(pdev->osdev, tx_msdu, ADF_OS_DMA_TO_DEVICE); adf_nbuf_tx_free(tx_msdu, 1 /* error */); } } diff --git a/CORE/CLD_TXRX/TXRX/ol_tx_queue.c b/CORE/CLD_TXRX/TXRX/ol_tx_queue.c index eeb4cc31ca23..66358bcba544 100644 --- a/CORE/CLD_TXRX/TXRX/ol_tx_queue.c +++ b/CORE/CLD_TXRX/TXRX/ol_tx_queue.c @@ -538,6 +538,9 @@ ol_txrx_vdev_flush(ol_txrx_vdev_handle vdev) adf_os_timer_cancel(&vdev->ll_pause.timer); while (vdev->ll_pause.txq.head) { adf_nbuf_t next = adf_nbuf_next(vdev->ll_pause.txq.head); + adf_nbuf_set_next(vdev->ll_pause.txq.head, NULL); + adf_nbuf_unmap(vdev->pdev->osdev, vdev->ll_pause.txq.head, + ADF_OS_DMA_TO_DEVICE); adf_nbuf_tx_free(vdev->ll_pause.txq.head, 1 /* error */); vdev->ll_pause.txq.head = next; } diff --git a/CORE/CLD_TXRX/TXRX/ol_txrx.c b/CORE/CLD_TXRX/TXRX/ol_txrx.c index fc228bfe7ce5..0c83e5ce7355 100644 --- a/CORE/CLD_TXRX/TXRX/ol_txrx.c +++ b/CORE/CLD_TXRX/TXRX/ol_txrx.c @@ -932,6 +932,9 @@ ol_txrx_vdev_detach( adf_os_timer_free(&vdev->ll_pause.timer); while (vdev->ll_pause.txq.head) { adf_nbuf_t next = adf_nbuf_next(vdev->ll_pause.txq.head); + adf_nbuf_set_next(vdev->ll_pause.txq.head, NULL); + adf_nbuf_unmap(pdev->osdev, vdev->ll_pause.txq.head, + ADF_OS_DMA_TO_DEVICE); adf_nbuf_tx_free(vdev->ll_pause.txq.head, 1 /* error */); vdev->ll_pause.txq.head = next; } -- cgit v1.2.3