On Sat 1 Feb 2025, 10:03 Ariel Otilibili, wrote: > Both legs of the loop share the same logic: the common parts are about > reserving and filling both address and length into the description. > > This is moved into reserve_and_fill(). > > Bugzilla ID: 1440 > Suggested-by: Maryam Tahhan > Signed-off-by: Ariel Otilibili > --- > drivers/net/af_xdp/rte_eth_af_xdp.c | 62 ++++++++++++++++------------- > 1 file changed, 34 insertions(+), 28 deletions(-) > > diff --git a/drivers/net/af_xdp/rte_eth_af_xdp.c > b/drivers/net/af_xdp/rte_eth_af_xdp.c > index 092bcb73aa0a..840a12dbf508 100644 > --- a/drivers/net/af_xdp/rte_eth_af_xdp.c > +++ b/drivers/net/af_xdp/rte_eth_af_xdp.c > @@ -536,6 +536,31 @@ kick_tx(struct pkt_tx_queue *txq, struct > xsk_ring_cons *cq) > } > } > > +static inline struct xdp_desc * > +reserve_and_fill(struct pkt_tx_queue *txq, struct rte_mbuf *mbuf, > + struct xsk_umem_info *umem) > +{ > + struct xdp_desc *desc = NULL; > + uint32_t *idx_tx = NULL; > + uint64_t addr, offset; > + > + if (!xsk_ring_prod__reserve(&txq->tx, 1, idx_tx)) > + goto out; > + > + desc = xsk_ring_prod__tx_desc(&txq->tx, *idx_tx); > + desc->len = mbuf->pkt_len; > + > + addr = (uint64_t)mbuf - (uint64_t)umem->buffer > + - umem->mb_pool->header_size; > + offset = rte_pktmbuf_mtod(mbuf, uint64_t) - (uint64_t)mbuf > + + umem->mb_pool->header_size; > + offset = offset << XSK_UNALIGNED_BUF_OFFSET_SHIFT; > + desc->addr = addr | offset; > + > +out: > + return desc; > +} > + > #if defined(XDP_UMEM_UNALIGNED_CHUNK_FLAG) > static uint16_t > af_xdp_tx_zc(void *queue, struct rte_mbuf **bufs, uint16_t nb_pkts) > @@ -545,10 +570,8 @@ af_xdp_tx_zc(void *queue, struct rte_mbuf **bufs, > uint16_t nb_pkts) > struct rte_mbuf *mbuf; > unsigned long tx_bytes = 0; > int i; > - uint32_t idx_tx; > uint16_t count = 0; > struct xdp_desc *desc; > - uint64_t addr, offset; > struct xsk_ring_cons *cq = &txq->pair->cq; > uint32_t free_thresh = cq->size >> 1; > > @@ -559,21 +582,12 @@ af_xdp_tx_zc(void *queue, struct rte_mbuf **bufs, > uint16_t nb_pkts) > mbuf = bufs[i]; > > if (mbuf->pool == umem->mb_pool) { > - if (!xsk_ring_prod__reserve(&txq->tx, 1, &idx_tx)) > { > + if (!(desc = reserve_and_fill(txq, mbuf, umem))) { > kick_tx(txq, cq); > - if (!xsk_ring_prod__reserve(&txq->tx, 1, > - &idx_tx)) > + if (!(desc = reserve_and_fill(txq, mbuf, > umem))) > goto out; > } > - desc = xsk_ring_prod__tx_desc(&txq->tx, idx_tx); > - desc->len = mbuf->pkt_len; > - addr = (uint64_t)mbuf - (uint64_t)umem->buffer - > - umem->mb_pool->header_size; > - offset = rte_pktmbuf_mtod(mbuf, uint64_t) - > - (uint64_t)mbuf + > - umem->mb_pool->header_size; > - offset = offset << XSK_UNALIGNED_BUF_OFFSET_SHIFT; > - desc->addr = addr | offset; > + > tx_bytes += desc->len; > count++; > } else { > @@ -584,26 +598,18 @@ af_xdp_tx_zc(void *queue, struct rte_mbuf **bufs, > uint16_t nb_pkts) > if (local_mbuf == NULL) > goto out; > > - if (!xsk_ring_prod__reserve(&txq->tx, 1, &idx_tx)) > { > + if (!(desc = reserve_and_fill(txq, local_mbuf, > umem))) { > rte_pktmbuf_free(local_mbuf); > goto out; > } > > - desc = xsk_ring_prod__tx_desc(&txq->tx, idx_tx); > - desc->len = mbuf->pkt_len; > - > So I think i spotted one issue, you might need override desc->len after the call to the reserve_and_fill function so as it's not taken supposed to be from local_mbuf here. - addr = (uint64_t)local_mbuf - > (uint64_t)umem->buffer - > - umem->mb_pool->header_size; > - offset = rte_pktmbuf_mtod(local_mbuf, uint64_t) - > - (uint64_t)local_mbuf + > - umem->mb_pool->header_size; > - pkt = xsk_umem__get_data(umem->buffer, addr + > offset); > - offset = offset << XSK_UNALIGNED_BUF_OFFSET_SHIFT; > - desc->addr = addr | offset; > + pkt = xsk_umem__get_data(umem->buffer, > + (desc->addr & ~0xFFF) > + + (desc->addr & 0xFFF)); > Would prefer to move this pkt assignment to reserve_and_fill() What if we passed a void **ppkt to reserve_and_fill() then kept the original logic just wrapped in a NULL check? if (ppkt) { *ppkt = xsk_umem__get_data(umem->buffer, addr + offset); } Before the offset and desc->addr offset = offset << XSK_UNALIGNED_BUF_OFFSET_SHIFT; desc->addr = addr | offset; WDYT? rte_memcpy(pkt, rte_pktmbuf_mtod(mbuf, void *), > - desc->len); > - tx_bytes += desc->len; > + desc->len); > rte_pktmbuf_free(mbuf); > + tx_bytes += desc->len; > count++; > } > } > -- > 2.30.2 > >