Hi all, The rte_pktmbuf_free() function could be optimized by freeing multiple segments in bulk using rte_mempool_put_bulk().
I got this idea while optimizing the rte_pktmbuf_free_bulk() function similarly, as suggested by Stephen Hemminger and Konstantin Ananyev. If any of you DPDK performance freaks want to test this concept, here's some source code to get you started. /** * @internal Size of the array holding mbufs from the same membool to be freed * in bulk. */ #define RTE_PKTMBUF_FREE_BULK_SZ 64 /** * @internal helper function for freeing a bulk of mbufs via an array holding * mbufs from the same mempool. */ static __rte_always_inline void rte_pktmbuf_free_seg_via_array(struct rte_mbuf *m, struct rte_mbuf * * const free, unsigned int * const nb_free) { m = rte_pktmbuf_prefree_seg(m); if (likely(m != NULL)) { if (*nb_free >= RTE_PKTMBUF_FREE_BULK_SZ || (*nb_free > 0 && m->pool != free[0]->pool)) { rte_mempool_put_bulk(free[0]->pool, (void **)free, *nb_free); *nb_free = 0; } free[(*nb_free)++] = m; } } /** * Free a packet mbuf back into its original mempool. * * Free an mbuf, and all its segments in case of chained buffers. Each * segment is added back into its original mempool. * * @param m * The packet mbuf to be freed. If NULL, the function does nothing. */ static inline void rte_pktmbuf_free(struct rte_mbuf *m) { struct rte_mbuf *m_next, *free[RTE_PKTMBUF_FREE_BULK_SZ]; unsigned int nb_free = 0; if (unlikely(m == NULL)) return; __rte_mbuf_sanity_check(m, 1); do { m_next = m->next; rte_pktmbuf_free_seg_via_array(m, free, &nb_free); m = m_next; } while (m != NULL); if (nb_free > 0) rte_mempool_put_bulk(free[0]->pool, (void **)free, nb_free); } Med venlig hilsen / kind regards Morten Brørup CTO SmartShare Systems A/S Tonsbakken 16-18 DK-2740 Skovlunde Denmark Office +45 70 20 00 93 Direct +45 89 93 50 22 Mobile +45 25 40 82 12 m...@smartsharesystems.com www.smartsharesystems.com