get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 41309,
    "url": "http://patches.dpdk.org/api/patches/41309/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/20180620083705.C831E1B489@dpdk.org/",
    "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": "<20180620083705.C831E1B489@dpdk.org>",
    "list_archive_url": "https://inbox.dpdk.org/dev/20180620083705.C831E1B489@dpdk.org",
    "date": "2018-06-20T08:37:00",
    "name": "[v4] net/bonding: add add/remove mac addrs",
    "commit_ref": null,
    "pull_url": null,
    "state": "accepted",
    "archived": true,
    "hash": "64241c01a85fd4b13a9edfd637e24c7be25cfafa",
    "submitter": {
        "id": 1036,
        "url": "http://patches.dpdk.org/api/people/1036/?format=api",
        "name": "Alex Kiselev",
        "email": "alex@therouter.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/20180620083705.C831E1B489@dpdk.org/mbox/",
    "series": [
        {
            "id": 177,
            "url": "http://patches.dpdk.org/api/series/177/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=177",
            "date": "2018-06-20T08:37:00",
            "name": "[v4] net/bonding: add add/remove mac addrs",
            "version": 4,
            "mbox": "http://patches.dpdk.org/series/177/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/41309/comments/",
    "check": "success",
    "checks": "http://patches.dpdk.org/api/patches/41309/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 C831E1B489;\n\tWed, 20 Jun 2018 10:37:05 +0200 (CEST)",
            "from relay-out2.mail.masterhost.ru (relay-out2.mail.masterhost.ru\n\t[83.222.12.12]) by dpdk.org (Postfix) with ESMTP id 972DF1B487\n\tfor <dev@dpdk.org>; Wed, 20 Jun 2018 10:37:04 +0200 (CEST)",
            "from [37.139.80.50] (helo=h5.therouter.net)\n\tby relay2.mail.masterhost.ru with esmtpa \n\tenvelope from <alex@therouter.net>\n\tauthenticated with alex@therouter.net\n\tmessage id 1fVYbt-0004rR-BG; Wed, 20 Jun 2018 11:37:02 +0300",
            "by h5.therouter.net (sSMTP sendmail emulation);\n\tWed, 20 Jun 2018 11:37:00 +0300"
        ],
        "From": "\"Alex Kiselev\" <alex@therouter.net>",
        "Date": "Wed, 20 Jun 2018 11:37:00 +0300",
        "To": "\"dev@dpdk.org\" <dev@dpdk.org>, Chas Williams <3chas3@gmail.com>,\n\tStephen Hemminger <stephen@networkplumber.org>,\n\tMatan Azrad <matan@mellanox.com>",
        "X-KLMS-Rule-ID": "1",
        "X-KLMS-Message-Action": "clean",
        "X-KLMS-AntiSpam-Lua-Profiles": "126034 [Jun 20 2018]",
        "X-KLMS-AntiSpam-Version": "5.8.1.0",
        "X-KLMS-AntiSpam-Envelope-From": "alex@therouter.net",
        "X-KLMS-AntiSpam-Rate": "0",
        "X-KLMS-AntiSpam-Status": "not_detected",
        "X-KLMS-AntiSpam-Method": "none",
        "X-KLMS-AntiSpam-Info": "LuaCore: 146 146\n\t2365bc6c38c3cc6a39a631922dcb3b077b6ed1a2, {rep_avail},\n\t{msgid_missed_heavy}, DmarcAF: none",
        "X-MS-Exchange-Organization-SCL": "-1",
        "X-KLMS-AntiSpam-Interceptor-Info": "scan successful",
        "X-KLMS-AntiPhishing": "not scanned, disabled by settings",
        "X-KLMS-AntiVirus": "Kaspersky Security for Linux Mail Server, version 8.0.2.16,\n\tnot scanned, license restriction",
        "Subject": "[dpdk-dev] [PATCH v4] net/bonding: add add/remove mac addrs",
        "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>",
        "Message-Id": "<20180620083705.C831E1B489@dpdk.org>"
    },
    "content": "add functions to add/remove MAC addresses\nSigned-off-by: Alex Kiselev <alex@therouter.net>\n---\n drivers/net/bonding/rte_eth_bond_api.c     |  12 ++-\n drivers/net/bonding/rte_eth_bond_pmd.c     | 131 ++++++++++++++++++++++++++++-\n drivers/net/bonding/rte_eth_bond_private.h |   8 ++\n 3 files changed, 146 insertions(+), 5 deletions(-)",
    "diff": "diff --git a/drivers/net/bonding/rte_eth_bond_api.c b/drivers/net/bonding/rte_eth_bond_api.c\nindex d558df8b9..9123f4614 100644\n--- a/drivers/net/bonding/rte_eth_bond_api.c\n+++ b/drivers/net/bonding/rte_eth_bond_api.c\n@@ -373,6 +373,13 @@ __eth_bond_slave_add_lock_free(uint16_t bonded_port_id, uint16_t slave_port_id)\n \t\treturn -1;\n \t}\n \n+\t/* Add additional MAC addresses to the slave */\n+\tif (slave_add_mac_addresses(bonded_eth_dev, slave_port_id) != 0) {\n+\t\tRTE_BOND_LOG(ERR, \"Failed to add mac address(es) to slave %hu\",\n+\t\t\t\tslave_port_id);\n+\t\treturn -1;\n+\t}\n+\n \tinternals->slave_count++;\n \n \tif (bonded_eth_dev->data->dev_started) {\n@@ -387,7 +394,7 @@ __eth_bond_slave_add_lock_free(uint16_t bonded_port_id, uint16_t slave_port_id)\n \t/* Add slave details to bonded device */\n \tslave_eth_dev->data->dev_flags |= RTE_ETH_DEV_BONDED_SLAVE;\n \n-\t/* Update all slave devices MACs*/\n+\t/* Update all slave devices MACs */\n \tmac_address_slaves_update(bonded_eth_dev);\n \n \t/* Register link status change callback with bonded device pointer as\n@@ -491,6 +498,9 @@ __eth_bond_slave_remove_lock_free(uint16_t bonded_port_id,\n \trte_eth_dev_default_mac_addr_set(slave_port_id,\n \t\t\t&(internals->slaves[slave_idx].persisted_mac_addr));\n \n+\t/* remove additional MAC addresses from the slave */\n+\tslave_remove_mac_addresses(bonded_eth_dev, slave_port_id);\n+\n \t/*\n \t * Remove bond device flows from slave device.\n \t * Note: don't restore flow isolate mode.\ndiff --git a/drivers/net/bonding/rte_eth_bond_pmd.c b/drivers/net/bonding/rte_eth_bond_pmd.c\nindex 02d94b1b1..20b8ec06f 100644\n--- a/drivers/net/bonding/rte_eth_bond_pmd.c\n+++ b/drivers/net/bonding/rte_eth_bond_pmd.c\n@@ -25,6 +25,7 @@\n \n #define REORDER_PERIOD_MS 10\n #define DEFAULT_POLLING_INTERVAL_10_MS (10)\n+#define BOND_MAX_MAC_ADDRS 16\n \n #define HASH_L4_PORTS(h) ((h)->src_port ^ (h)->dst_port)\n \n@@ -1588,6 +1589,61 @@ mac_address_set(struct rte_eth_dev *eth_dev, struct ether_addr *new_mac_addr)\n \treturn 0;\n }\n \n+static const struct ether_addr null_mac_addr;\n+\n+/*\n+ * Add additional MAC addresses to the slave\n+ */\n+int\n+slave_add_mac_addresses(struct rte_eth_dev *bonded_eth_dev,\n+\t\tuint16_t slave_port_id)\n+{\n+\tint i, ret;\n+\tstruct ether_addr *mac_addr;\n+\n+\tfor (i = 1; i < BOND_MAX_MAC_ADDRS; i++) {\n+\t\tmac_addr = &bonded_eth_dev->data->mac_addrs[i];\n+\t\tif (is_same_ether_addr(mac_addr, &null_mac_addr))\n+\t\t\tbreak;\n+\n+\t\tret = rte_eth_dev_mac_addr_add(slave_port_id, mac_addr, 0);\n+\t\tif (ret < 0) {\n+\t\t\t/* rollback */\n+\t\t\tfor (i--; i > 0; i--)\n+\t\t\t\trte_eth_dev_mac_addr_remove(slave_port_id,\n+\t\t\t\t\t&bonded_eth_dev->data->mac_addrs[i]);\n+\t\t\treturn ret;\n+\t\t}\n+\t}\n+\n+\treturn 0;\n+}\n+\n+/*\n+ * Remove additional MAC addresses from the slave\n+ */\n+int\n+slave_remove_mac_addresses(struct rte_eth_dev *bonded_eth_dev,\n+\t\tuint16_t slave_port_id)\n+{\n+\tint i, rc, ret;\n+\tstruct ether_addr *mac_addr;\n+\n+\trc = 0;\n+\tfor (i = 1; i < BOND_MAX_MAC_ADDRS; i++) {\n+\t\tmac_addr = &bonded_eth_dev->data->mac_addrs[i];\n+\t\tif (is_same_ether_addr(mac_addr, &null_mac_addr))\n+\t\t\tbreak;\n+\n+\t\tret = rte_eth_dev_mac_addr_remove(slave_port_id, mac_addr);\n+\t\t/* save only the first error */\n+\t\tif (ret < 0 && rc == 0)\n+\t\t\trc = ret;\n+\t}\n+\n+\treturn rc;\n+}\n+\n int\n mac_address_slaves_update(struct rte_eth_dev *bonded_eth_dev)\n {\n@@ -2219,7 +2275,7 @@ bond_ethdev_info(struct rte_eth_dev *dev, struct rte_eth_dev_info *dev_info)\n \tuint16_t max_nb_rx_queues = UINT16_MAX;\n \tuint16_t max_nb_tx_queues = UINT16_MAX;\n \n-\tdev_info->max_mac_addrs = 1;\n+\tdev_info->max_mac_addrs = BOND_MAX_MAC_ADDRS;\n \n \tdev_info->max_rx_pktlen = internals->candidate_max_rx_pktlen ?\n \t\t\tinternals->candidate_max_rx_pktlen :\n@@ -2905,6 +2961,68 @@ bond_filter_ctrl(struct rte_eth_dev *dev __rte_unused,\n \treturn -ENOTSUP;\n }\n \n+static int\n+bond_ethdev_mac_addr_add(struct rte_eth_dev *dev, struct ether_addr *mac_addr,\n+\t\t\t\t__rte_unused uint32_t index, uint32_t vmdq)\n+{\n+\tstruct rte_eth_dev *slave_eth_dev;\n+\tstruct bond_dev_private *internals = dev->data->dev_private;\n+\tint ret, i;\n+\n+\trte_spinlock_lock(&internals->lock);\n+\n+\tfor (i = 0; i < internals->slave_count; i++) {\n+\t\tslave_eth_dev = &rte_eth_devices[internals->slaves[i].port_id];\n+\t\tif (*slave_eth_dev->dev_ops->mac_addr_add == NULL ||\n+\t\t\t *slave_eth_dev->dev_ops->mac_addr_remove == NULL) {\n+\t\t\tret = -ENOTSUP;\n+\t\t\tgoto end;\n+\t\t}\n+\t}\n+\n+\tfor (i = 0; i < internals->slave_count; i++) {\n+\t\tret = rte_eth_dev_mac_addr_add(internals->slaves[i].port_id,\n+\t\t\t\tmac_addr, vmdq);\n+\t\tif (ret < 0) {\n+\t\t\t/* rollback */\n+\t\t\tfor (i--; i >= 0; i--)\n+\t\t\t\trte_eth_dev_mac_addr_remove(\n+\t\t\t\t\tinternals->slaves[i].port_id, mac_addr);\n+\t\t\tgoto end;\n+\t\t}\n+\t}\n+\n+\tret = 0;\n+end:\n+\trte_spinlock_unlock(&internals->lock);\n+\treturn ret;\n+}\n+\n+static void\n+bond_ethdev_mac_addr_remove(struct rte_eth_dev *dev, uint32_t index)\n+{\n+\tstruct rte_eth_dev *slave_eth_dev;\n+\tstruct bond_dev_private *internals = dev->data->dev_private;\n+\tint i;\n+\n+\trte_spinlock_lock(&internals->lock);\n+\n+\tfor (i = 0; i < internals->slave_count; i++) {\n+\t\tslave_eth_dev = &rte_eth_devices[internals->slaves[i].port_id];\n+\t\tif (*slave_eth_dev->dev_ops->mac_addr_remove == NULL)\n+\t\t\tgoto end;\n+\t}\n+\n+\tstruct ether_addr *mac_addr = &dev->data->mac_addrs[index];\n+\n+\tfor (i = 0; i < internals->slave_count; i++)\n+\t\trte_eth_dev_mac_addr_remove(internals->slaves[i].port_id,\n+\t\t\t\tmac_addr);\n+\n+end:\n+\trte_spinlock_unlock(&internals->lock);\n+}\n+\n const struct eth_dev_ops default_dev_ops = {\n \t.dev_start            = bond_ethdev_start,\n \t.dev_stop             = bond_ethdev_stop,\n@@ -2927,6 +3045,8 @@ const struct eth_dev_ops default_dev_ops = {\n \t.rss_hash_conf_get    = bond_ethdev_rss_hash_conf_get,\n \t.mtu_set              = bond_ethdev_mtu_set,\n \t.mac_addr_set         = bond_ethdev_mac_address_set,\n+\t.mac_addr_add         = bond_ethdev_mac_addr_add,\n+\t.mac_addr_remove      = bond_ethdev_mac_addr_remove,\n \t.filter_ctrl          = bond_filter_ctrl\n };\n \n@@ -2954,10 +3074,13 @@ bond_alloc(struct rte_vdev_device *dev, uint8_t mode)\n \teth_dev->data->nb_rx_queues = (uint16_t)1;\n \teth_dev->data->nb_tx_queues = (uint16_t)1;\n \n-\teth_dev->data->mac_addrs = rte_zmalloc_socket(name, ETHER_ADDR_LEN, 0,\n-\t\t\tsocket_id);\n+\t/* Allocate memory for storing MAC addresses */\n+\teth_dev->data->mac_addrs = rte_zmalloc_socket(name, ETHER_ADDR_LEN *\n+\t\t\tBOND_MAX_MAC_ADDRS, 0, socket_id);\n \tif (eth_dev->data->mac_addrs == NULL) {\n-\t\tRTE_BOND_LOG(ERR, \"Unable to malloc mac_addrs\");\n+\t\tRTE_BOND_LOG(ERR,\n+\t\t\t     \"Failed to allocate %u bytes needed to store MAC addresses\",\n+\t\t\t     ETHER_ADDR_LEN * BOND_MAX_MAC_ADDRS);\n \t\tgoto err;\n \t}\n \ndiff --git a/drivers/net/bonding/rte_eth_bond_private.h b/drivers/net/bonding/rte_eth_bond_private.h\nindex 65445b863..43e0e448d 100644\n--- a/drivers/net/bonding/rte_eth_bond_private.h\n+++ b/drivers/net/bonding/rte_eth_bond_private.h\n@@ -230,6 +230,14 @@ mac_address_get(struct rte_eth_dev *eth_dev, struct ether_addr *dst_mac_addr);\n int\n mac_address_slaves_update(struct rte_eth_dev *bonded_eth_dev);\n \n+int\n+slave_add_mac_addresses(struct rte_eth_dev *bonded_eth_dev,\n+\t\tuint16_t slave_port_id);\n+\n+int\n+slave_remove_mac_addresses(struct rte_eth_dev *bonded_eth_dev,\n+\t\tuint16_t slave_port_id);\n+\n int\n bond_ethdev_mode_set(struct rte_eth_dev *eth_dev, int mode);\n \n",
    "prefixes": [
        "v4"
    ]
}