18fd92a66SOlivier Matz /* SPDX-License-Identifier: BSD-3-Clause 2e60fbd5bSAdrien Mazarguil * Copyright 2015 6WIND S.A. 3e60fbd5bSAdrien Mazarguil * Copyright 2015 Mellanox. 4e60fbd5bSAdrien Mazarguil */ 58fd92a66SOlivier Matz 63f2fe392SNélio Laranjeiro #include <unistd.h> 7e60fbd5bSAdrien Mazarguil 8e60fbd5bSAdrien Mazarguil #include <rte_ether.h> 9ffc905f3SFerruh Yigit #include <rte_ethdev_driver.h> 10198a3c33SNelio Laranjeiro #include <rte_interrupts.h> 11198a3c33SNelio Laranjeiro #include <rte_alarm.h> 12e60fbd5bSAdrien Mazarguil 13e60fbd5bSAdrien Mazarguil #include "mlx5.h" 14e60fbd5bSAdrien Mazarguil #include "mlx5_rxtx.h" 15e60fbd5bSAdrien Mazarguil #include "mlx5_utils.h" 16e60fbd5bSAdrien Mazarguil 176e78005aSNélio Laranjeiro static void 186e78005aSNélio Laranjeiro priv_txq_stop(struct priv *priv) 196e78005aSNélio Laranjeiro { 206e78005aSNélio Laranjeiro unsigned int i; 216e78005aSNélio Laranjeiro 226e78005aSNélio Laranjeiro for (i = 0; i != priv->txqs_n; ++i) 236e78005aSNélio Laranjeiro mlx5_priv_txq_release(priv, i); 246e78005aSNélio Laranjeiro } 256e78005aSNélio Laranjeiro 266e78005aSNélio Laranjeiro static int 276e78005aSNélio Laranjeiro priv_txq_start(struct priv *priv) 286e78005aSNélio Laranjeiro { 296e78005aSNélio Laranjeiro unsigned int i; 306e78005aSNélio Laranjeiro int ret = 0; 316e78005aSNélio Laranjeiro 326e78005aSNélio Laranjeiro /* Add memory regions to Tx queues. */ 336e78005aSNélio Laranjeiro for (i = 0; i != priv->txqs_n; ++i) { 346e78005aSNélio Laranjeiro unsigned int idx = 0; 356e78005aSNélio Laranjeiro struct mlx5_mr *mr; 366e78005aSNélio Laranjeiro struct mlx5_txq_ctrl *txq_ctrl = mlx5_priv_txq_get(priv, i); 376e78005aSNélio Laranjeiro 386e78005aSNélio Laranjeiro if (!txq_ctrl) 396e78005aSNélio Laranjeiro continue; 40de48f165SYongseok Koh LIST_FOREACH(mr, &priv->mr, next) { 416e78005aSNélio Laranjeiro priv_txq_mp2mr_reg(priv, &txq_ctrl->txq, mr->mp, idx++); 42de48f165SYongseok Koh if (idx == MLX5_PMD_TX_MP_CACHE) 43de48f165SYongseok Koh break; 44de48f165SYongseok Koh } 456e78005aSNélio Laranjeiro txq_alloc_elts(txq_ctrl); 466e78005aSNélio Laranjeiro txq_ctrl->ibv = mlx5_priv_txq_ibv_new(priv, i); 476e78005aSNélio Laranjeiro if (!txq_ctrl->ibv) { 486e78005aSNélio Laranjeiro ret = ENOMEM; 496e78005aSNélio Laranjeiro goto error; 506e78005aSNélio Laranjeiro } 516e78005aSNélio Laranjeiro } 524a984153SXueming Li ret = priv_tx_uar_remap(priv, priv->ctx->cmd_fd); 534a984153SXueming Li if (ret) 544a984153SXueming Li goto error; 554a984153SXueming Li return ret; 566e78005aSNélio Laranjeiro error: 576e78005aSNélio Laranjeiro priv_txq_stop(priv); 584a984153SXueming Li return ret; 596e78005aSNélio Laranjeiro } 606e78005aSNélio Laranjeiro 61a1366b1aSNélio Laranjeiro static void 62a1366b1aSNélio Laranjeiro priv_rxq_stop(struct priv *priv) 63a1366b1aSNélio Laranjeiro { 64a1366b1aSNélio Laranjeiro unsigned int i; 65a1366b1aSNélio Laranjeiro 66a1366b1aSNélio Laranjeiro for (i = 0; i != priv->rxqs_n; ++i) 67a1366b1aSNélio Laranjeiro mlx5_priv_rxq_release(priv, i); 68a1366b1aSNélio Laranjeiro } 69a1366b1aSNélio Laranjeiro 70a1366b1aSNélio Laranjeiro static int 71a1366b1aSNélio Laranjeiro priv_rxq_start(struct priv *priv) 72a1366b1aSNélio Laranjeiro { 73a1366b1aSNélio Laranjeiro unsigned int i; 74a1366b1aSNélio Laranjeiro int ret = 0; 75a1366b1aSNélio Laranjeiro 76a1366b1aSNélio Laranjeiro for (i = 0; i != priv->rxqs_n; ++i) { 77a1366b1aSNélio Laranjeiro struct mlx5_rxq_ctrl *rxq_ctrl = mlx5_priv_rxq_get(priv, i); 78a1366b1aSNélio Laranjeiro 79a1366b1aSNélio Laranjeiro if (!rxq_ctrl) 80a1366b1aSNélio Laranjeiro continue; 81a1366b1aSNélio Laranjeiro ret = rxq_alloc_elts(rxq_ctrl); 82a1366b1aSNélio Laranjeiro if (ret) 83a1366b1aSNélio Laranjeiro goto error; 84a1366b1aSNélio Laranjeiro rxq_ctrl->ibv = mlx5_priv_rxq_ibv_new(priv, i); 85a1366b1aSNélio Laranjeiro if (!rxq_ctrl->ibv) { 86a1366b1aSNélio Laranjeiro ret = ENOMEM; 87a1366b1aSNélio Laranjeiro goto error; 88a1366b1aSNélio Laranjeiro } 89a1366b1aSNélio Laranjeiro } 90a1366b1aSNélio Laranjeiro return -ret; 91a1366b1aSNélio Laranjeiro error: 92a1366b1aSNélio Laranjeiro priv_rxq_stop(priv); 93a1366b1aSNélio Laranjeiro return -ret; 94a1366b1aSNélio Laranjeiro } 95a1366b1aSNélio Laranjeiro 96e60fbd5bSAdrien Mazarguil /** 97e60fbd5bSAdrien Mazarguil * DPDK callback to start the device. 98e60fbd5bSAdrien Mazarguil * 99e60fbd5bSAdrien Mazarguil * Simulate device start by attaching all configured flows. 100e60fbd5bSAdrien Mazarguil * 101e60fbd5bSAdrien Mazarguil * @param dev 102e60fbd5bSAdrien Mazarguil * Pointer to Ethernet device structure. 103e60fbd5bSAdrien Mazarguil * 104e60fbd5bSAdrien Mazarguil * @return 105e60fbd5bSAdrien Mazarguil * 0 on success, negative errno value on failure. 106e60fbd5bSAdrien Mazarguil */ 107e60fbd5bSAdrien Mazarguil int 108e60fbd5bSAdrien Mazarguil mlx5_dev_start(struct rte_eth_dev *dev) 109e60fbd5bSAdrien Mazarguil { 110e60fbd5bSAdrien Mazarguil struct priv *priv = dev->data->dev_private; 1116e78005aSNélio Laranjeiro struct mlx5_mr *mr = NULL; 112ecc1c29dSAdrien Mazarguil int err; 113e60fbd5bSAdrien Mazarguil 114272733b5SNélio Laranjeiro dev->data->dev_started = 1; 115e60fbd5bSAdrien Mazarguil priv_lock(priv); 116272733b5SNélio Laranjeiro err = priv_flow_create_drop_queue(priv); 117272733b5SNélio Laranjeiro if (err) { 118272733b5SNélio Laranjeiro ERROR("%p: Drop queue allocation failed: %s", 119272733b5SNélio Laranjeiro (void *)dev, strerror(err)); 120272733b5SNélio Laranjeiro goto error; 121272733b5SNélio Laranjeiro } 122ecc1c29dSAdrien Mazarguil DEBUG("%p: allocating and configuring hash RX queues", (void *)dev); 1236e78005aSNélio Laranjeiro rte_mempool_walk(mlx5_mp2mr_iter, priv); 1246e78005aSNélio Laranjeiro err = priv_txq_start(priv); 1256e78005aSNélio Laranjeiro if (err) { 1266e78005aSNélio Laranjeiro ERROR("%p: TXQ allocation failed: %s", 1276e78005aSNélio Laranjeiro (void *)dev, strerror(err)); 1286e78005aSNélio Laranjeiro goto error; 1296e78005aSNélio Laranjeiro } 130a1366b1aSNélio Laranjeiro err = priv_rxq_start(priv); 131a1366b1aSNélio Laranjeiro if (err) { 132a1366b1aSNélio Laranjeiro ERROR("%p: RXQ allocation failed: %s", 133a1366b1aSNélio Laranjeiro (void *)dev, strerror(err)); 134a1366b1aSNélio Laranjeiro goto error; 135a1366b1aSNélio Laranjeiro } 136e1016cb7SAdrien Mazarguil err = priv_rx_intr_vec_enable(priv); 137e1016cb7SAdrien Mazarguil if (err) { 138e1016cb7SAdrien Mazarguil ERROR("%p: RX interrupt vector creation failed", 139e1016cb7SAdrien Mazarguil (void *)priv); 140e1016cb7SAdrien Mazarguil goto error; 1413c7d44afSShahaf Shuler } 142c8d4ee50SNélio Laranjeiro priv_xstats_init(priv); 143c7bf6225SYongseok Koh /* Update link status and Tx/Rx callbacks for the first time. */ 144c7bf6225SYongseok Koh memset(&dev->data->dev_link, 0, sizeof(struct rte_eth_link)); 145e313ef4cSShahaf Shuler INFO("Forcing port %u link to be up", dev->data->port_id); 146e313ef4cSShahaf Shuler err = priv_force_link_status_change(priv, ETH_LINK_UP); 147e313ef4cSShahaf Shuler if (err) { 148e313ef4cSShahaf Shuler DEBUG("Failed to set port %u link to be up", 149e313ef4cSShahaf Shuler dev->data->port_id); 150e313ef4cSShahaf Shuler goto error; 151e313ef4cSShahaf Shuler } 152c7bf6225SYongseok Koh priv_dev_interrupt_handler_install(priv, dev); 153c8d4ee50SNélio Laranjeiro priv_unlock(priv); 154c8d4ee50SNélio Laranjeiro return 0; 155c8d4ee50SNélio Laranjeiro error: 156e60fbd5bSAdrien Mazarguil /* Rollback. */ 157272733b5SNélio Laranjeiro dev->data->dev_started = 0; 1585f64e6bfSNélio Laranjeiro for (mr = LIST_FIRST(&priv->mr); mr; mr = LIST_FIRST(&priv->mr)) 1596e78005aSNélio Laranjeiro priv_mr_release(priv, mr); 1601b37f5d8SNélio Laranjeiro priv_flow_stop(priv, &priv->flows); 16129957ec4SNélio Laranjeiro priv_dev_traffic_disable(priv, dev); 1626e78005aSNélio Laranjeiro priv_txq_stop(priv); 163272733b5SNélio Laranjeiro priv_rxq_stop(priv); 164272733b5SNélio Laranjeiro priv_flow_delete_drop_queue(priv); 1655e0fbcf9SYongseok Koh priv_unlock(priv); 16680554894SOlivier Matz return err; 167e60fbd5bSAdrien Mazarguil } 168e60fbd5bSAdrien Mazarguil 169e60fbd5bSAdrien Mazarguil /** 170e60fbd5bSAdrien Mazarguil * DPDK callback to stop the device. 171e60fbd5bSAdrien Mazarguil * 172e60fbd5bSAdrien Mazarguil * Simulate device stop by detaching all configured flows. 173e60fbd5bSAdrien Mazarguil * 174e60fbd5bSAdrien Mazarguil * @param dev 175e60fbd5bSAdrien Mazarguil * Pointer to Ethernet device structure. 176e60fbd5bSAdrien Mazarguil */ 177e60fbd5bSAdrien Mazarguil void 178e60fbd5bSAdrien Mazarguil mlx5_dev_stop(struct rte_eth_dev *dev) 179e60fbd5bSAdrien Mazarguil { 180e60fbd5bSAdrien Mazarguil struct priv *priv = dev->data->dev_private; 1816e78005aSNélio Laranjeiro struct mlx5_mr *mr; 182e60fbd5bSAdrien Mazarguil 183e60fbd5bSAdrien Mazarguil priv_lock(priv); 1843f2fe392SNélio Laranjeiro dev->data->dev_started = 0; 1853f2fe392SNélio Laranjeiro /* Prevent crashes when queues are still in use. */ 1863f2fe392SNélio Laranjeiro dev->rx_pkt_burst = removed_rx_burst; 1873f2fe392SNélio Laranjeiro dev->tx_pkt_burst = removed_tx_burst; 1883f2fe392SNélio Laranjeiro rte_wmb(); 1893f2fe392SNélio Laranjeiro usleep(1000 * priv->rxqs_n); 190ecc1c29dSAdrien Mazarguil DEBUG("%p: cleaning up and destroying hash RX queues", (void *)dev); 1911b37f5d8SNélio Laranjeiro priv_flow_stop(priv, &priv->flows); 19229957ec4SNélio Laranjeiro priv_dev_traffic_disable(priv, dev); 193e1016cb7SAdrien Mazarguil priv_rx_intr_vec_disable(priv); 1941b37f5d8SNélio Laranjeiro priv_dev_interrupt_handler_uninstall(priv, dev); 1956e78005aSNélio Laranjeiro priv_txq_stop(priv); 196a1366b1aSNélio Laranjeiro priv_rxq_stop(priv); 1975f64e6bfSNélio Laranjeiro for (mr = LIST_FIRST(&priv->mr); mr; mr = LIST_FIRST(&priv->mr)) 1986e78005aSNélio Laranjeiro priv_mr_release(priv, mr); 199272733b5SNélio Laranjeiro priv_flow_delete_drop_queue(priv); 200e60fbd5bSAdrien Mazarguil priv_unlock(priv); 201e60fbd5bSAdrien Mazarguil } 202272733b5SNélio Laranjeiro 203272733b5SNélio Laranjeiro /** 204272733b5SNélio Laranjeiro * Enable traffic flows configured by control plane 205272733b5SNélio Laranjeiro * 206272733b5SNélio Laranjeiro * @param priv 207272733b5SNélio Laranjeiro * Pointer to Ethernet device private data. 208272733b5SNélio Laranjeiro * @param dev 209272733b5SNélio Laranjeiro * Pointer to Ethernet device structure. 210272733b5SNélio Laranjeiro * 211272733b5SNélio Laranjeiro * @return 212272733b5SNélio Laranjeiro * 0 on success. 213272733b5SNélio Laranjeiro */ 214272733b5SNélio Laranjeiro int 215272733b5SNélio Laranjeiro priv_dev_traffic_enable(struct priv *priv, struct rte_eth_dev *dev) 216272733b5SNélio Laranjeiro { 217272733b5SNélio Laranjeiro struct rte_flow_item_eth bcast = { 218272733b5SNélio Laranjeiro .dst.addr_bytes = "\xff\xff\xff\xff\xff\xff", 219272733b5SNélio Laranjeiro }; 220272733b5SNélio Laranjeiro struct rte_flow_item_eth ipv6_multi_spec = { 221272733b5SNélio Laranjeiro .dst.addr_bytes = "\x33\x33\x00\x00\x00\x00", 222272733b5SNélio Laranjeiro }; 223272733b5SNélio Laranjeiro struct rte_flow_item_eth ipv6_multi_mask = { 224272733b5SNélio Laranjeiro .dst.addr_bytes = "\xff\xff\x00\x00\x00\x00", 225272733b5SNélio Laranjeiro }; 226272733b5SNélio Laranjeiro struct rte_flow_item_eth unicast = { 227272733b5SNélio Laranjeiro .src.addr_bytes = "\x00\x00\x00\x00\x00\x00", 228272733b5SNélio Laranjeiro }; 229272733b5SNélio Laranjeiro struct rte_flow_item_eth unicast_mask = { 230272733b5SNélio Laranjeiro .dst.addr_bytes = "\xff\xff\xff\xff\xff\xff", 231272733b5SNélio Laranjeiro }; 232272733b5SNélio Laranjeiro const unsigned int vlan_filter_n = priv->vlan_filter_n; 233272733b5SNélio Laranjeiro const struct ether_addr cmp = { 234272733b5SNélio Laranjeiro .addr_bytes = "\x00\x00\x00\x00\x00\x00", 235272733b5SNélio Laranjeiro }; 236272733b5SNélio Laranjeiro unsigned int i; 237272733b5SNélio Laranjeiro unsigned int j; 238272733b5SNélio Laranjeiro int ret; 239272733b5SNélio Laranjeiro 240f8cb4b57SNélio Laranjeiro if (priv->isolated) 241f8cb4b57SNélio Laranjeiro return 0; 242f8cb4b57SNélio Laranjeiro if (dev->data->promiscuous) { 243f8cb4b57SNélio Laranjeiro struct rte_flow_item_eth promisc = { 244f8cb4b57SNélio Laranjeiro .dst.addr_bytes = "\x00\x00\x00\x00\x00\x00", 245f8cb4b57SNélio Laranjeiro .src.addr_bytes = "\x00\x00\x00\x00\x00\x00", 246f8cb4b57SNélio Laranjeiro .type = 0, 247f8cb4b57SNélio Laranjeiro }; 248f8cb4b57SNélio Laranjeiro 249f8cb4b57SNélio Laranjeiro claim_zero(mlx5_ctrl_flow(dev, &promisc, &promisc)); 250f8cb4b57SNélio Laranjeiro return 0; 251f8cb4b57SNélio Laranjeiro } 252f8cb4b57SNélio Laranjeiro if (dev->data->all_multicast) { 253f8cb4b57SNélio Laranjeiro struct rte_flow_item_eth multicast = { 254f8cb4b57SNélio Laranjeiro .dst.addr_bytes = "\x01\x00\x00\x00\x00\x00", 255f8cb4b57SNélio Laranjeiro .src.addr_bytes = "\x00\x00\x00\x00\x00\x00", 256f8cb4b57SNélio Laranjeiro .type = 0, 257f8cb4b57SNélio Laranjeiro }; 258f8cb4b57SNélio Laranjeiro 259f8cb4b57SNélio Laranjeiro claim_zero(mlx5_ctrl_flow(dev, &multicast, &multicast)); 260f8cb4b57SNélio Laranjeiro } else { 261f8cb4b57SNélio Laranjeiro /* Add broadcast/multicast flows. */ 262f8cb4b57SNélio Laranjeiro for (i = 0; i != vlan_filter_n; ++i) { 263f8cb4b57SNélio Laranjeiro uint16_t vlan = priv->vlan_filter[i]; 264f8cb4b57SNélio Laranjeiro 265f8cb4b57SNélio Laranjeiro struct rte_flow_item_vlan vlan_spec = { 266f8cb4b57SNélio Laranjeiro .tci = rte_cpu_to_be_16(vlan), 267f8cb4b57SNélio Laranjeiro }; 268f8cb4b57SNélio Laranjeiro struct rte_flow_item_vlan vlan_mask = { 269f8cb4b57SNélio Laranjeiro .tci = 0xffff, 270f8cb4b57SNélio Laranjeiro }; 271f8cb4b57SNélio Laranjeiro 272f8cb4b57SNélio Laranjeiro ret = mlx5_ctrl_flow_vlan(dev, &bcast, &bcast, 273f8cb4b57SNélio Laranjeiro &vlan_spec, &vlan_mask); 274f8cb4b57SNélio Laranjeiro if (ret) 275f8cb4b57SNélio Laranjeiro goto error; 276f8cb4b57SNélio Laranjeiro ret = mlx5_ctrl_flow_vlan(dev, &ipv6_multi_spec, 277f8cb4b57SNélio Laranjeiro &ipv6_multi_mask, 278f8cb4b57SNélio Laranjeiro &vlan_spec, &vlan_mask); 279f8cb4b57SNélio Laranjeiro if (ret) 280f8cb4b57SNélio Laranjeiro goto error; 281f8cb4b57SNélio Laranjeiro } 282f8cb4b57SNélio Laranjeiro if (!vlan_filter_n) { 283f8cb4b57SNélio Laranjeiro ret = mlx5_ctrl_flow(dev, &bcast, &bcast); 284f8cb4b57SNélio Laranjeiro if (ret) 285f8cb4b57SNélio Laranjeiro goto error; 286f8cb4b57SNélio Laranjeiro ret = mlx5_ctrl_flow(dev, &ipv6_multi_spec, 287f8cb4b57SNélio Laranjeiro &ipv6_multi_mask); 288f8cb4b57SNélio Laranjeiro if (ret) 289f8cb4b57SNélio Laranjeiro goto error; 290f8cb4b57SNélio Laranjeiro } 291f8cb4b57SNélio Laranjeiro } 292f8cb4b57SNélio Laranjeiro /* Add MAC address flows. */ 293272733b5SNélio Laranjeiro for (i = 0; i != MLX5_MAX_MAC_ADDRESSES; ++i) { 294272733b5SNélio Laranjeiro struct ether_addr *mac = &dev->data->mac_addrs[i]; 295272733b5SNélio Laranjeiro 296272733b5SNélio Laranjeiro if (!memcmp(mac, &cmp, sizeof(*mac))) 297272733b5SNélio Laranjeiro continue; 298272733b5SNélio Laranjeiro memcpy(&unicast.dst.addr_bytes, 299272733b5SNélio Laranjeiro mac->addr_bytes, 300272733b5SNélio Laranjeiro ETHER_ADDR_LEN); 301272733b5SNélio Laranjeiro for (j = 0; j != vlan_filter_n; ++j) { 302272733b5SNélio Laranjeiro uint16_t vlan = priv->vlan_filter[j]; 303272733b5SNélio Laranjeiro 304272733b5SNélio Laranjeiro struct rte_flow_item_vlan vlan_spec = { 305272733b5SNélio Laranjeiro .tci = rte_cpu_to_be_16(vlan), 306272733b5SNélio Laranjeiro }; 307272733b5SNélio Laranjeiro struct rte_flow_item_vlan vlan_mask = { 308272733b5SNélio Laranjeiro .tci = 0xffff, 309272733b5SNélio Laranjeiro }; 310272733b5SNélio Laranjeiro 311272733b5SNélio Laranjeiro ret = mlx5_ctrl_flow_vlan(dev, &unicast, 312272733b5SNélio Laranjeiro &unicast_mask, 313272733b5SNélio Laranjeiro &vlan_spec, 314272733b5SNélio Laranjeiro &vlan_mask); 315272733b5SNélio Laranjeiro if (ret) 316272733b5SNélio Laranjeiro goto error; 317272733b5SNélio Laranjeiro } 318272733b5SNélio Laranjeiro if (!vlan_filter_n) { 319272733b5SNélio Laranjeiro ret = mlx5_ctrl_flow(dev, &unicast, 320272733b5SNélio Laranjeiro &unicast_mask); 321272733b5SNélio Laranjeiro if (ret) 322272733b5SNélio Laranjeiro goto error; 323272733b5SNélio Laranjeiro } 324272733b5SNélio Laranjeiro } 325272733b5SNélio Laranjeiro return 0; 326272733b5SNélio Laranjeiro error: 327272733b5SNélio Laranjeiro return rte_errno; 328272733b5SNélio Laranjeiro } 329272733b5SNélio Laranjeiro 330272733b5SNélio Laranjeiro 331272733b5SNélio Laranjeiro /** 332272733b5SNélio Laranjeiro * Disable traffic flows configured by control plane 333272733b5SNélio Laranjeiro * 334272733b5SNélio Laranjeiro * @param priv 335272733b5SNélio Laranjeiro * Pointer to Ethernet device private data. 336272733b5SNélio Laranjeiro * @param dev 337272733b5SNélio Laranjeiro * Pointer to Ethernet device structure. 338272733b5SNélio Laranjeiro * 339272733b5SNélio Laranjeiro * @return 340272733b5SNélio Laranjeiro * 0 on success. 341272733b5SNélio Laranjeiro */ 342272733b5SNélio Laranjeiro int 343*56f08e16SNélio Laranjeiro priv_dev_traffic_disable(struct priv *priv, 344*56f08e16SNélio Laranjeiro struct rte_eth_dev *dev __rte_unused) 345272733b5SNélio Laranjeiro { 346272733b5SNélio Laranjeiro priv_flow_flush(priv, &priv->ctrl_flows); 347272733b5SNélio Laranjeiro return 0; 348272733b5SNélio Laranjeiro } 349272733b5SNélio Laranjeiro 350272733b5SNélio Laranjeiro /** 351272733b5SNélio Laranjeiro * Restart traffic flows configured by control plane 352272733b5SNélio Laranjeiro * 353272733b5SNélio Laranjeiro * @param priv 354272733b5SNélio Laranjeiro * Pointer to Ethernet device private data. 355272733b5SNélio Laranjeiro * @param dev 356272733b5SNélio Laranjeiro * Pointer to Ethernet device structure. 357272733b5SNélio Laranjeiro * 358272733b5SNélio Laranjeiro * @return 359272733b5SNélio Laranjeiro * 0 on success. 360272733b5SNélio Laranjeiro */ 361272733b5SNélio Laranjeiro int 362272733b5SNélio Laranjeiro priv_dev_traffic_restart(struct priv *priv, struct rte_eth_dev *dev) 363272733b5SNélio Laranjeiro { 364272733b5SNélio Laranjeiro if (dev->data->dev_started) { 365272733b5SNélio Laranjeiro priv_dev_traffic_disable(priv, dev); 366272733b5SNélio Laranjeiro priv_dev_traffic_enable(priv, dev); 367272733b5SNélio Laranjeiro } 368272733b5SNélio Laranjeiro return 0; 369272733b5SNélio Laranjeiro } 370272733b5SNélio Laranjeiro 371272733b5SNélio Laranjeiro /** 372272733b5SNélio Laranjeiro * Restart traffic flows configured by control plane 373272733b5SNélio Laranjeiro * 374272733b5SNélio Laranjeiro * @param dev 375272733b5SNélio Laranjeiro * Pointer to Ethernet device structure. 376272733b5SNélio Laranjeiro * 377272733b5SNélio Laranjeiro * @return 378272733b5SNélio Laranjeiro * 0 on success. 379272733b5SNélio Laranjeiro */ 380272733b5SNélio Laranjeiro int 381272733b5SNélio Laranjeiro mlx5_traffic_restart(struct rte_eth_dev *dev) 382272733b5SNélio Laranjeiro { 383272733b5SNélio Laranjeiro struct priv *priv = dev->data->dev_private; 384272733b5SNélio Laranjeiro 385272733b5SNélio Laranjeiro priv_lock(priv); 386272733b5SNélio Laranjeiro priv_dev_traffic_restart(priv, dev); 387272733b5SNélio Laranjeiro priv_unlock(priv); 388272733b5SNélio Laranjeiro return 0; 389272733b5SNélio Laranjeiro } 390