Skip to content

Commit

Permalink
net/nfp: fix RSS failed on VXLAN inner layer
Browse files Browse the repository at this point in the history
Before the commit 5126a90
("net/nfp: use offload flag to control VXLAN configuration"),
in the initial logic 'nfp_net_start()' will enable the
NFP_NET_CFG_CTRL_VXLAN flag if hardware has the capability,
'udp_tunnel_port_add()' and 'udp_tunnel_port_del()' just do
the port add and delete action.

But the commit 5126a90
("net/nfp: use offload flag to control VXLAN configuration")
added another limitation of RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO over
the VXLAN inner RSS flag of Tx wrongly, which caused the
NFP_NET_CFG_CTRL_VXLAN cannot be enable, thus 'udp_tunnel_port_add()'
and 'udp_tunnel_port_del()' can not done their works.

This commit fix the problem and do a little of enhancement to the
initial logic, move the logic of enable NFP_NET_CFG_CTRL_VXLAN into the
'udp_tunnel_port_add()', and add the logic of disable
NFP_NET_CFG_CTRL_VXLAN into the 'udp_tunnel_port_del()', thus the whole
solution more complete and easier to understand.

Fixes: 5126a90 ("net/nfp: use offload flag to control VXLAN configuration")
Cc: stable@dpdk.org

Signed-off-by: Long Wu <long.wu@corigine.com>
Reviewed-by: Chaoyong He <chaoyong.he@corigine.com>
Reviewed-by: Peng Zhang <peng.zhang@corigine.com>
  • Loading branch information
wulong2022 authored and ferruhy committed Oct 17, 2024
1 parent 6011b12 commit 79e7b4f
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 33 deletions.
47 changes: 27 additions & 20 deletions drivers/net/nfp/nfp_ethdev.c
Original file line number Diff line number Diff line change
Expand Up @@ -443,13 +443,6 @@ nfp_net_start(struct rte_eth_dev *dev)
update |= NFP_NET_CFG_UPDATE_GEN | NFP_NET_CFG_UPDATE_RING;

txmode = &dev->data->dev_conf.txmode;
/* Enable vxlan */
if ((txmode->offloads & RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO) != 0) {
if ((hw->cap & NFP_NET_CFG_CTRL_VXLAN) != 0) {
new_ctrl |= NFP_NET_CFG_CTRL_VXLAN;
update |= NFP_NET_CFG_UPDATE_VXLAN;
}
}

