From eee607b51a871cd5e0e8ce80e3514a012817f57b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mika=20Lepp=C3=A4nen?= Date: Fri, 1 Jun 2018 12:10:47 +0300 Subject: [PATCH] Corrected TX buffer reclaim error When all TX descriptors were reserved in a row so that TX buffer reclaim interrupt did not happen during reservation sequence, after the interrupt occurred, TX buffer reclaim did no longer free buffers. This happened because when all descriptors were in use, last free index pointed to consumed index. --- .../TARGET_NXP_EMAC/TARGET_LPCTarget/lpc17_emac.cpp | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/features/netsocket/emac-drivers/TARGET_NXP_EMAC/TARGET_LPCTarget/lpc17_emac.cpp b/features/netsocket/emac-drivers/TARGET_NXP_EMAC/TARGET_LPCTarget/lpc17_emac.cpp index 3c6e0e28cf..26391558c1 100644 --- a/features/netsocket/emac-drivers/TARGET_NXP_EMAC/TARGET_LPCTarget/lpc17_emac.cpp +++ b/features/netsocket/emac-drivers/TARGET_NXP_EMAC/TARGET_LPCTarget/lpc17_emac.cpp @@ -116,6 +116,7 @@ struct lpc_enetdata { volatile uint32_t rx_free_descs; /**< Count of free RX descriptors */ emac_mem_buf_t *txb[LPC_NUM_BUFF_TXDESCS]; /**< TX pbuf pointer list, zero-copy mode */ uint32_t lpc_last_tx_idx; /**< TX last descriptor index, zero-copy mode */ + uint32_t lpc_reserved_tx_num; /**< Number of reserved TX descriptors, zero-copy mode */ }; #if defined(TARGET_LPC1768) || defined(TARGET_LPC1769) @@ -419,6 +420,7 @@ bool LPC17_EMAC::lpc_tx_setup() LPC_EMAC->TxDescriptorNumber = LPC_NUM_BUFF_TXDESCS - 1; lpc_enetdata.lpc_last_tx_idx = 0; + lpc_enetdata.lpc_reserved_tx_num = 0; return true; } @@ -431,7 +433,8 @@ void LPC17_EMAC::lpc_tx_reclaim_st(uint32_t cidx) { TXLockMutex.lock(); - while (cidx != lpc_enetdata.lpc_last_tx_idx) { + // If consume index not last freed index or all descriptors in use + while (cidx != lpc_enetdata.lpc_last_tx_idx || lpc_enetdata.lpc_reserved_tx_num == LPC_NUM_BUFF_TXDESCS) { if (lpc_enetdata.txb[lpc_enetdata.lpc_last_tx_idx] != NULL) { memory_manager->free(lpc_enetdata.txb[lpc_enetdata.lpc_last_tx_idx]); lpc_enetdata.txb[lpc_enetdata.lpc_last_tx_idx] = NULL; @@ -443,6 +446,7 @@ void LPC17_EMAC::lpc_tx_reclaim_st(uint32_t cidx) if (lpc_enetdata.lpc_last_tx_idx >= LPC_NUM_BUFF_TXDESCS) { lpc_enetdata.lpc_last_tx_idx = 0; } + lpc_enetdata.lpc_reserved_tx_num--; } TXLockMutex.unlock(); @@ -573,6 +577,7 @@ bool LPC17_EMAC::link_out(emac_mem_buf_t *p) if (idx >= LPC_NUM_BUFF_TXDESCS) { idx = 0; } + lpc_enetdata.lpc_reserved_tx_num++; } LPC_EMAC->TxProduceIndex = idx;