DPDK v16.07 introduces the ability to free memzones. Up until this point, DPDK memory pools created in OVS could not be destroyed, thus incurring a memory leak.
Leverage the DPDK v16.07 rte_mempool API to free DPDK mempools when their associated reference count reaches 0 (this indicates that the memory pool is no longer in use). Until DPDK v16.07 is supported, this patch may be considered RFC. Signed-off-by: Mark Kavanagh <mark.b.kavan...@intel.com> --- lib/netdev-dpdk.c | 29 ++++++++++++++--------------- 1 file changed, 14 insertions(+), 15 deletions(-) diff --git a/lib/netdev-dpdk.c b/lib/netdev-dpdk.c index dfb26d4..b9027a7 100644 --- a/lib/netdev-dpdk.c +++ b/lib/netdev-dpdk.c @@ -505,7 +505,7 @@ dpdk_mp_get(int socket_id, int mtu) OVS_REQUIRES(dpdk_mutex) } static void -dpdk_mp_put(struct dpdk_mp *dmp) +dpdk_mp_put(struct dpdk_mp *dmp) OVS_REQUIRES(dpdk_mutex) { if (!dmp) { @@ -513,15 +513,11 @@ dpdk_mp_put(struct dpdk_mp *dmp) } dmp->refcount--; - ovs_assert(dmp->refcount >= 0); -#if 0 - /* I could not find any API to destroy mp. */ - if (dmp->refcount == 0) { - list_delete(dmp->list_node); - /* destroy mp-pool. */ + if (OVS_UNLIKELY(!dmp->refcount)) { + ovs_list_remove(&dmp->list_node); + rte_mempool_free(dmp->mp); } -#endif } static void @@ -909,16 +905,17 @@ netdev_dpdk_destruct(struct netdev *netdev) { struct netdev_dpdk *dev = netdev_dpdk_cast(netdev); + ovs_mutex_lock(&dpdk_mutex); ovs_mutex_lock(&dev->mutex); + rte_eth_dev_stop(dev->port_id); free(ovsrcu_get_protected(struct ingress_policer *, &dev->ingress_policer)); - ovs_mutex_unlock(&dev->mutex); - - ovs_mutex_lock(&dpdk_mutex); rte_free(dev->tx_q); ovs_list_remove(&dev->list_node); dpdk_mp_put(dev->dpdk_mp); + + ovs_mutex_unlock(&dev->mutex); ovs_mutex_unlock(&dpdk_mutex); } @@ -933,6 +930,9 @@ netdev_dpdk_vhost_destruct(struct netdev *netdev) { struct netdev_dpdk *dev = netdev_dpdk_cast(netdev); + ovs_mutex_lock(&dpdk_mutex); + ovs_mutex_lock(&dev->mutex); + /* Guest becomes an orphan if still attached. */ if (is_vhost_running(dev->vid)) { VLOG_ERR("Removing port '%s' while vhost device still attached.", @@ -948,15 +948,13 @@ netdev_dpdk_vhost_destruct(struct netdev *netdev) fatal_signal_remove_file_to_unlink(dev->vhost_id); } - ovs_mutex_lock(&dev->mutex); free(ovsrcu_get_protected(struct ingress_policer *, &dev->ingress_policer)); - ovs_mutex_unlock(&dev->mutex); - - ovs_mutex_lock(&dpdk_mutex); rte_free(dev->tx_q); ovs_list_remove(&dev->list_node); dpdk_mp_put(dev->dpdk_mp); + + ovs_mutex_unlock(&dev->mutex); ovs_mutex_unlock(&dpdk_mutex); } @@ -1614,6 +1612,7 @@ netdev_dpdk_set_mtu(const struct netdev *netdev, int mtu) ovs_mutex_lock(&dpdk_mutex); ovs_mutex_lock(&dev->mutex); + if (dev->mtu == mtu) { err = 0; goto out; -- 1.9.3 _______________________________________________ dev mailing list dev@openvswitch.org http://openvswitch.org/mailman/listinfo/dev