if ((hw->cap & NFP_NET_CFG_CTRL_RINGCFG) != 0)
new_ctrl |= NFP_NET_CFG_CTRL_RINGCFG;
Expand Down Expand Up @@ -854,11 +847,13 @@ nfp_udp_tunnel_port_add(struct rte_eth_dev *dev,
{
int ret;
uint32_t idx;
uint32_t ctrl;
struct nfp_hw *hw;
uint16_t vxlan_port;
struct nfp_net_hw *hw;
struct nfp_net_hw *net_hw;
enum rte_eth_tunnel_type tnl_type;

hw = dev->data->dev_private;
net_hw = dev->data->dev_private;
vxlan_port = tunnel_udp->udp_port;
tnl_type = tunnel_udp->prot_type;

Expand All @@ -867,21 +862,26 @@ nfp_udp_tunnel_port_add(struct rte_eth_dev *dev,
return -ENOTSUP;
}

ret = nfp_net_find_vxlan_idx(hw, vxlan_port, &idx);
ret = nfp_net_find_vxlan_idx(net_hw, vxlan_port, &idx);
if (ret != 0) {
PMD_DRV_LOG(ERR, "Failed find valid vxlan idx");
return -EINVAL;
}

if (hw->vxlan_usecnt[idx] == 0) {
ret = nfp_net_set_vxlan_port(hw, idx, vxlan_port);
if (net_hw->vxlan_usecnt[idx] == 0) {
hw = &net_hw->super;
ctrl = hw->ctrl | NFP_NET_CFG_CTRL_VXLAN;

ret = nfp_net_set_vxlan_port(net_hw, idx, vxlan_port, ctrl);
if (ret != 0) {
PMD_DRV_LOG(ERR, "Failed set vxlan port");
return -EINVAL;
}

hw->ctrl = ctrl;
}

hw->vxlan_usecnt[idx]++;
net_hw->vxlan_usecnt[idx]++;

return 0;
}
Expand All @@ -892,11 +892,13 @@ nfp_udp_tunnel_port_del(struct rte_eth_dev *dev,
{
int ret;
uint32_t idx;
uint32_t ctrl;
struct nfp_hw *hw;
uint16_t vxlan_port;
struct nfp_net_hw *hw;
struct nfp_net_hw *net_hw;
enum rte_eth_tunnel_type tnl_type;

hw = dev->data->dev_private;
net_hw = dev->data->dev_private;
vxlan_port = tunnel_udp->udp_port;
tnl_type = tunnel_udp->prot_type;

Expand All @@ -905,20 +907,25 @@ nfp_udp_tunnel_port_del(struct rte_eth_dev *dev,
return -ENOTSUP;
}

ret = nfp_net_find_vxlan_idx(hw, vxlan_port, &idx);
if (ret != 0 || hw->vxlan_usecnt[idx] == 0) {
ret = nfp_net_find_vxlan_idx(net_hw, vxlan_port, &idx);
if (ret != 0 || net_hw->vxlan_usecnt[idx] == 0) {
PMD_DRV_LOG(ERR, "Failed find valid vxlan idx");
return -EINVAL;
}

hw->vxlan_usecnt[idx]--;
net_hw->vxlan_usecnt[idx]--;

if (hw->vxlan_usecnt[idx] == 0) {
ret = nfp_net_set_vxlan_port(hw, idx, 0);
if (net_hw->vxlan_usecnt[idx] == 0) {
hw = &net_hw->super;
ctrl = hw->ctrl & ~NFP_NET_CFG_CTRL_VXLAN;

ret = nfp_net_set_vxlan_port(net_hw, idx, 0, ctrl);
if (ret != 0) {
PMD_DRV_LOG(ERR, "Failed set vxlan port");
return -EINVAL;
}

hw->ctrl = ctrl;
}

return 0;
Expand Down
15 changes: 3 additions & 12 deletions drivers/net/nfp/nfp_net_common.c
Original file line number Diff line number Diff line change
Expand Up @@ -2154,9 +2154,9 @@ nfp_net_close_tx_queue(struct rte_eth_dev *dev)
int
nfp_net_set_vxlan_port(struct nfp_net_hw *net_hw,
size_t idx,
uint16_t port)
uint16_t port,
uint32_t ctrl)
{
int ret;
uint32_t i;
struct nfp_hw *hw = &net_hw->super;

Expand All @@ -2172,16 +2172,7 @@ nfp_net_set_vxlan_port(struct nfp_net_hw *net_hw,
(net_hw->vxlan_ports[i + 1] << 16) | net_hw->vxlan_ports[i]);
}

rte_spinlock_lock(&hw->reconfig_lock);

nn_cfg_writel(hw, NFP_NET_CFG_UPDATE, NFP_NET_CFG_UPDATE_VXLAN);
rte_wmb();

ret = nfp_reconfig_real(hw, NFP_NET_CFG_UPDATE_VXLAN);

rte_spinlock_unlock(&hw->reconfig_lock);

return ret;
return nfp_reconfig(hw, ctrl, NFP_NET_CFG_UPDATE_VXLAN);
}

/*
Expand Down
5 changes: 4 additions & 1 deletion drivers/net/nfp/nfp_net_common.h
Original file line number Diff line number Diff line change
Expand Up @@ -345,7 +345,10 @@ void nfp_net_stop_rx_queue(struct rte_eth_dev *dev);
void nfp_net_close_rx_queue(struct rte_eth_dev *dev);
void nfp_net_stop_tx_queue(struct rte_eth_dev *dev);
void nfp_net_close_tx_queue(struct rte_eth_dev *dev);
int nfp_net_set_vxlan_port(struct nfp_net_hw *hw, size_t idx, uint16_t port);
int nfp_net_set_vxlan_port(struct nfp_net_hw *hw,
size_t idx,
uint16_t port,
uint32_t ctrl);
void nfp_net_rx_desc_limits(struct nfp_net_hw_priv *hw_priv,
uint16_t *min_rx_desc,
uint16_t *max_rx_desc);
Expand Down

0 comments on commit 79e7b4f

Please sign in to comment.