Add support to the ice driver for the API rte_eth_tx_done_cleanup
 to force free consumed buffers on Tx ring.

Signed-off-by: Di ChenxuX <chenxux...@intel.com>
---
 drivers/net/ice/ice_ethdev.c |  1 +
 drivers/net/ice/ice_rxtx.c   | 41 ++++++++++++++++++++++++++++++++++++
 drivers/net/ice/ice_rxtx.h   |  1 +
 3 files changed, 43 insertions(+)

diff --git a/drivers/net/ice/ice_ethdev.c b/drivers/net/ice/ice_ethdev.c
index 63997fdfb..617f7b2ac 100644
--- a/drivers/net/ice/ice_ethdev.c
+++ b/drivers/net/ice/ice_ethdev.c
@@ -160,6 +160,7 @@ static const struct eth_dev_ops ice_eth_dev_ops = {
        .filter_ctrl                  = ice_dev_filter_ctrl,
        .udp_tunnel_port_add          = ice_dev_udp_tunnel_port_add,
        .udp_tunnel_port_del          = ice_dev_udp_tunnel_port_del,
+       .tx_done_cleanup              = ice_tx_done_cleanup,
 };
 
 /* store statistics names and its offset in stats structure */
diff --git a/drivers/net/ice/ice_rxtx.c b/drivers/net/ice/ice_rxtx.c
index 81af81441..f991cb6c0 100644
--- a/drivers/net/ice/ice_rxtx.c
+++ b/drivers/net/ice/ice_rxtx.c
@@ -579,6 +579,47 @@ ice_tx_queue_stop(struct rte_eth_dev *dev, uint16_t 
tx_queue_id)
        return 0;
 }
 
+
+int ice_tx_done_cleanup(void *txq, uint32_t free_cnt)
+{
+       struct ice_tx_queue *q = (struct ice_tx_queue *)txq;
+       struct ice_tx_entry *sw_ring;
+       uint16_t tx_id;    /* Current segment being processed. */
+       uint16_t tx_cleaned;
+
+       int count = 0;
+
+       if (q == NULL)
+               return -ENODEV;
+
+       sw_ring = q->sw_ring;
+       tx_cleaned = q->last_desc_cleaned;
+       tx_id = sw_ring[q->last_desc_cleaned].next_id;
+       if ((q->tx_ring[tx_id].cmd_type_offset_bsz &
+                       rte_cpu_to_le_64(ICE_TXD_QW1_DTYPE_M)) !=
+                       rte_cpu_to_le_64(ICE_TX_DESC_DTYPE_DESC_DONE))
+               return 0;
+
+       do {
+               if (sw_ring[tx_id].mbuf == NULL)
+                       break;
+
+               rte_pktmbuf_free_seg(sw_ring[tx_id].mbuf);
+               sw_ring[tx_id].mbuf = NULL;
+               sw_ring[tx_id].last_id = tx_id;
+
+               /* Move to next segemnt. */
+               tx_cleaned = tx_id;
+               tx_id = sw_ring[tx_id].next_id;
+               count++;
+       } while (count != (int)free_cnt);
+
+       q->nb_tx_free += (uint16_t)count;
+       q->last_desc_cleaned = tx_cleaned;
+
+       return count;
+}
+
 int
 ice_rx_queue_setup(struct rte_eth_dev *dev,
                   uint16_t queue_idx,
diff --git a/drivers/net/ice/ice_rxtx.h b/drivers/net/ice/ice_rxtx.h
index e9214110c..1ac3f3f91 100644
--- a/drivers/net/ice/ice_rxtx.h
+++ b/drivers/net/ice/ice_rxtx.h
@@ -170,6 +170,7 @@ int ice_rx_descriptor_status(void *rx_queue, uint16_t 
offset);
 int ice_tx_descriptor_status(void *tx_queue, uint16_t offset);
 void ice_set_default_ptype_table(struct rte_eth_dev *dev);
 const uint32_t *ice_dev_supported_ptypes_get(struct rte_eth_dev *dev);
+int ice_tx_done_cleanup(void *txq, uint32_t free_cnt);
 
 int ice_rx_vec_dev_check(struct rte_eth_dev *dev);
 int ice_tx_vec_dev_check(struct rte_eth_dev *dev);
-- 
2.17.1

Reply via email to