get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

GET /api/patches/47065/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 47065,
    "url": "http://patches.dpdk.org/api/patches/47065/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/20181019020757.27698-5-thomas@monjalon.net/",
    "project": {
        "id": 1,
        "url": "http://patches.dpdk.org/api/projects/1/?format=api",
        "name": "DPDK",
        "link_name": "dpdk",
        "list_id": "dev.dpdk.org",
        "list_email": "dev@dpdk.org",
        "web_url": "http://core.dpdk.org",
        "scm_url": "git://dpdk.org/dpdk",
        "webscm_url": "http://git.dpdk.org/dpdk",
        "list_archive_url": "https://inbox.dpdk.org/dev",
        "list_archive_url_format": "https://inbox.dpdk.org/dev/{}",
        "commit_url_format": ""
    },
    "msgid": "<20181019020757.27698-5-thomas@monjalon.net>",
    "list_archive_url": "https://inbox.dpdk.org/dev/20181019020757.27698-5-thomas@monjalon.net",
    "date": "2018-10-19T02:07:55",
    "name": "[v6,4/6] ethdev: free all common data when releasing port",
    "commit_ref": null,
    "pull_url": null,
    "state": "accepted",
    "archived": true,
    "hash": "cf84f139bc1b3af0bf063a186adce0168362a53d",
    "submitter": {
        "id": 685,
        "url": "http://patches.dpdk.org/api/people/685/?format=api",
        "name": "Thomas Monjalon",
        "email": "thomas@monjalon.net"
    },
    "delegate": {
        "id": 319,
        "url": "http://patches.dpdk.org/api/users/319/?format=api",
        "username": "fyigit",
        "first_name": "Ferruh",
        "last_name": "Yigit",
        "email": "ferruh.yigit@amd.com"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/20181019020757.27698-5-thomas@monjalon.net/mbox/",
    "series": [
        {
            "id": 1984,
            "url": "http://patches.dpdk.org/api/series/1984/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=1984",
            "date": "2018-10-19T02:07:51",
            "name": "ethdev port freeing",
            "version": 6,
            "mbox": "http://patches.dpdk.org/series/1984/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/47065/comments/",
    "check": "success",
    "checks": "http://patches.dpdk.org/api/patches/47065/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<dev-bounces@dpdk.org>",
        "X-Original-To": "patchwork@dpdk.org",
        "Delivered-To": "patchwork@dpdk.org",
        "Received": [
            "from [92.243.14.124] (localhost [127.0.0.1])\n\tby dpdk.org (Postfix) with ESMTP id E94751B153;\n\tFri, 19 Oct 2018 04:08:12 +0200 (CEST)",
            "from out3-smtp.messagingengine.com (out3-smtp.messagingengine.com\n\t[66.111.4.27]) by dpdk.org (Postfix) with ESMTP id C2E221B120\n\tfor <dev@dpdk.org>; Fri, 19 Oct 2018 04:08:05 +0200 (CEST)",
            "from compute1.internal (compute1.nyi.internal [10.202.2.41])\n\tby mailout.nyi.internal (Postfix) with ESMTP id 694AC22986;\n\tThu, 18 Oct 2018 22:08:05 -0400 (EDT)",
            "from mailfrontend2 ([10.202.2.163])\n\tby compute1.internal (MEProxy); Thu, 18 Oct 2018 22:08:05 -0400",
            "from xps.monjalon.net (184.203.134.77.rev.sfr.net [77.134.203.184])\n\tby mail.messagingengine.com (Postfix) with ESMTPA id 0A13C102DD;\n\tThu, 18 Oct 2018 22:08:03 -0400 (EDT)"
        ],
        "DKIM-Signature": [
            "v=1; a=rsa-sha256; c=relaxed/relaxed; d=monjalon.net; h=\n\tfrom:to:cc:subject:date:message-id:in-reply-to:references\n\t:mime-version:content-transfer-encoding; s=mesmtp; bh=ut4lSRJIKG\n\tl/BwjnhCjm5kpirPJvCgrHBBR9w9tWd24=; b=KdAmeuDu5RfTIR4Cs0ztxYDtyP\n\t5AozuXyTHQvBzZvEDnEN2qaDL0cSFNtPliI4DbW/KRSAELCimWN63NZ2v7oD1h9/\n\tOH02TY+o7seorpcpPUqrWmA5pDyKpmPh6rCPox9d4T7vxlsp0EFBoTbLTVhfCV2V\n\tosU81U60IVl67vGfQ=",
            "v=1; a=rsa-sha256; c=relaxed/relaxed; d=\n\tmessagingengine.com; h=cc:content-transfer-encoding:date:from\n\t:in-reply-to:message-id:mime-version:references:subject:to\n\t:x-me-proxy:x-me-proxy:x-me-sender:x-me-sender:x-sasl-enc; s=\n\tfm1; bh=ut4lSRJIKGl/BwjnhCjm5kpirPJvCgrHBBR9w9tWd24=; b=q9/dttex\n\tNznbVSy6km+GJHBZaKOfGNI1yDi/+VfVkh/o6soXCBLJMnWY5XAG+/m+5mVKldHi\n\tLsfmb6IWrvuqNZrtIxZ+5yVK9nYL1hdGg0bUQpMT19i1EBl/e+Tdoiqt/ooVncRp\n\tMImY8ZEYxmAOUm5qOVQZMLllCPl/yFtXSg/4jKQHq9zsMAF1n3pUuq4OuAuNPS4k\n\t1gPPwvnRn+M4JXvdcJbODfSBxU9yHnzQOIcPSLvYYStlOt/gZ0pyZk78ud/RU6nR\n\tqTuXTwfP2Ws3nFYq1blYePg5hp4gOsHrAAlKyGbrn5AH/XXOyaxbj+wcnz1Vr+Ar\n\tQiE1ykTQ7PNxRg=="
        ],
        "X-ME-Sender": "<xms:hTzJW2KNXKIm--n_IvgvOAOW9OvgU_IJs3BmLW87D_HcCzc4rgsc2A>",
        "X-ME-Proxy": "<xmx:hTzJWw0FZsbqMl_npYAuC1EEKIocIqotgxdYxIuol7Ev59CWqAdYmw>\n\t<xmx:hTzJW-X7oDwSYi1Jjzo71GTvbxlc3udYa23-4_K-NWx28a7o-i9nWQ>\n\t<xmx:hTzJW89qhkk9Bd-ToltkpljamtMX_GF7yY2nw8EnL9mAqbSmJTKIZQ>\n\t<xmx:hTzJWz2vkNObyqzaDI2njd3fFwUF9DIE3JDZYxA45IJheacd63oVgQ>\n\t<xmx:hTzJW3B9xX5Bcjhio3Iwjho72wBHmhS2u7KGhA6Lj8uWbb6po72MhA>\n\t<xmx:hTzJW10l8GLrwePj2_JVeW5HbV2Qh0gd6PExRVw0u-Luq9ADpEWQvA>",
        "From": "Thomas Monjalon <thomas@monjalon.net>",
        "To": "ferruh.yigit@intel.com,\n\tarybchenko@solarflare.com",
        "Cc": "dev@dpdk.org, ophirmu@mellanox.com, bernard.iremonger@intel.com,\n\trahul.lakkireddy@chelsio.com",
        "Date": "Fri, 19 Oct 2018 04:07:55 +0200",
        "Message-Id": "<20181019020757.27698-5-thomas@monjalon.net>",
        "X-Mailer": "git-send-email 2.19.0",
        "In-Reply-To": "<20181019020757.27698-1-thomas@monjalon.net>",
        "References": "<20180907233929.21950-1-thomas@monjalon.net>\n\t<20181019020757.27698-1-thomas@monjalon.net>",
        "MIME-Version": "1.0",
        "Content-Transfer-Encoding": "8bit",
        "Subject": "[dpdk-dev] [PATCH v6 4/6] ethdev: free all common data when\n\treleasing port",
        "X-BeenThere": "dev@dpdk.org",
        "X-Mailman-Version": "2.1.15",
        "Precedence": "list",
        "List-Id": "DPDK patches and discussions <dev.dpdk.org>",
        "List-Unsubscribe": "<https://mails.dpdk.org/options/dev>,\n\t<mailto:dev-request@dpdk.org?subject=unsubscribe>",
        "List-Archive": "<http://mails.dpdk.org/archives/dev/>",
        "List-Post": "<mailto:dev@dpdk.org>",
        "List-Help": "<mailto:dev-request@dpdk.org?subject=help>",
        "List-Subscribe": "<https://mails.dpdk.org/listinfo/dev>,\n\t<mailto:dev-request@dpdk.org?subject=subscribe>",
        "Errors-To": "dev-bounces@dpdk.org",
        "Sender": "\"dev\" <dev-bounces@dpdk.org>"
    },
    "content": "This is a clean-up of common ethdev data freeing.\nAll data freeing are moved to rte_eth_dev_release_port()\nand done only in case of primary process.\n\nIt is probably fixing some memory leaks for PMDs which were\nnot freeing all data.\n\nSigned-off-by: Thomas Monjalon <thomas@monjalon.net>\nAcked-by: Andrew Rybchenko <arybchenko@solarflare.com>\n---\n drivers/net/af_packet/rte_eth_af_packet.c |  5 ++--\n drivers/net/ark/ark_ethdev.c              |  1 -\n drivers/net/avf/avf_ethdev.c              |  3 ---\n drivers/net/avp/avp_ethdev.c              |  5 ----\n drivers/net/axgbe/axgbe_ethdev.c          |  3 ---\n drivers/net/bnxt/bnxt_ethdev.c            |  4 ----\n drivers/net/bonding/rte_eth_bond_pmd.c    |  9 +++----\n drivers/net/cxgbe/cxgbe_main.c            | 16 ++-----------\n drivers/net/cxgbe/cxgbevf_main.c          |  9 +------\n drivers/net/dpaa/dpaa_ethdev.c            | 10 --------\n drivers/net/dpaa2/dpaa2_ethdev.c          | 10 --------\n drivers/net/e1000/em_ethdev.c             |  3 ---\n drivers/net/e1000/igb_ethdev.c            |  6 -----\n drivers/net/enetc/enetc_ethdev.c          |  4 +---\n drivers/net/failsafe/failsafe.c           |  6 +++--\n drivers/net/fm10k/fm10k_ethdev.c          |  8 -------\n drivers/net/i40e/i40e_ethdev.c            |  3 ---\n drivers/net/i40e/i40e_ethdev_vf.c         |  3 ---\n drivers/net/i40e/i40e_vf_representor.c    |  5 +++-\n drivers/net/ixgbe/ixgbe_ethdev.c          |  9 -------\n drivers/net/ixgbe/ixgbe_vf_representor.c  |  5 +++-\n drivers/net/kni/rte_eth_kni.c             |  5 ++--\n drivers/net/liquidio/lio_ethdev.c         |  3 ---\n drivers/net/mlx4/mlx4.c                   |  7 +++++-\n drivers/net/mlx5/mlx5.c                   | 11 ++++++---\n drivers/net/mvneta/mvneta_ethdev.c        | 16 ++++---------\n drivers/net/mvpp2/mrvl_ethdev.c           | 16 ++++---------\n drivers/net/netvsc/hn_ethdev.c            | 15 ++----------\n drivers/net/null/rte_eth_null.c           |  4 ++--\n drivers/net/octeontx/octeontx_ethdev.c    | 29 +++++++++--------------\n drivers/net/pcap/rte_eth_pcap.c           |  8 +++----\n drivers/net/qede/qede_ethdev.c            |  5 ----\n drivers/net/ring/rte_eth_ring.c           |  6 ++---\n drivers/net/sfc/sfc_ethdev.c              |  3 ---\n drivers/net/softnic/rte_eth_softnic.c     |  7 +++---\n drivers/net/szedata2/rte_eth_szedata2.c   |  1 -\n drivers/net/tap/rte_eth_tap.c             |  6 ++++-\n drivers/net/vhost/rte_eth_vhost.c         |  9 +++----\n drivers/net/virtio/virtio_ethdev.c        |  3 ---\n drivers/net/virtio/virtio_user_ethdev.c   |  3 ---\n drivers/net/vmxnet3/vmxnet3_ethdev.c      |  3 ---\n lib/librte_ethdev/rte_ethdev.c            | 21 ++++++++--------\n lib/librte_ethdev/rte_ethdev_core.h       | 14 ++++++++---\n lib/librte_ethdev/rte_ethdev_driver.h     |  9 ++++++-\n lib/librte_ethdev/rte_ethdev_pci.h        | 10 --------\n 45 files changed, 109 insertions(+), 232 deletions(-)",
    "diff": "diff --git a/drivers/net/af_packet/rte_eth_af_packet.c b/drivers/net/af_packet/rte_eth_af_packet.c\nindex 376d76302..2efc17725 100644\n--- a/drivers/net/af_packet/rte_eth_af_packet.c\n+++ b/drivers/net/af_packet/rte_eth_af_packet.c\n@@ -986,6 +986,9 @@ rte_pmd_af_packet_remove(struct rte_vdev_device *dev)\n \tif (eth_dev == NULL)\n \t\treturn -1;\n \n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n+\n \tif (rte_eal_process_type() != RTE_PROC_PRIMARY)\n \t\treturn rte_eth_dev_release_port_secondary(eth_dev);\n \n@@ -996,8 +999,6 @@ rte_pmd_af_packet_remove(struct rte_vdev_device *dev)\n \t}\n \tfree(internals->if_name);\n \n-\trte_free(eth_dev->data->dev_private);\n-\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/ark/ark_ethdev.c b/drivers/net/ark/ark_ethdev.c\nindex 552ca01a6..70d62ec7f 100644\n--- a/drivers/net/ark/ark_ethdev.c\n+++ b/drivers/net/ark/ark_ethdev.c\n@@ -506,7 +506,6 @@ eth_ark_dev_uninit(struct rte_eth_dev *dev)\n \tdev->dev_ops = NULL;\n \tdev->rx_pkt_burst = NULL;\n \tdev->tx_pkt_burst = NULL;\n-\trte_free(dev->data->mac_addrs);\n \treturn 0;\n }\n \ndiff --git a/drivers/net/avf/avf_ethdev.c b/drivers/net/avf/avf_ethdev.c\nindex e56d57c43..13eec1b45 100644\n--- a/drivers/net/avf/avf_ethdev.c\n+++ b/drivers/net/avf/avf_ethdev.c\n@@ -1303,9 +1303,6 @@ avf_dev_uninit(struct rte_eth_dev *dev)\n \trte_free(vf->aq_resp);\n \tvf->aq_resp = NULL;\n \n-\trte_free(dev->data->mac_addrs);\n-\tdev->data->mac_addrs = NULL;\n-\n \tif (vf->rss_lut) {\n \t\trte_free(vf->rss_lut);\n \t\tvf->rss_lut = NULL;\ndiff --git a/drivers/net/avp/avp_ethdev.c b/drivers/net/avp/avp_ethdev.c\nindex 0f8ccb954..09388d05f 100644\n--- a/drivers/net/avp/avp_ethdev.c\n+++ b/drivers/net/avp/avp_ethdev.c\n@@ -1036,11 +1036,6 @@ eth_avp_dev_uninit(struct rte_eth_dev *eth_dev)\n \t\treturn ret;\n \t}\n \n-\tif (eth_dev->data->mac_addrs != NULL) {\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\teth_dev->data->mac_addrs = NULL;\n-\t}\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/axgbe/axgbe_ethdev.c b/drivers/net/axgbe/axgbe_ethdev.c\nindex 4b84b50c0..e89c0ec2c 100644\n--- a/drivers/net/axgbe/axgbe_ethdev.c\n+++ b/drivers/net/axgbe/axgbe_ethdev.c\n@@ -718,9 +718,6 @@ eth_axgbe_dev_uninit(struct rte_eth_dev *eth_dev)\n \t\treturn 0;\n \n \tpci_dev = RTE_DEV_TO_PCI(eth_dev->device);\n-\t/*Free macaddres*/\n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n \teth_dev->dev_ops = NULL;\n \teth_dev->rx_pkt_burst = NULL;\n \teth_dev->tx_pkt_burst = NULL;\ndiff --git a/drivers/net/bnxt/bnxt_ethdev.c b/drivers/net/bnxt/bnxt_ethdev.c\nindex c11fe9c8c..801c6ffad 100644\n--- a/drivers/net/bnxt/bnxt_ethdev.c\n+++ b/drivers/net/bnxt/bnxt_ethdev.c\n@@ -3501,10 +3501,6 @@ bnxt_dev_uninit(struct rte_eth_dev *eth_dev)\n \tbnxt_disable_int(bp);\n \tbnxt_free_int(bp);\n \tbnxt_free_mem(bp);\n-\tif (eth_dev->data->mac_addrs != NULL) {\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\teth_dev->data->mac_addrs = NULL;\n-\t}\n \tif (bp->grp_info != NULL) {\n \t\trte_free(bp->grp_info);\n \t\tbp->grp_info = NULL;\ndiff --git a/drivers/net/bonding/rte_eth_bond_pmd.c b/drivers/net/bonding/rte_eth_bond_pmd.c\nindex b731132a5..77fb3dcd3 100644\n--- a/drivers/net/bonding/rte_eth_bond_pmd.c\n+++ b/drivers/net/bonding/rte_eth_bond_pmd.c\n@@ -3128,10 +3128,9 @@ bond_alloc(struct rte_vdev_device *dev, uint8_t mode)\n \n err:\n \trte_free(internals);\n-\tif (eth_dev != NULL) {\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\trte_eth_dev_release_port(eth_dev);\n-\t}\n+\tif (eth_dev != NULL)\n+\t\teth_dev->data->dev_private = NULL;\n+\trte_eth_dev_release_port(eth_dev);\n \treturn -1;\n }\n \n@@ -3292,8 +3291,6 @@ bond_remove(struct rte_vdev_device *dev)\n \trte_mempool_free(internals->mode6.mempool);\n \trte_bitmap_free(internals->vlan_filter_bmp);\n \trte_free(internals->vlan_filter_bmpmem);\n-\trte_free(eth_dev->data->dev_private);\n-\trte_free(eth_dev->data->mac_addrs);\n \n \trte_eth_dev_release_port(eth_dev);\n \ndiff --git a/drivers/net/cxgbe/cxgbe_main.c b/drivers/net/cxgbe/cxgbe_main.c\nindex a135df9c7..88dc851f8 100644\n--- a/drivers/net/cxgbe/cxgbe_main.c\n+++ b/drivers/net/cxgbe/cxgbe_main.c\n@@ -1710,12 +1710,7 @@ void cxgbe_close(struct adapter *adapter)\n \t\t\tif (pi->viid != 0)\n \t\t\t\tt4_free_vi(adapter, adapter->mbox,\n \t\t\t\t\t   adapter->pf, 0, pi->viid);\n-\t\t\trte_free(pi->eth_dev->data->mac_addrs);\n-\t\t\t/* Skip first port since it'll be freed by DPDK stack */\n-\t\t\tif (i) {\n-\t\t\t\trte_free(pi->eth_dev->data->dev_private);\n-\t\t\t\trte_eth_dev_release_port(pi->eth_dev);\n-\t\t\t}\n+\t\t\trte_eth_dev_release_port(pi->eth_dev);\n \t\t}\n \t\tadapter->flags &= ~FULL_INIT_DONE;\n \t}\n@@ -1918,14 +1913,7 @@ int cxgbe_probe(struct adapter *adapter)\n \t\tif (pi->viid != 0)\n \t\t\tt4_free_vi(adapter, adapter->mbox, adapter->pf,\n \t\t\t\t   0, pi->viid);\n-\t\t/* Skip first port since it'll be de-allocated by DPDK */\n-\t\tif (i == 0)\n-\t\t\tcontinue;\n-\t\tif (pi->eth_dev) {\n-\t\t\tif (pi->eth_dev->data->dev_private)\n-\t\t\t\trte_free(pi->eth_dev->data->dev_private);\n-\t\t\trte_eth_dev_release_port(pi->eth_dev);\n-\t\t}\n+\t\trte_eth_dev_release_port(pi->eth_dev);\n \t}\n \n \tif (adapter->flags & FW_OK)\ndiff --git a/drivers/net/cxgbe/cxgbevf_main.c b/drivers/net/cxgbe/cxgbevf_main.c\nindex 4214d0312..6223e1250 100644\n--- a/drivers/net/cxgbe/cxgbevf_main.c\n+++ b/drivers/net/cxgbe/cxgbevf_main.c\n@@ -282,14 +282,7 @@ int cxgbevf_probe(struct adapter *adapter)\n \t\tif (pi->viid != 0)\n \t\t\tt4_free_vi(adapter, adapter->mbox, adapter->pf,\n \t\t\t\t   0, pi->viid);\n-\t\t/* Skip first port since it'll be de-allocated by DPDK */\n-\t\tif (i == 0)\n-\t\t\tcontinue;\n-\t\tif (pi->eth_dev) {\n-\t\t\tif (pi->eth_dev->data->dev_private)\n-\t\t\t\trte_free(pi->eth_dev->data->dev_private);\n-\t\t\trte_eth_dev_release_port(pi->eth_dev);\n-\t\t}\n+\t\trte_eth_dev_release_port(pi->eth_dev);\n \t}\n \treturn -err;\n }\ndiff --git a/drivers/net/dpaa/dpaa_ethdev.c b/drivers/net/dpaa/dpaa_ethdev.c\nindex 5c743c3c8..d0572b3d9 100644\n--- a/drivers/net/dpaa/dpaa_ethdev.c\n+++ b/drivers/net/dpaa/dpaa_ethdev.c\n@@ -1439,10 +1439,6 @@ dpaa_dev_uninit(struct rte_eth_dev *dev)\n \trte_free(dpaa_intf->tx_queues);\n \tdpaa_intf->tx_queues = NULL;\n \n-\t/* free memory for storing MAC addresses */\n-\trte_free(dev->data->mac_addrs);\n-\tdev->data->mac_addrs = NULL;\n-\n \tdev->dev_ops = NULL;\n \tdev->rx_pkt_burst = NULL;\n \tdev->tx_pkt_burst = NULL;\n@@ -1544,9 +1540,6 @@ rte_dpaa_probe(struct rte_dpaa_driver *dpaa_drv __rte_unused,\n \t\treturn 0;\n \t}\n \n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(eth_dev->data->dev_private);\n-\n \trte_eth_dev_release_port(eth_dev);\n \treturn diag;\n }\n@@ -1561,9 +1554,6 @@ rte_dpaa_remove(struct rte_dpaa_device *dpaa_dev)\n \teth_dev = dpaa_dev->eth_dev;\n \tdpaa_dev_uninit(eth_dev);\n \n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(eth_dev->data->dev_private);\n-\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/dpaa2/dpaa2_ethdev.c b/drivers/net/dpaa2/dpaa2_ethdev.c\nindex 3987d13df..8267ee3f0 100644\n--- a/drivers/net/dpaa2/dpaa2_ethdev.c\n+++ b/drivers/net/dpaa2/dpaa2_ethdev.c\n@@ -2065,12 +2065,6 @@ dpaa2_dev_uninit(struct rte_eth_dev *eth_dev)\n \n \tdpaa2_free_rx_tx_queues(eth_dev);\n \n-\t/* free memory for storing MAC addresses */\n-\tif (eth_dev->data->mac_addrs) {\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\teth_dev->data->mac_addrs = NULL;\n-\t}\n-\n \t/* Close the device at underlying layer*/\n \tret = dpni_close(dpni, CMD_PRI_LOW, priv->token);\n \tif (ret) {\n@@ -2133,8 +2127,6 @@ rte_dpaa2_probe(struct rte_dpaa2_driver *dpaa2_drv,\n \t\treturn 0;\n \t}\n \n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(eth_dev->data->dev_private);\n \trte_eth_dev_release_port(eth_dev);\n \treturn diag;\n }\n@@ -2147,8 +2139,6 @@ rte_dpaa2_remove(struct rte_dpaa2_device *dpaa2_dev)\n \teth_dev = dpaa2_dev->eth_dev;\n \tdpaa2_dev_uninit(eth_dev);\n \n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(eth_dev->data->dev_private);\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/e1000/em_ethdev.c b/drivers/net/e1000/em_ethdev.c\nindex 28c153512..8230824e7 100644\n--- a/drivers/net/e1000/em_ethdev.c\n+++ b/drivers/net/e1000/em_ethdev.c\n@@ -329,9 +329,6 @@ eth_em_dev_uninit(struct rte_eth_dev *eth_dev)\n \teth_dev->rx_pkt_burst = NULL;\n \teth_dev->tx_pkt_burst = NULL;\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \t/* disable uio intr before callback unregister */\n \trte_intr_disable(intr_handle);\n \trte_intr_callback_unregister(intr_handle,\ndiff --git a/drivers/net/e1000/igb_ethdev.c b/drivers/net/e1000/igb_ethdev.c\nindex e542ef572..d9d29d22f 100644\n--- a/drivers/net/e1000/igb_ethdev.c\n+++ b/drivers/net/e1000/igb_ethdev.c\n@@ -917,9 +917,6 @@ eth_igb_dev_uninit(struct rte_eth_dev *eth_dev)\n \t/* Reset any pending lock */\n \tigb_reset_swfw_lock(hw);\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \t/* uninitialize PF if max_vfs not zero */\n \tigb_pf_host_uninit(eth_dev);\n \n@@ -1073,9 +1070,6 @@ eth_igbvf_dev_uninit(struct rte_eth_dev *eth_dev)\n \teth_dev->rx_pkt_burst = NULL;\n \teth_dev->tx_pkt_burst = NULL;\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \t/* disable uio intr before callback unregister */\n \trte_intr_disable(&pci_dev->intr_handle);\n \trte_intr_callback_unregister(&pci_dev->intr_handle,\ndiff --git a/drivers/net/enetc/enetc_ethdev.c b/drivers/net/enetc/enetc_ethdev.c\nindex 3ee7bb446..023fe7517 100644\n--- a/drivers/net/enetc/enetc_ethdev.c\n+++ b/drivers/net/enetc/enetc_ethdev.c\n@@ -108,11 +108,9 @@ enetc_dev_init(struct rte_eth_dev *eth_dev)\n }\n \n static int\n-enetc_dev_uninit(struct rte_eth_dev *eth_dev)\n+enetc_dev_uninit(struct rte_eth_dev *eth_dev __rte_unused)\n {\n \tPMD_INIT_FUNC_TRACE();\n-\trte_free(eth_dev->data->mac_addrs);\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/failsafe/failsafe.c b/drivers/net/failsafe/failsafe.c\nindex c3999f026..fed36da5f 100644\n--- a/drivers/net/failsafe/failsafe.c\n+++ b/drivers/net/failsafe/failsafe.c\n@@ -280,7 +280,8 @@ fs_eth_dev_create(struct rte_vdev_device *vdev)\n free_subs:\n \tfs_sub_device_free(dev);\n free_dev:\n-\trte_free(PRIV(dev));\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\tdev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(dev);\n \treturn -1;\n }\n@@ -305,7 +306,8 @@ fs_rte_eth_free(const char *name)\n \tif (ret)\n \t\tERROR(\"Error while destroying hotplug mutex\");\n \trte_free(PRIV(dev)->mcast_addrs);\n-\trte_free(PRIV(dev));\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\tdev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(dev);\n \treturn ret;\n }\ndiff --git a/drivers/net/fm10k/fm10k_ethdev.c b/drivers/net/fm10k/fm10k_ethdev.c\nindex 46983e5df..bb7b906a9 100644\n--- a/drivers/net/fm10k/fm10k_ethdev.c\n+++ b/drivers/net/fm10k/fm10k_ethdev.c\n@@ -3234,14 +3234,6 @@ eth_fm10k_dev_uninit(struct rte_eth_dev *dev)\n \t\t\tfm10k_dev_interrupt_handler_vf, (void *)dev);\n \t}\n \n-\t/* free mac memory */\n-\tif (dev->data->mac_addrs) {\n-\t\trte_free(dev->data->mac_addrs);\n-\t\tdev->data->mac_addrs = NULL;\n-\t}\n-\n-\tmemset(hw, 0, sizeof(*hw));\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/i40e/i40e_ethdev.c b/drivers/net/i40e/i40e_ethdev.c\nindex f7a685c8c..8a5c3c8fb 100644\n--- a/drivers/net/i40e/i40e_ethdev.c\n+++ b/drivers/net/i40e/i40e_ethdev.c\n@@ -1728,9 +1728,6 @@ eth_i40e_dev_uninit(struct rte_eth_dev *dev)\n \t/* uninitialize pf host driver */\n \ti40e_pf_host_uninit(dev);\n \n-\trte_free(dev->data->mac_addrs);\n-\tdev->data->mac_addrs = NULL;\n-\n \t/* disable uio intr before callback unregister */\n \trte_intr_disable(intr_handle);\n \ndiff --git a/drivers/net/i40e/i40e_ethdev_vf.c b/drivers/net/i40e/i40e_ethdev_vf.c\nindex baa6cc58f..ed2fc1310 100644\n--- a/drivers/net/i40e/i40e_ethdev_vf.c\n+++ b/drivers/net/i40e/i40e_ethdev_vf.c\n@@ -1483,9 +1483,6 @@ i40evf_dev_uninit(struct rte_eth_dev *eth_dev)\n \t\treturn -1;\n \t}\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/i40e/i40e_vf_representor.c b/drivers/net/i40e/i40e_vf_representor.c\nindex 24751d13c..43fe00cca 100644\n--- a/drivers/net/i40e/i40e_vf_representor.c\n+++ b/drivers/net/i40e/i40e_vf_representor.c\n@@ -523,7 +523,10 @@ i40e_vf_representor_init(struct rte_eth_dev *ethdev, void *init_params)\n }\n \n int\n-i40e_vf_representor_uninit(struct rte_eth_dev *ethdev __rte_unused)\n+i40e_vf_representor_uninit(struct rte_eth_dev *ethdev)\n {\n+\t/* mac_addrs must not be freed because part of i40e_pf_vf */\n+\tethdev->data->mac_addrs = NULL;\n+\n \treturn 0;\n }\ndiff --git a/drivers/net/ixgbe/ixgbe_ethdev.c b/drivers/net/ixgbe/ixgbe_ethdev.c\nindex c458bffc0..269595b73 100644\n--- a/drivers/net/ixgbe/ixgbe_ethdev.c\n+++ b/drivers/net/ixgbe/ixgbe_ethdev.c\n@@ -1337,12 +1337,6 @@ eth_ixgbe_dev_uninit(struct rte_eth_dev *eth_dev)\n \t/* uninitialize PF if max_vfs not zero */\n \tixgbe_pf_host_uninit(eth_dev);\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n-\trte_free(eth_dev->data->hash_mac_addrs);\n-\teth_dev->data->hash_mac_addrs = NULL;\n-\n \t/* remove all the fdir filters & hash */\n \tixgbe_fdir_filter_uninit(eth_dev);\n \n@@ -1722,9 +1716,6 @@ eth_ixgbevf_dev_uninit(struct rte_eth_dev *eth_dev)\n \t/* Disable the interrupts for VF */\n \tixgbevf_intr_disable(eth_dev);\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \trte_intr_disable(intr_handle);\n \trte_intr_callback_unregister(intr_handle,\n \t\t\t\t     ixgbevf_dev_interrupt_handler, eth_dev);\ndiff --git a/drivers/net/ixgbe/ixgbe_vf_representor.c b/drivers/net/ixgbe/ixgbe_vf_representor.c\nindex b0fbbc49f..eb9bbe5cb 100644\n--- a/drivers/net/ixgbe/ixgbe_vf_representor.c\n+++ b/drivers/net/ixgbe/ixgbe_vf_representor.c\n@@ -225,7 +225,10 @@ ixgbe_vf_representor_init(struct rte_eth_dev *ethdev, void *init_params)\n }\n \n int\n-ixgbe_vf_representor_uninit(struct rte_eth_dev *ethdev __rte_unused)\n+ixgbe_vf_representor_uninit(struct rte_eth_dev *ethdev)\n {\n+\t/* mac_addrs must not be freed because part of ixgbe_vf_info */\n+\tethdev->data->mac_addrs = NULL;\n+\n \treturn 0;\n }\ndiff --git a/drivers/net/kni/rte_eth_kni.c b/drivers/net/kni/rte_eth_kni.c\nindex 72f3c16c1..f43ee7d2e 100644\n--- a/drivers/net/kni/rte_eth_kni.c\n+++ b/drivers/net/kni/rte_eth_kni.c\n@@ -463,6 +463,9 @@ eth_kni_remove(struct rte_vdev_device *vdev)\n \tif (eth_dev == NULL)\n \t\treturn -1;\n \n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n+\n \tif (rte_eal_process_type() != RTE_PROC_PRIMARY)\n \t\treturn rte_eth_dev_release_port_secondary(eth_dev);\n \n@@ -471,8 +474,6 @@ eth_kni_remove(struct rte_vdev_device *vdev)\n \tinternals = eth_dev->data->dev_private;\n \trte_kni_release(internals->kni);\n \n-\trte_free(internals);\n-\n \trte_eth_dev_release_port(eth_dev);\n \n \tis_kni_initialized--;\ndiff --git a/drivers/net/liquidio/lio_ethdev.c b/drivers/net/liquidio/lio_ethdev.c\nindex 0f59e4475..d13ab06c0 100644\n--- a/drivers/net/liquidio/lio_ethdev.c\n+++ b/drivers/net/liquidio/lio_ethdev.c\n@@ -2043,9 +2043,6 @@ lio_eth_dev_uninit(struct rte_eth_dev *eth_dev)\n \t/* lio_free_sc_buffer_pool */\n \tlio_free_sc_buffer_pool(lio_dev);\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \teth_dev->dev_ops = NULL;\n \teth_dev->rx_pkt_burst = NULL;\n \teth_dev->tx_pkt_burst = NULL;\ndiff --git a/drivers/net/mlx4/mlx4.c b/drivers/net/mlx4/mlx4.c\nindex 3de7bc53e..7f07b8dc0 100644\n--- a/drivers/net/mlx4/mlx4.c\n+++ b/drivers/net/mlx4/mlx4.c\n@@ -781,12 +781,17 @@ mlx4_pci_probe(struct rte_pci_driver *pci_drv, struct rte_pci_device *pci_dev)\n \t\tcontinue;\n port_error:\n \t\trte_free(priv);\n+\t\tif (eth_dev != NULL)\n+\t\t\teth_dev->data->dev_private = NULL;\n \t\tif (pd)\n \t\t\tclaim_zero(mlx4_glue->dealloc_pd(pd));\n \t\tif (ctx)\n \t\t\tclaim_zero(mlx4_glue->close_device(ctx));\n-\t\tif (eth_dev)\n+\t\tif (eth_dev != NULL) {\n+\t\t\t/* mac_addrs must not be freed because part of dev_private */\n+\t\t\teth_dev->data->mac_addrs = NULL;\n \t\t\trte_eth_dev_release_port(eth_dev);\n+\t\t}\n \t\tbreak;\n \t}\n \t/*\ndiff --git a/drivers/net/mlx5/mlx5.c b/drivers/net/mlx5/mlx5.c\nindex 8cbfee1ba..b2be74b51 100644\n--- a/drivers/net/mlx5/mlx5.c\n+++ b/drivers/net/mlx5/mlx5.c\n@@ -1223,11 +1223,16 @@ mlx5_dev_spawn(struct rte_device *dpdk_dev,\n \t\tif (own_domain_id)\n \t\t\tclaim_zero(rte_eth_switch_domain_free(priv->domain_id));\n \t\trte_free(priv);\n+\t\tif (eth_dev != NULL)\n+\t\t\teth_dev->data->dev_private = NULL;\n \t}\n \tif (pd)\n \t\tclaim_zero(mlx5_glue->dealloc_pd(pd));\n-\tif (eth_dev)\n+\tif (eth_dev != NULL) {\n+\t\t/* mac_addrs must not be freed alone because part of dev_private */\n+\t\teth_dev->data->mac_addrs = NULL;\n \t\trte_eth_dev_release_port(eth_dev);\n+\t}\n \tif (ctx)\n \t\tclaim_zero(mlx5_glue->close_device(ctx));\n \tassert(err > 0);\n@@ -1447,8 +1452,8 @@ mlx5_pci_probe(struct rte_pci_driver *pci_drv __rte_unused,\n \t\t\tif (!list[i].eth_dev)\n \t\t\t\tcontinue;\n \t\t\tmlx5_dev_close(list[i].eth_dev);\n-\t\t\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\t\t\trte_free(list[i].eth_dev->data->dev_private);\n+\t\t\t/* mac_addrs must not be freed because in dev_private */\n+\t\t\tlist[i].eth_dev->data->mac_addrs = NULL;\n \t\t\tclaim_zero(rte_eth_dev_release_port(list[i].eth_dev));\n \t\t}\n \t\t/* Restore original error. */\ndiff --git a/drivers/net/mvneta/mvneta_ethdev.c b/drivers/net/mvneta/mvneta_ethdev.c\nindex f7071bc2e..2d7666454 100644\n--- a/drivers/net/mvneta/mvneta_ethdev.c\n+++ b/drivers/net/mvneta/mvneta_ethdev.c\n@@ -787,8 +787,9 @@ mvneta_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \tpriv = rte_zmalloc_socket(name, sizeof(*priv), 0, rte_socket_id());\n \tif (!priv) {\n \t\tret = -ENOMEM;\n-\t\tgoto out_free_dev;\n+\t\tgoto out_free;\n \t}\n+\teth_dev->data->dev_private = priv;\n \n \teth_dev->data->mac_addrs =\n \t\trte_zmalloc(\"mac_addrs\",\n@@ -796,20 +797,19 @@ mvneta_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \tif (!eth_dev->data->mac_addrs) {\n \t\tMVNETA_LOG(ERR, \"Failed to allocate space for eth addrs\");\n \t\tret = -ENOMEM;\n-\t\tgoto out_free_priv;\n+\t\tgoto out_free;\n \t}\n \n \tmemset(&req, 0, sizeof(req));\n \tstrcpy(req.ifr_name, name);\n \tret = ioctl(fd, SIOCGIFHWADDR, &req);\n \tif (ret)\n-\t\tgoto out_free_mac;\n+\t\tgoto out_free;\n \n \tmemcpy(eth_dev->data->mac_addrs[0].addr_bytes,\n \t       req.ifr_addr.sa_data, ETHER_ADDR_LEN);\n \n \teth_dev->data->kdrv = RTE_KDRV_NONE;\n-\teth_dev->data->dev_private = priv;\n \teth_dev->device = &vdev->device;\n \teth_dev->rx_pkt_burst = mvneta_rx_pkt_burst;\n \tmvneta_set_tx_function(eth_dev);\n@@ -817,11 +817,7 @@ mvneta_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \n \trte_eth_dev_probing_finish(eth_dev);\n \treturn 0;\n-out_free_mac:\n-\trte_free(eth_dev->data->mac_addrs);\n-out_free_priv:\n-\trte_free(priv);\n-out_free_dev:\n+out_free:\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn ret;\n@@ -836,8 +832,6 @@ mvneta_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n static void\n mvneta_eth_dev_destroy(struct rte_eth_dev *eth_dev)\n {\n-\trte_free(eth_dev->data->dev_private);\n-\trte_free(eth_dev->data->mac_addrs);\n \trte_eth_dev_release_port(eth_dev);\n }\n \ndiff --git a/drivers/net/mvpp2/mrvl_ethdev.c b/drivers/net/mvpp2/mrvl_ethdev.c\nindex 0682c635a..ab4c14e51 100644\n--- a/drivers/net/mvpp2/mrvl_ethdev.c\n+++ b/drivers/net/mvpp2/mrvl_ethdev.c\n@@ -2780,8 +2780,9 @@ mrvl_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \tpriv = mrvl_priv_create(name);\n \tif (!priv) {\n \t\tret = -ENOMEM;\n-\t\tgoto out_free_dev;\n+\t\tgoto out_free;\n \t}\n+\teth_dev->data->dev_private = priv;\n \n \teth_dev->data->mac_addrs =\n \t\trte_zmalloc(\"mac_addrs\",\n@@ -2789,20 +2790,19 @@ mrvl_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \tif (!eth_dev->data->mac_addrs) {\n \t\tMRVL_LOG(ERR, \"Failed to allocate space for eth addrs\");\n \t\tret = -ENOMEM;\n-\t\tgoto out_free_priv;\n+\t\tgoto out_free;\n \t}\n \n \tmemset(&req, 0, sizeof(req));\n \tstrcpy(req.ifr_name, name);\n \tret = ioctl(fd, SIOCGIFHWADDR, &req);\n \tif (ret)\n-\t\tgoto out_free_mac;\n+\t\tgoto out_free;\n \n \tmemcpy(eth_dev->data->mac_addrs[0].addr_bytes,\n \t       req.ifr_addr.sa_data, ETHER_ADDR_LEN);\n \n \teth_dev->data->kdrv = RTE_KDRV_NONE;\n-\teth_dev->data->dev_private = priv;\n \teth_dev->device = &vdev->device;\n \teth_dev->rx_pkt_burst = mrvl_rx_pkt_burst;\n \tmrvl_set_tx_function(eth_dev);\n@@ -2810,12 +2810,8 @@ mrvl_eth_dev_create(struct rte_vdev_device *vdev, const char *name)\n \n \trte_eth_dev_probing_finish(eth_dev);\n \treturn 0;\n-out_free_mac:\n-\trte_free(eth_dev->data->mac_addrs);\n-out_free_dev:\n+out_free:\n \trte_eth_dev_release_port(eth_dev);\n-out_free_priv:\n-\trte_free(priv);\n \n \treturn ret;\n }\n@@ -2839,8 +2835,6 @@ mrvl_eth_dev_destroy(const char *name)\n \tpriv = eth_dev->data->dev_private;\n \tpp2_bpool_deinit(priv->bpool);\n \tused_bpools[priv->pp_id] &= ~(1 << priv->bpool_bit);\n-\trte_free(priv);\n-\trte_free(eth_dev->data->mac_addrs);\n \trte_eth_dev_release_port(eth_dev);\n }\n \ndiff --git a/drivers/net/netvsc/hn_ethdev.c b/drivers/net/netvsc/hn_ethdev.c\nindex 8e728d639..aa38ee7a3 100644\n--- a/drivers/net/netvsc/hn_ethdev.c\n+++ b/drivers/net/netvsc/hn_ethdev.c\n@@ -118,20 +118,11 @@ eth_dev_vmbus_allocate(struct rte_vmbus_device *dev, size_t private_data_size)\n static void\n eth_dev_vmbus_release(struct rte_eth_dev *eth_dev)\n {\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n \t/* free ether device */\n \trte_eth_dev_release_port(eth_dev);\n \n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(eth_dev->data->dev_private);\n-\n-\teth_dev->data->dev_private = NULL;\n-\n-\t/*\n-\t * Secondary process will check the name to attach.\n-\t * Clear this field to avoid attaching a released ports.\n-\t */\n-\teth_dev->data->name[0] = '\\0';\n-\n \teth_dev->device = NULL;\n \teth_dev->intr_handle = NULL;\n }\n@@ -829,8 +820,6 @@ eth_hn_dev_uninit(struct rte_eth_dev *eth_dev)\n \trte_free(hv->primary);\n \trte_eth_dev_owner_delete(hv->owner.id);\n \n-\teth_dev->data->mac_addrs = NULL;\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/null/rte_eth_null.c b/drivers/net/null/rte_eth_null.c\nindex 1e8237a41..b77283ae7 100644\n--- a/drivers/net/null/rte_eth_null.c\n+++ b/drivers/net/null/rte_eth_null.c\n@@ -682,8 +682,8 @@ rte_pmd_null_remove(struct rte_vdev_device *dev)\n \tif (rte_eal_process_type() != RTE_PROC_PRIMARY)\n \t\treturn rte_eth_dev_release_port_secondary(eth_dev);\n \n-\trte_free(eth_dev->data->dev_private);\n-\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/octeontx/octeontx_ethdev.c b/drivers/net/octeontx/octeontx_ethdev.c\nindex 5431b44dc..746507912 100644\n--- a/drivers/net/octeontx/octeontx_ethdev.c\n+++ b/drivers/net/octeontx/octeontx_ethdev.c\n@@ -1015,12 +1015,22 @@ octeontx_create(struct rte_vdev_device *dev, int port, uint8_t evdev,\n \t\treturn 0;\n \t}\n \n+\t/* Reserve an ethdev entry */\n+\teth_dev = rte_eth_dev_allocate(octtx_name);\n+\tif (eth_dev == NULL) {\n+\t\tocteontx_log_err(\"failed to allocate rte_eth_dev\");\n+\t\tres = -ENOMEM;\n+\t\tgoto err;\n+\t}\n+\tdata = eth_dev->data;\n+\n \tnic = rte_zmalloc_socket(octtx_name, sizeof(*nic), 0, socket_id);\n \tif (nic == NULL) {\n \t\tocteontx_log_err(\"failed to allocate nic structure\");\n \t\tres = -ENOMEM;\n \t\tgoto err;\n \t}\n+\tdata->dev_private = nic;\n \n \tnic->port_id = port;\n \tnic->evdev = evdev;\n@@ -1037,21 +1047,11 @@ octeontx_create(struct rte_vdev_device *dev, int port, uint8_t evdev,\n \t\tgoto err;\n \t}\n \n-\t/* Reserve an ethdev entry */\n-\teth_dev = rte_eth_dev_allocate(octtx_name);\n-\tif (eth_dev == NULL) {\n-\t\tocteontx_log_err(\"failed to allocate rte_eth_dev\");\n-\t\tres = -ENOMEM;\n-\t\tgoto err;\n-\t}\n-\n \teth_dev->device = &dev->device;\n \teth_dev->intr_handle = NULL;\n \teth_dev->data->kdrv = RTE_KDRV_NONE;\n \teth_dev->data->numa_node = dev->device.numa_node;\n \n-\tdata = eth_dev->data;\n-\tdata->dev_private = nic;\n \tdata->port_id = eth_dev->data->port_id;\n \n \tnic->ev_queues = 1;\n@@ -1103,12 +1103,7 @@ octeontx_create(struct rte_vdev_device *dev, int port, uint8_t evdev,\n \tif (nic)\n \t\tocteontx_port_close(nic);\n \n-\tif (eth_dev != NULL) {\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\trte_free(data);\n-\t\trte_free(nic);\n-\t\trte_eth_dev_release_port(eth_dev);\n-\t}\n+\trte_eth_dev_release_port(eth_dev);\n \n \treturn res;\n }\n@@ -1142,8 +1137,6 @@ octeontx_remove(struct rte_vdev_device *dev)\n \t\trte_event_dev_stop(nic->evdev);\n \t\tPMD_INIT_LOG(INFO, \"Closing octeontx device %s\", octtx_name);\n \n-\t\trte_free(eth_dev->data->mac_addrs);\n-\t\trte_free(eth_dev->data->dev_private);\n \t\trte_eth_dev_release_port(eth_dev);\n \t\trte_event_dev_close(nic->evdev);\n \t}\ndiff --git a/drivers/net/pcap/rte_eth_pcap.c b/drivers/net/pcap/rte_eth_pcap.c\nindex ede5ebb45..1790a8064 100644\n--- a/drivers/net/pcap/rte_eth_pcap.c\n+++ b/drivers/net/pcap/rte_eth_pcap.c\n@@ -1232,11 +1232,9 @@ pmd_pcap_remove(struct rte_vdev_device *dev)\n \t\treturn rte_eth_dev_release_port_secondary(eth_dev);\n \n \tinternals = eth_dev->data->dev_private;\n-\tif (internals && internals->phy_mac)\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\n-\trte_free(eth_dev->data->dev_private);\n-\n+\tif (internals != NULL && internals->phy_mac == 0)\n+\t\t/* not dynamically allocated, must not be freed */\n+\t\teth_dev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/qede/qede_ethdev.c b/drivers/net/qede/qede_ethdev.c\nindex 18d244a93..404859426 100644\n--- a/drivers/net/qede/qede_ethdev.c\n+++ b/drivers/net/qede/qede_ethdev.c\n@@ -2666,11 +2666,6 @@ static int qede_dev_common_uninit(struct rte_eth_dev *eth_dev)\n \teth_dev->rx_pkt_burst = NULL;\n \teth_dev->tx_pkt_burst = NULL;\n \n-\tif (eth_dev->data->mac_addrs)\n-\t\trte_free(eth_dev->data->mac_addrs);\n-\n-\teth_dev->data->mac_addrs = NULL;\n-\n \treturn 0;\n }\n \ndiff --git a/drivers/net/ring/rte_eth_ring.c b/drivers/net/ring/rte_eth_ring.c\nindex bfe2f1780..aeb48f5ec 100644\n--- a/drivers/net/ring/rte_eth_ring.c\n+++ b/drivers/net/ring/rte_eth_ring.c\n@@ -666,10 +666,8 @@ rte_pmd_ring_remove(struct rte_vdev_device *dev)\n \t\t}\n \t}\n \n-\trte_free(eth_dev->data->rx_queues);\n-\trte_free(eth_dev->data->tx_queues);\n-\trte_free(eth_dev->data->dev_private);\n-\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(eth_dev);\n \treturn 0;\n }\ndiff --git a/drivers/net/sfc/sfc_ethdev.c b/drivers/net/sfc/sfc_ethdev.c\nindex b2e17f26e..3886daf7a 100644\n--- a/drivers/net/sfc/sfc_ethdev.c\n+++ b/drivers/net/sfc/sfc_ethdev.c\n@@ -2035,9 +2035,6 @@ sfc_eth_dev_uninit(struct rte_eth_dev *dev)\n \tsfc_detach(sa);\n \tsfc_unprobe(sa);\n \n-\trte_free(dev->data->mac_addrs);\n-\tdev->data->mac_addrs = NULL;\n-\n \tsfc_kvargs_cleanup(sa);\n \n \tsfc_adapter_unlock(sa);\ndiff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c\nindex 0fd264e25..9a2418438 100644\n--- a/drivers/net/softnic/rte_eth_softnic.c\n+++ b/drivers/net/softnic/rte_eth_softnic.c\n@@ -556,7 +556,6 @@ static int\n pmd_remove(struct rte_vdev_device *vdev)\n {\n \tstruct rte_eth_dev *dev = NULL;\n-\tstruct pmd_internals *p;\n \n \tif (!vdev)\n \t\treturn -EINVAL;\n@@ -567,12 +566,12 @@ pmd_remove(struct rte_vdev_device *vdev)\n \tdev = rte_eth_dev_allocated(rte_vdev_device_name(vdev));\n \tif (dev == NULL)\n \t\treturn -ENODEV;\n-\tp = dev->data->dev_private;\n \n \t/* Free device data structures*/\n-\trte_free(dev->data);\n+\tpmd_free(dev->data->dev_private);\n+\tdev->data->dev_private = NULL; /* already freed */\n+\tdev->data->mac_addrs = NULL; /* statically allocated */\n \trte_eth_dev_release_port(dev);\n-\tpmd_free(p);\n \n \treturn 0;\n }\ndiff --git a/drivers/net/szedata2/rte_eth_szedata2.c b/drivers/net/szedata2/rte_eth_szedata2.c\nindex 4e5e01cf1..88448eff6 100644\n--- a/drivers/net/szedata2/rte_eth_szedata2.c\n+++ b/drivers/net/szedata2/rte_eth_szedata2.c\n@@ -1544,7 +1544,6 @@ rte_szedata2_eth_dev_uninit(struct rte_eth_dev *dev)\n \tPMD_INIT_FUNC_TRACE();\n \n \tfree(internals->sze_dev_path);\n-\trte_free(dev->data->mac_addrs);\n \n \tPMD_DRV_LOG(INFO, \"%s device %s successfully uninitialized\",\n \t\t\tRTE_STR(RTE_SZEDATA2_DRIVER_NAME), dev->data->name);\ndiff --git a/drivers/net/tap/rte_eth_tap.c b/drivers/net/tap/rte_eth_tap.c\nindex 84aaf2410..2327fbf8c 100644\n--- a/drivers/net/tap/rte_eth_tap.c\n+++ b/drivers/net/tap/rte_eth_tap.c\n@@ -1808,6 +1808,8 @@ eth_dev_tap_create(struct rte_vdev_device *vdev, char *tap_name,\n error_exit:\n \tif (pmd->ioctl_sock > 0)\n \t\tclose(pmd->ioctl_sock);\n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\tdev->data->mac_addrs = NULL;\n \trte_eth_dev_release_port(dev);\n \n error_exit_nodev:\n@@ -2076,6 +2078,9 @@ rte_pmd_tap_remove(struct rte_vdev_device *dev)\n \tif (!eth_dev)\n \t\treturn -ENODEV;\n \n+\t/* mac_addrs must not be freed alone because part of dev_private */\n+\teth_dev->data->mac_addrs = NULL;\n+\n \tif (rte_eal_process_type() != RTE_PROC_PRIMARY)\n \t\treturn rte_eth_dev_release_port_secondary(eth_dev);\n \n@@ -2102,7 +2107,6 @@ rte_pmd_tap_remove(struct rte_vdev_device *dev)\n \t}\n \n \tclose(internals->ioctl_sock);\n-\trte_free(eth_dev->data->dev_private);\n \trte_eth_dev_release_port(eth_dev);\n \n \tif (internals->ka_fd != -1) {\ndiff --git a/drivers/net/vhost/rte_eth_vhost.c b/drivers/net/vhost/rte_eth_vhost.c\nindex a7604ff23..cf51c072d 100644\n--- a/drivers/net/vhost/rte_eth_vhost.c\n+++ b/drivers/net/vhost/rte_eth_vhost.c\n@@ -1220,10 +1220,12 @@ eth_dev_vhost_create(struct rte_vdev_device *dev, char *iface_name,\n \teth_dev = rte_eth_vdev_allocate(dev, sizeof(*internal));\n \tif (eth_dev == NULL)\n \t\tgoto error;\n+\tdata = eth_dev->data;\n \n \teth_addr = rte_zmalloc_socket(name, sizeof(*eth_addr), 0, numa_node);\n \tif (eth_addr == NULL)\n \t\tgoto error;\n+\tdata->mac_addrs = eth_addr;\n \t*eth_addr = base_eth_addr;\n \teth_addr->addr_bytes[5] = eth_dev->data->port_id;\n \n@@ -1253,13 +1255,11 @@ eth_dev_vhost_create(struct rte_vdev_device *dev, char *iface_name,\n \trte_spinlock_init(&vring_state->lock);\n \tvring_states[eth_dev->data->port_id] = vring_state;\n \n-\tdata = eth_dev->data;\n \tdata->nb_rx_queues = queues;\n \tdata->nb_tx_queues = queues;\n \tinternal->max_queues = queues;\n \tinternal->vid = -1;\n \tdata->dev_link = pmd_link;\n-\tdata->mac_addrs = eth_addr;\n \tdata->dev_flags = RTE_ETH_DEV_INTR_LSC;\n \n \teth_dev->dev_ops = &ops;\n@@ -1291,10 +1291,7 @@ eth_dev_vhost_create(struct rte_vdev_device *dev, char *iface_name,\n \t\tfree(internal->dev_name);\n \t}\n \trte_free(vring_state);\n-\trte_free(eth_addr);\n-\tif (eth_dev)\n-\t\trte_eth_dev_release_port(eth_dev);\n-\trte_free(internal);\n+\trte_eth_dev_release_port(eth_dev);\n \trte_free(list);\n \n \treturn -1;\ndiff --git a/drivers/net/virtio/virtio_ethdev.c b/drivers/net/virtio/virtio_ethdev.c\nindex 730c41707..10a7e3fcc 100644\n--- a/drivers/net/virtio/virtio_ethdev.c\n+++ b/drivers/net/virtio/virtio_ethdev.c\n@@ -1706,9 +1706,6 @@ eth_virtio_dev_uninit(struct rte_eth_dev *eth_dev)\n \teth_dev->tx_pkt_burst = NULL;\n \teth_dev->rx_pkt_burst = NULL;\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \t/* reset interrupt callback  */\n \tif (eth_dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC)\n \t\trte_intr_callback_unregister(eth_dev->intr_handle,\ndiff --git a/drivers/net/virtio/virtio_user_ethdev.c b/drivers/net/virtio/virtio_user_ethdev.c\nindex 525d16cab..420364b7a 100644\n--- a/drivers/net/virtio/virtio_user_ethdev.c\n+++ b/drivers/net/virtio/virtio_user_ethdev.c\n@@ -422,7 +422,6 @@ virtio_user_eth_dev_alloc(struct rte_vdev_device *vdev)\n \tif (!dev) {\n \t\tPMD_INIT_LOG(ERR, \"malloc virtio_user_dev failed\");\n \t\trte_eth_dev_release_port(eth_dev);\n-\t\trte_free(hw);\n \t\treturn NULL;\n \t}\n \n@@ -449,7 +448,6 @@ virtio_user_eth_dev_free(struct rte_eth_dev *eth_dev)\n \tstruct virtio_hw *hw = data->dev_private;\n \n \trte_free(hw->virtio_user_dev);\n-\trte_free(hw);\n \trte_eth_dev_release_port(eth_dev);\n }\n \n@@ -662,7 +660,6 @@ virtio_user_pmd_remove(struct rte_vdev_device *vdev)\n \tdev = hw->virtio_user_dev;\n \tvirtio_user_dev_uninit(dev);\n \n-\trte_free(eth_dev->data->dev_private);\n \trte_eth_dev_release_port(eth_dev);\n \n \treturn 0;\ndiff --git a/drivers/net/vmxnet3/vmxnet3_ethdev.c b/drivers/net/vmxnet3/vmxnet3_ethdev.c\nindex 78e5b7680..41bcd450a 100644\n--- a/drivers/net/vmxnet3/vmxnet3_ethdev.c\n+++ b/drivers/net/vmxnet3/vmxnet3_ethdev.c\n@@ -368,9 +368,6 @@ eth_vmxnet3_dev_uninit(struct rte_eth_dev *eth_dev)\n \teth_dev->tx_pkt_burst = NULL;\n \teth_dev->tx_pkt_prepare = NULL;\n \n-\trte_free(eth_dev->data->mac_addrs);\n-\teth_dev->data->mac_addrs = NULL;\n-\n \treturn 0;\n }\n \ndiff --git a/lib/librte_ethdev/rte_ethdev.c b/lib/librte_ethdev/rte_ethdev.c\nindex 571f0e850..3bc05f4c3 100644\n--- a/lib/librte_ethdev/rte_ethdev.c\n+++ b/lib/librte_ethdev/rte_ethdev.c\n@@ -388,7 +388,14 @@ rte_eth_dev_release_port(struct rte_eth_dev *eth_dev)\n \n \teth_dev->state = RTE_ETH_DEV_UNUSED;\n \n-\tmemset(eth_dev->data, 0, sizeof(struct rte_eth_dev_data));\n+\tif (rte_eal_process_type() == RTE_PROC_PRIMARY) {\n+\t\trte_free(eth_dev->data->rx_queues);\n+\t\trte_free(eth_dev->data->tx_queues);\n+\t\trte_free(eth_dev->data->mac_addrs);\n+\t\trte_free(eth_dev->data->hash_mac_addrs);\n+\t\trte_free(eth_dev->data->dev_private);\n+\t\tmemset(eth_dev->data, 0, sizeof(struct rte_eth_dev_data));\n+\t}\n \n \trte_spinlock_unlock(&rte_eth_dev_shared_data->ownership_lock);\n \n@@ -3529,7 +3536,7 @@ rte_eth_dev_create(struct rte_device *device, const char *name,\n \t\t\tif (!ethdev->data->dev_private) {\n \t\t\t\tRTE_LOG(ERR, EAL, \"failed to allocate private data\");\n \t\t\t\tretval = -ENOMEM;\n-\t\t\t\tgoto data_alloc_failed;\n+\t\t\t\tgoto probe_failed;\n \t\t\t}\n \t\t}\n \t} else {\n@@ -3561,14 +3568,9 @@ rte_eth_dev_create(struct rte_device *device, const char *name,\n \trte_eth_dev_probing_finish(ethdev);\n \n \treturn retval;\n-probe_failed:\n-\t/* free ports private data if primary process */\n-\tif (rte_eal_process_type() == RTE_PROC_PRIMARY)\n-\t\trte_free(ethdev->data->dev_private);\n \n-data_alloc_failed:\n+probe_failed:\n \trte_eth_dev_release_port(ethdev);\n-\n \treturn retval;\n }\n \n@@ -3592,9 +3594,6 @@ rte_eth_dev_destroy(struct rte_eth_dev *ethdev,\n \tif (rte_eal_process_type() != RTE_PROC_PRIMARY)\n \t\treturn rte_eth_dev_release_port_secondary(ethdev);\n \n-\trte_free(ethdev->data->dev_private);\n-\tethdev->data->dev_private = NULL;\n-\n \treturn rte_eth_dev_release_port(ethdev);\n }\n \ndiff --git a/lib/librte_ethdev/rte_ethdev_core.h b/lib/librte_ethdev/rte_ethdev_core.h\nindex 03ec4992a..9fb826e1d 100644\n--- a/lib/librte_ethdev/rte_ethdev_core.h\n+++ b/lib/librte_ethdev/rte_ethdev_core.h\n@@ -579,7 +579,10 @@ struct rte_eth_dev_data {\n \n \tstruct rte_eth_dev_sriov sriov;    /**< SRIOV data */\n \n-\tvoid *dev_private;              /**< PMD-specific private data */\n+\tvoid *dev_private;\n+\t\t\t/**< PMD-specific private data.\n+\t\t\t *   @see rte_eth_dev_release_port()\n+\t\t\t */\n \n \tstruct rte_eth_link dev_link;   /**< Link-level information & status. */\n \tstruct rte_eth_conf dev_conf;   /**< Configuration applied to device. */\n@@ -588,11 +591,16 @@ struct rte_eth_dev_data {\n \t\t\t/**< Common RX buffer size handled by all queues. */\n \n \tuint64_t rx_mbuf_alloc_failed; /**< RX ring mbuf allocation failures. */\n-\tstruct ether_addr *mac_addrs;  /**< Device Ethernet link address. */\n+\tstruct ether_addr *mac_addrs;\n+\t\t\t/**< Device Ethernet link address.\n+\t\t\t *   @see rte_eth_dev_release_port()\n+\t\t\t */\n \tuint64_t mac_pool_sel[ETH_NUM_RECEIVE_MAC_ADDR];\n \t\t\t/**< Bitmap associating MAC addresses to pools. */\n \tstruct ether_addr *hash_mac_addrs;\n-\t\t\t/**< Device Ethernet MAC addresses of hash filtering. */\n+\t\t\t/**< Device Ethernet MAC addresses of hash filtering.\n+\t\t\t *   @see rte_eth_dev_release_port()\n+\t\t\t */\n \tuint16_t port_id;           /**< Device [external] port identifier. */\n \n \t__extension__\ndiff --git a/lib/librte_ethdev/rte_ethdev_driver.h b/lib/librte_ethdev/rte_ethdev_driver.h\nindex ca31b5777..66274be7a 100644\n--- a/lib/librte_ethdev/rte_ethdev_driver.h\n+++ b/lib/librte_ethdev/rte_ethdev_driver.h\n@@ -58,7 +58,14 @@ struct rte_eth_dev *rte_eth_dev_attach_secondary(const char *name);\n \n /**\n  * @internal\n- * Release the specified ethdev port.\n+ * Notify RTE_ETH_EVENT_DESTROY and release the specified ethdev port.\n+ *\n+ * The following PMD-managed data fields will be freed:\n+ *   - dev_private\n+ *   - mac_addrs\n+ *   - hash_mac_addrs\n+ * If one of these fields should not be freed,\n+ * it must be reset to NULL by the PMD, typically in dev_close method.\n  *\n  * @param eth_dev\n  * Device to be detached.\ndiff --git a/lib/librte_ethdev/rte_ethdev_pci.h b/lib/librte_ethdev/rte_ethdev_pci.h\nindex 70d2d2503..8ff4f6b89 100644\n--- a/lib/librte_ethdev/rte_ethdev_pci.h\n+++ b/lib/librte_ethdev/rte_ethdev_pci.h\n@@ -142,16 +142,6 @@ rte_eth_dev_pci_release(struct rte_eth_dev *eth_dev)\n \t\treturn;\n \t}\n \n-\t/* primary process */\n-\trte_free(eth_dev->data->dev_private);\n-\teth_dev->data->dev_private = NULL;\n-\n-\t/*\n-\t * Secondary process will check the name to attach.\n-\t * Clear this field to avoid attaching a released ports.\n-\t */\n-\teth_dev->data->name[0] = '\\0';\n-\n \teth_dev->device = NULL;\n \teth_dev->intr_handle = NULL;\n \n",
    "prefixes": [
        "v6",
        "4/6"
    ]
}