* [PATCH v1 00/13] net/sxe2: fix bugs
@ 2026-08-18 2:15 liujie5
2026-08-18 2:15 ` [PATCH v1 01/13] net/sxe2: add Rx queue buffer split fill support liujie5
` (13 more replies)
0 siblings, 14 replies; 278+ messages in thread
From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw)
To: stephen; +Cc: dev, Jie Liu
From: Jie Liu <liujie5@linkdatatechnology.com>
Jie Liu (13):
net/sxe2: add Rx queue buffer split fill support
net/sxe2: update switchdev repr VSI ID display format
net/sxe2: add ACL engine event statistics support
net/sxe2: enhance device cap and res management
net/sxe2: improve representor device initialization
net/sxe2: refactor flow tunnel port handling
net/sxe2: validate IPsec key length against maximum limit
net/sxe2: enhance repr event handling and MP code
net/sxe2: optimize vectorized Tx/Rx path
common/sxe2: allow munmap during kernel reset
net/sxe2: clean up duplicate function declarations
net/sxe2: clean up structure definitions
doc/sxe2: add acl-stat-type parameter documentation
doc/guides/nics/sxe2.rst | 33 +--
drivers/common/sxe2/sxe2_common.c | 5 +-
drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +-
drivers/net/sxe2/sxe2_cmd_chnl.c | 215 +++++++++++++++--
drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +-
drivers/net/sxe2/sxe2_drv_cmd.h | 47 ++--
drivers/net/sxe2/sxe2_dump.c | 10 +-
drivers/net/sxe2/sxe2_ethdev.c | 203 +++++++++-------
drivers/net/sxe2/sxe2_ethdev.h | 38 +--
drivers/net/sxe2/sxe2_ethdev_repr.c | 13 +-
drivers/net/sxe2/sxe2_flow.c | 259 +++++++++++++++++----
drivers/net/sxe2/sxe2_flow.h | 6 +-
drivers/net/sxe2/sxe2_flow_define.h | 13 +-
drivers/net/sxe2/sxe2_flow_parse_action.c | 37 ++-
drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------
drivers/net/sxe2/sxe2_flow_parse_pattern.h | 7 -
drivers/net/sxe2/sxe2_ipsec.c | 5 +
drivers/net/sxe2/sxe2_irq.c | 27 ++-
drivers/net/sxe2/sxe2_mac.c | 10 +-
drivers/net/sxe2/sxe2_mp.c | 59 +++--
drivers/net/sxe2/sxe2_queue.c | 2 +
drivers/net/sxe2/sxe2_queue.h | 7 +-
drivers/net/sxe2/sxe2_rx.c | 5 +-
drivers/net/sxe2/sxe2_security.c | 1 +
drivers/net/sxe2/sxe2_switchdev.c | 12 +-
drivers/net/sxe2/sxe2_tx.c | 42 +++-
drivers/net/sxe2/sxe2_tx.h | 4 +
drivers/net/sxe2/sxe2_txrx.c | 19 +-
drivers/net/sxe2/sxe2_txrx_poll.h | 2 -
drivers/net/sxe2/sxe2_txrx_vec.c | 79 +++----
drivers/net/sxe2/sxe2_txrx_vec.h | 1 +
drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +-
drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------
drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +-
drivers/net/sxe2/sxe2_txrx_vec_neon.c | 218 +++++++++++------
drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +-
drivers/net/sxe2/sxe2_vsi.c | 8 +-
37 files changed, 988 insertions(+), 697 deletions(-)
--
2.52.0
^ permalink raw reply [flat|nested] 278+ messages in thread* [PATCH v1 01/13] net/sxe2: add Rx queue buffer split fill support 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 02/13] net/sxe2: update switchdev repr VSI ID display format liujie5 ` (12 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Implement sxe2_rxq_buf_split_fill function to configure Rx queue buffer split offload. The function validates and sets split parameters based on protocol header type. Supports following split types: - L2: Ether - L3: IPv4, IPv6 - L4: TCP, UDP, SCTP - Tunnel: GRE/NAT - Inner L2/L3/L4 for tunneled packets Sets split_type_mask and header_len (256 bytes) for hardware buffer split configuration. Returns error if protocol header is not configured or unsupported. Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 142 ++++++++++++++++++++++++++++--- 1 file changed, 128 insertions(+), 14 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..9ed5559eff 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,7 +43,7 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) + __sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) @@ -193,6 +192,102 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + int32_t ret = 0; + uint32_t proto_hdr; + + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + ret = -1; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + ret = -1; + } else { + ctxt->hdr_len = 0; + ctxt->split_type_mask = 0; + } +l_end: + return ret; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -226,7 +321,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } @@ -391,7 +496,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -412,6 +517,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) { int32_t ret = 0; struct sxe2_common_device *cdev = adapter->cdev; + struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; struct sxe2_drv_cmd_params param = {0}; struct sxe2_drv_link_info_resp resp = {0}; @@ -425,6 +531,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) } adapter->link_ctxt.speed = resp.speed; adapter->link_ctxt.link_up = resp.status; + (void)sxe2_link_update(dev, 0); l_end: return ret; @@ -447,7 +554,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -467,7 +574,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -668,7 +775,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1532,7 +1639,7 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, [SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U] = SXE2_UDP_TUNNEL_PROTOCOL_GTP_U, [SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE] = SXE2_UDP_TUNNEL_PROTOCOL_NVGRE, }; - struct sxe2_udp_tunnel_cfg tunnel_config = {}; + struct sxe2_udp_tunnel_cfg tunnel_config = {0}; tunnel_config.protocol = flow_proto_to_udp_tunnel_proto[proto]; ret = sxe2_drv_udp_tunnel_get(adapter, &tunnel_config); @@ -1560,8 +1667,10 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; @@ -1569,6 +1678,7 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; +l_end: return ret; } @@ -1591,7 +1701,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); goto l_end; } @@ -1635,7 +1745,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1652,7 +1762,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1666,7 +1776,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1726,10 +1836,14 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + flow->create_err = ret; + goto l_end; + } flow->flow_id = resp.flow_id; flow->create_err = ret; +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 02/13] net/sxe2: update switchdev repr VSI ID display format 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 2026-08-18 2:15 ` [PATCH v1 01/13] net/sxe2: add Rx queue buffer split fill support liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 03/13] net/sxe2: add ACL engine event statistics support liujie5 ` (11 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Update the output format for representor primary VSI ID and backup VSI ID in switchdev dump function. The fields repr_vf_primary_vsi_id and repr_vf_backup_vsi_id should be displayed correctly for better debug visibility. Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 03/13] net/sxe2: add ACL engine event statistics support 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 2026-08-18 2:15 ` [PATCH v1 01/13] net/sxe2: add Rx queue buffer split fill support liujie5 2026-08-18 2:15 ` [PATCH v1 02/13] net/sxe2: update switchdev repr VSI ID display format liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 04/13] net/sxe2: enhance device cap and res management liujie5 ` (10 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for ACL flow engine to track packet hits and bytes. This enables flow aging and traffic monitoring for ACL rules. Implementation includes: - Add acl-stat-type devarg to configure statistics type - Implement sxe2_drv_flow_acl_get_stat_id for stat allocation - Implement sxe2_drv_flow_acl_free_stat for stat cleanup - Implement sxe2_drv_flow_acl_query_stat for stat query - Integrate stat operations into flow create/destroy/query paths Statistics are accumulated in manager context and reported through rte_flow_query() interface with COUNT action. Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 73 +++++++++++++- drivers/net/sxe2/sxe2_cmd_chnl.h | 9 +- drivers/net/sxe2/sxe2_drv_cmd.h | 17 ++++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 25 +++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 111 ++++++++++++++++------ drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 13 +-- drivers/net/sxe2/sxe2_flow_parse_action.c | 19 +++- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 225 insertions(+), 53 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 9ed5559eff..b2dbd4457d 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1914,7 +1914,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; @@ -1943,6 +1943,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_acl_query_stat_req req = { 0 }; + struct sxe2_drv_acl_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..7d75a91061 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -165,7 +165,14 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); + +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..d332d15980 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -668,6 +668,18 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_fc_get_resp { uint8_t rsv[3]; } __rte_packed_end; +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_req { + uint32_t stat_id; + uint32_t stat_ctrl; + uint32_t is_clear; +} __rte_packed_end; + +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_resp { + uint32_t stat_index; + uint64_t stat_hits; + uint64_t stat_bytes; +} __rte_packed_end; + enum sxe2_drv_cmd_module { SXE2_DRV_CMD_MODULE_HANDSHAKE = 0, SXE2_DRV_CMD_MODULE_DEV = 1, @@ -824,6 +836,11 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..3c3e78125d 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -971,11 +972,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -983,19 +984,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1177,13 +1178,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2350,6 +2358,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..7e495e5cb9 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -138,6 +138,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..3cf98dd294 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,26 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1122,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1120,7 +1130,10 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1131,7 +1144,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1143,17 +1156,24 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1170,17 +1190,23 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1197,7 +1223,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1218,7 +1252,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,12 +1382,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1370,15 +1410,15 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1387,5 +1427,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..f56f687dc7 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,19 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..cdd6fcfdcd 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -1037,11 +1037,24 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, if (engine_type == SXE2_FLOW_ENGINE_FNAV) { sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); act_count = action->conf; - flow->action.count.user_id = act_count->id; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) + if (flow->action.count.user_id == 0) { flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; + ++adapter->flow_ctxt.fnav_hw_res.global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++adapter->flow_ctxt.acl_hw_res.global_index; + } action_num[SXE2_FLOW_ACTION_COUNT]++; } else { rte_flow_error_set(error, ENOTSUP, diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 04/13] net/sxe2: enhance device cap and res management 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (2 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 03/13] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 05/13] net/sxe2: improve representor device initialization liujie5 ` (9 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch improves the SXE2 PMD with several key enhancements: - Enhance device info reporting: * Add NULL check for main VSI in dev_infos_get * Add max_mac_addrs field support * Add RSS_HASH offload capability * Conditionally enable QINQ_STRIP/QINQ_INSERT based on port VLAN check * Fill nb_rx_queues and nb_tx_queues fields * Set no_of_elements in buffer_split_supported_hdr_ptypes_get - Unify PCI register operations: * Move SXE2_PCI_REG_WRITE and SXE2_PCI_REG_READ to common header * Replace write-combined write with regular write in pci_map_write_reg * Add resource type validation in dev_pci_res_seg_map - Improve VF representor matching logic: * Remove kernel_repr_id encoding approach * Match PF number and VF ID directly against representor info * Add proper error handling for mismatched representor types - Support multi-port probing: * Loop through nb_ports in eth_pmd_probe * Handle probe failure with proper cleanup - Update resource cleanup order in dev_close: * Adjust uninit sequence to prevent use-after-free * Add NULL check for dev_ops before calling dev_close - Add device type checks in UDP tunnel operations: * Restrict tunnel operations to PF only * Reject operations on VF representors - Store additional device capabilities: * Save port_idx and pf_idx from device capabilities Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 178 +++++++++++++++++++-------------- drivers/net/sxe2/sxe2_ethdev.h | 6 +- drivers/net/sxe2/sxe2_queue.h | 2 - 3 files changed, 107 insertions(+), 79 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 3c3e78125d..ccf04fe1d9 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -95,7 +95,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } @@ -782,6 +787,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; @@ -789,6 +798,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | @@ -800,11 +810,9 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | - RTE_ETH_RX_OFFLOAD_TCP_LRO; + RTE_ETH_RX_OFFLOAD_TCP_LRO | + RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | @@ -850,13 +858,20 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_IPIP_TNL_TSO | RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; + if (sxe2_ipsec_supported(adapter)) { + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; + } if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; - dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; } if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { @@ -909,7 +924,8 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; - + dev_info->nb_rx_queues = dev->data->nb_rx_queues; + dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; dev_info->default_rxportconf.nb_queues = 1; @@ -918,11 +934,8 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->default_txportconf.ring_size = SXE2_RING_SIZE_MIN; dev_info->rx_seg_capa.max_nseg = SXE2_RX_MAX_NSEG; - dev_info->rx_seg_capa.multi_pools = true; - dev_info->rx_seg_capa.offset_allowed = false; - dev_info->rx_seg_capa.offset_align_log2 = false; return 0; @@ -930,7 +943,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -968,6 +981,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes); return ptypes; } @@ -1352,6 +1366,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); @@ -1437,7 +1453,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } @@ -1550,6 +1566,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); @@ -1765,14 +1787,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1783,7 +1804,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } @@ -1936,6 +1956,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1948,12 +1974,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2005,15 +2025,15 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_fc_state_err: (void)sxe2_flow_uninit(dev); init_flow_err: -init_rss_err: sxe2_security_uinit(dev); +init_rss_err: init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: @@ -2035,17 +2055,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); @@ -2068,9 +2086,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); @@ -2143,42 +2163,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx = UINT16_MAX; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2191,15 +2194,30 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num != req_eth_da->ports[port_idx]) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf %u", + adapter->switchdev_info.pf_num, req_eth_da->ports[port_idx]); + rte_errno = EBUSY; + return false; + } + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, @@ -2317,6 +2335,7 @@ static int32_t sxe2_eth_pmd_probe(struct sxe2_common_device *cdev, { struct rte_eth_devargs eth_da = { .nb_ports = 0 }; int32_t ret = 0; + uint16_t port; ret = sxe2_parse_eth_devargs(cdev->dev, ð_da); if (ret != 0) { @@ -2324,7 +2343,18 @@ static int32_t sxe2_eth_pmd_probe(struct sxe2_common_device *cdev, goto l_end; } - ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, 0, kvargs); + if (eth_da.nb_ports > 0) { + for (port = 0; port < eth_da.nb_ports; port++) { + ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, port, kvargs); + if (ret != 0) { + PMD_LOG_ERR(INIT, "sxe2 eth pmd probe failed, ret=%d", ret); + (void)sxe2_eth_pmd_remove(cdev); + goto l_end; + } + } + } else { + ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, 0, kvargs); + } l_end: return ret; diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 7e495e5cb9..cfcb7fcf00 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 @@ -356,6 +353,9 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 05/13] net/sxe2: improve representor device initialization 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (3 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 04/13] net/sxe2: enhance device cap and res management liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 06/13] net/sxe2: refactor flow tunnel port handling liujie5 ` (8 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch enhances the representor device initialization with: - Add statistics initialization in sxe2_repr_dev_init * Call sxe2_stats_init to setup statistics infrastructure * Add proper error handling path for stats init failure - Add representor device naming and NUMA node assignment: * Update device name format to use base device name prefix * Set numa_node from parent device data for proper NUMA locality * Ensures representor devices are allocated on the same NUMA node - Code style improvements: * Align struct member fields in sxe2_adapter for consistency Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 24 ++++++++++++------------ drivers/net/sxe2/sxe2_ethdev_repr.c | 13 +++++++++++-- 2 files changed, 23 insertions(+), 14 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cfcb7fcf00..d0a0f41ceb 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -314,10 +314,10 @@ struct sxe2_fc_state_ctxt { }; struct sxe2_adapter { - struct sxe2_common_device *cdev; - struct sxe2_dev_info dev_info; - struct rte_pci_device *pci_dev; - struct sxe2_repr_private_data *repr_priv_data; + struct sxe2_common_device *cdev; + struct sxe2_dev_info dev_info; + struct rte_pci_device *pci_dev; + struct sxe2_repr_private_data *repr_priv_data; struct sxe2_pci_map_context map_ctxt; struct sxe2_irq_context irq_ctxt; struct sxe2_queue_context q_ctxt; @@ -338,16 +338,16 @@ struct sxe2_adapter { bool rule_started; bool flow_isolated; bool flow_isolate_cfg; - uint16_t dev_port_id; + uint16_t dev_port_id; bool is_dev_repr; - uint64_t cap_flags; + uint64_t cap_flags; enum sxe2_dev_type dev_type; - struct rte_ether_addr mac_addr; - uint8_t port_idx; - uint8_t pf_idx; - uint32_t tx_mode_flags; - uint32_t rx_mode_flags; - uint8_t started; + struct rte_ether_addr mac_addr; + uint8_t port_idx; + uint8_t pf_idx; + uint32_t tx_mode_flags; + uint32_t rx_mode_flags; + uint8_t started; }; #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: @@ -544,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -554,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 06/13] net/sxe2: refactor flow tunnel port handling 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (4 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 05/13] net/sxe2: improve representor device initialization liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 07/13] net/sxe2: validate IPsec key length against maximum limit liujie5 ` (7 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch refactors flow tunnel port handling and adds support for PF bond devices: - Refactor tunnel port functions from pattern module to flow module: * Move sxe2_flow_parse_pattern_ipip from sxe2_flow_parse_pattern.c * Move sxe2_flow_add_udp_tunnel_port from sxe2_flow_parse_pattern.c * Move sxe2_flow_add_tunnel_port from public API to static function * Remove public function declaration from header file * Keep functions internal to flow module for better encapsulation - Add PF bond device support in flow source split processing: * Add bond_member_cnt field to sxe2_adapter structure * Handle SXE2_DEV_T_PF_BOND device type in sxe2_flow_src_split_proc * Populate flow_src_vsi for all bond members - Enhance ACL engine support in flow actions: * Add ACL engine support in flow action checks * Allow PASSTHRU action for ACL engine Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 144 ++++++++++++++++++++- drivers/net/sxe2/sxe2_flow_parse_action.c | 18 ++- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 7 - 5 files changed, 151 insertions(+), 132 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index d0a0f41ceb..36f4cc9353 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -340,6 +340,7 @@ struct sxe2_adapter { bool flow_isolate_cfg; uint16_t dev_port_id; bool is_dev_repr; + uint16_t bond_member_cnt; uint64_t cap_flags; enum sxe2_dev_type dev_type; struct rte_ether_addr mac_addr; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 3cf98dd294..af85cb0d2b 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -285,14 +285,16 @@ static int32_t sxe2_flow_meta_proc(struct rte_eth_dev *dev, attr, "Only support priority 0."); ret = -rte_errno; goto l_end; - } else if (!adapter->switchdev_info.is_switchdev) { - PMD_LOG_ERR(DRV, "Legacy mode only support priority 0."); - rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ATTR_PRIORITY, - attr, "Legacy mode only priority 0."); - ret = -rte_errno; - goto l_end; } else { - flow->meta.flow_prio = attr->priority; + if (!adapter->switchdev_info.is_switchdev) { + PMD_LOG_ERR(DRV, "Legacy mode only support priority 0."); + rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ATTR_PRIORITY, + attr, "Legacy mode only priority 0."); + ret = -rte_errno; + goto l_end; + } else { + flow->meta.flow_prio = attr->priority; + } } } @@ -347,6 +349,21 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][idx] = UINT16_MAX; } + if (adapter->dev_type == SXE2_DEV_T_PF_BOND) { + flow_bond_num = adapter->bond_member_cnt; + for (idx = 0; idx < flow_bond_num; idx++) { + flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][idx] = + adapter->vsi_ctxt.bond_member_dpdk_vsi_id[idx]; + flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][idx] = + adapter->vsi_ctxt.bond_member_kernel_vsi_id[idx]; + } + } else { + flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = + adapter->vsi_ctxt.dpdk_vsi_id; + flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = + adapter->vsi_ctxt.kernel_vsi_id; + } + flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = adapter->vsi_ctxt.dpdk_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = adapter->vsi_ctxt.kernel_vsi_id; if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV || @@ -550,6 +567,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index cdd6fcfdcd..867d90ae1d 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; @@ -953,7 +959,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -988,7 +995,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..6872a767dd 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -36,11 +36,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, const struct rte_flow_item patterns[], struct rte_flow_error *error, struct sxe2_flow *flow); - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 07/13] net/sxe2: validate IPsec key length against maximum limit 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (5 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 06/13] net/sxe2: refactor flow tunnel port handling liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 08/13] net/sxe2: enhance repr event handling and MP code liujie5 ` (6 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Add validation check in sxe2_security_valid_key to ensure source key length does not exceed SXE2_IPSEC_MAX_KEY_LEN. This prevents potential buffer overflows when processing security keys that are longer than the supported maximum length. Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ipsec.c | 5 +++++ drivers/net/sxe2/sxe2_security.c | 1 + 2 files changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ipsec.c b/drivers/net/sxe2/sxe2_ipsec.c index e783a51b85..622fd1adfe 100644 --- a/drivers/net/sxe2/sxe2_ipsec.c +++ b/drivers/net/sxe2/sxe2_ipsec.c @@ -254,6 +254,11 @@ static bool sxe2_security_valid_key(uint16_t src_key, uint16_t max_key, goto l_end; } + if (src_key > SXE2_IPSEC_MAX_KEY_LEN) { + is_valid = false; + goto l_end; + } + is_valid = true; l_end: diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 08/13] net/sxe2: enhance repr event handling and MP code 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (6 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 07/13] net/sxe2: validate IPsec key length against maximum limit liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 09/13] net/sxe2: optimize vectorized Tx/Rx path liujie5 ` (5 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch improves representor link state event handling and refactors multi-process message processing: - Add representor link state event propagation: * Propagate LSC events to all VF representors when PF link changes * Get link status and trigger callbacks for each representor * Only process in primary process for representor callbacks * Change OICR log format to hexadecimal for better readability - Refactor primary process message handling: * Extract work logic to sxe2_mp_do_primary_work helper function * Use parameter copy to avoid side effects on original message * Simplify reply construction in primary handler - Simplify statistics interface: * Remove qstats parameter from sxe2_mp_req_get_stats * Remove qstats copy from shared memory * Update function signature in header and implementation - Improve error handling and cleanup: * Change error return from EINVAL to ENODATA when no response * Simplify sxe2_link_update_init error path * Remove unnecessary goto statements and cleanup labels * Remove extra whitespace Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 27 +++++++++++++---- drivers/net/sxe2/sxe2_mac.c | 10 ++----- drivers/net/sxe2/sxe2_mp.c | 59 +++++++++++++++++++++---------------- 3 files changed, 58 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..7fe500b229 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint8_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); @@ -863,12 +881,11 @@ static void sxe2_rxq_intr_unregister(struct rte_eth_dev *dev) (void)sxe2_drv_dev_rxq_irq_set(adapter->cdev, i, &efd, 1); sxe2_rxq_intr_efd_free(irq_ctxt->rxq_event_fd[i]); } + rte_free(irq_ctxt->rxq_event_fd); + irq_ctxt->rxq_event_fd = NULL; } - rte_free(irq_ctxt->rxq_event_fd); - irq_ctxt->rxq_event_fd = NULL; rte_intr_vec_list_free(intr_handle); - rte_intr_nb_efd_set(intr_handle, 0); rte_intr_max_intr_set(intr_handle, 0); } diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..e65c578262 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,20 +448,14 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - - (void)sxe2_link_update(dev, 0); -l_end: return ret; } + int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) { struct rte_eth_link new_link; diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 09/13] net/sxe2: optimize vectorized Tx/Rx path 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (7 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 08/13] net/sxe2: enhance repr event handling and MP code liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 10/13] common/sxe2: allow munmap during kernel reset liujie5 ` (4 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch optimizes vectorized packet processing with improved buffer management and unified buffer structure: - Introduce unified Tx buffer structure: * Add union in sxe2_tx_queue for buffer_ring/buffer_ring_vec * Use sxe2_tx_buffer_vec for vectorized Tx path * Eliminate runtime type checking and branching - Refactor Tx queue reset operations: * Extract desc ring reset to sxe2_tx_queue_desc_ring_reset * Add sxe2_tx_queue_reset_vec for vectorized queues * Simplify buffer initialization in vector mode - Optimize Tx vector path mbuf release: * Remove conditional AVX512 branching * Use direct buffer_vec access without casting * Simplify loop logic with consistent pattern * Remove NULL checks after initialization validation - Refactor Tx queue operations: * Export sxe2_tx_buffer_ring_free as public API * Add sxe2_tx_vec_ops_get() for vector operations * Use operation table instead of direct function calls - Improve VSI management: * Initialize other_vsi_list before main VSI creation * Ignore -EPERM errors when destroying VSI in uninit * Set main_vsi to NULL after successful destroy * Prevent dangling pointer references - Enhance Tx mode function selection: * Use rte_eth_tx_pkt_prepare_dummy for vectorized paths * Split NEON simple/offload mode selection logic * Clean up conditional compilation structure Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_rx.c | 5 +- drivers/net/sxe2/sxe2_switchdev.c | 8 +- drivers/net/sxe2/sxe2_tx.c | 42 +++-- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 19 ++- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 79 +++------ drivers/net/sxe2/sxe2_txrx_vec.h | 1 + drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +-------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 218 +++++++++++++++--------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 8 +- 15 files changed, 251 insertions(+), 302 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..6340ed933a 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) @@ -550,7 +551,7 @@ void __rte_cold sxe2_rxqs_all_stop(struct rte_eth_dev *dev) static int32_t sxe2_monitor_callback(const uint64_t value, const uint64_t arg[RTE_POWER_MONITOR_OPAQUE_SZ] __rte_unused) { - const uint64_t dd_state = rte_cpu_to_le_64(SXE2_RX_DESC_STATUS_DD_MASK); + const uint64_t dd_state = rte_cpu_to_le_64(SXE2_RX_DESC_STATUS_DD_SHIFT); return (value & dd_state) == dd_state ? -1 : 0; } diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..374cc4e223 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -316,13 +316,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - - repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - + repr_priv_data->repr_vf_vsi_id = repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; l_free: diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..d27d2ce630 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,25 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; - } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +586,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..05940c8cb5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,19 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void) +{ + static const struct sxe2_txq_ops ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, + }; + + return ops; +} + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -157,67 +170,28 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - dev = &rte_eth_devices[txq->port_id]; - - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; - } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } + for ( ; i < txq->next_use; ++i) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } @@ -233,7 +207,8 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); continue; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops_get(); + txq->ops.queue_reset(txq); } return ret; } diff --git a/drivers/net/sxe2/sxe2_txrx_vec.h b/drivers/net/sxe2/sxe2_txrx_vec.h index c139aed776..b9bc4f9c27 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.h +++ b/drivers/net/sxe2/sxe2_txrx_vec.h @@ -89,6 +89,7 @@ uint16_t sxe2_rx_pkts_scattered_vec_neon_offload(void *rx_queue, struct rte_mbuf uint16_t sxe2_tx_pkts_vec_neon_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); #endif +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void); int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev); int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..6e0bdce278 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,12 +34,57 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,18 +104,26 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -82,14 +135,23 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; @@ -150,22 +212,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -208,9 +272,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -267,23 +332,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -442,25 +490,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -480,7 +542,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -515,55 +578,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -587,12 +643,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..ba4cc7414e 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -230,7 +230,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +283,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -357,4 +358,5 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 10/13] common/sxe2: allow munmap during kernel reset 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (8 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 09/13] net/sxe2: optimize vectorized Tx/Rx path liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 11/13] net/sxe2: clean up duplicate function declarations liujie5 ` (3 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This patch improves error handling and resource management: - Add NULL pointer protection in driver remove path: * Check cdrv and cdrv->remove before calling remove function * Prevent NULL pointer dereference in sxe2_classes_driver_remove * Return SXE2_SUCCESS if no driver or remove handler exists - Allow memory unmap during kernel reset: * Remove kernel_reset restriction in sxe2_drv_dev_munmap * Enable cleanup operations even when kernel has been reset Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 5 ++++- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..3f60b2be11 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,11 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; - return cdrv->remove(cdev); + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 11/13] net/sxe2: clean up duplicate function declarations 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (9 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 10/13] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 12/13] net/sxe2: clean up structure definitions liujie5 ` (2 subsequent siblings) 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This commit removes duplicate function declarations in the sxe2 driver header files. - Remove duplicate sxe2_drv_promisc_config declaration in sxe2_cmd_chnl.h - Remove duplicate sxe2_drv_vsi_info_get declaration in sxe2_cmd_chnl.h - Remove duplicate sxe2_drv_mac_link_status_get declaration in sxe2_cmd_chnl.h - Remove duplicate sxe2_drv_rxq_mapping_set declaration in sxe2_cmd_chnl.h - Remove duplicate sxe2_dev_pci_seg_unmap declaration in sxe2_ethdev.h Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- 2 files changed, 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 7d75a91061..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 36f4cc9353..b43030deab 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -387,8 +387,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 12/13] net/sxe2: clean up structure definitions 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (10 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 11/13] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 2026-08-18 14:22 ` [PATCH v1 00/13] net/sxe2: fix bugs Stephen Hemminger 13 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This commit removes packed attributes and unused reserved fields from structure definitions in the sxe2 driver header file. - Remove packed attributes and rsv[2] field from sxe2_tm_res structure - Remove packed attributes from sxe2_tm_info structure - Remove packed attributes from sxe2_txq_map_info structure - Remove packed attributes from sxe2_rxq_map_info structure - Remove packed attributes from sxe2_queue_map_info structure - Remove packed attributes from sxe2_drv_sfp_req structure - Remove packed attributes from sxe2_drv_sfp_resp structure - Remove unused rsv[3] field from sxe2_drv_link_info_resp structure Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 30 ++++++++++++++---------------- 1 file changed, 14 insertions(+), 16 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index d332d15980..297bdca820 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,18 +347,17 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { uint16_t parent_teid; @@ -526,24 +524,24 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_mac_stats_resp { uint64_t prio_xon_2_xoff[SXE2_MAX_USER_PRIORITY]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_txq_map_info { +struct sxe2_txq_map_info { uint32_t txq_lan_pkt_cnt; uint32_t txq_lan_byte_cnt; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_rxq_map_info { +struct sxe2_rxq_map_info { uint64_t rxq_lan_in_pkt_cnt; uint64_t rxq_lan_in_byte_cnt; uint64_t rxq_fd_in_pkt_cnt; uint64_t rxq_mng_in_pkt_cnt; uint64_t rxq_mng_in_byte_cnt; uint64_t rxq_mng_out_pkt_cnt; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_queue_map_info { +struct sxe2_queue_map_info { struct sxe2_rxq_map_info rxq_stats_map_info[SXE2_RXQ_STATS_MAP_MAX_NUM]; struct sxe2_txq_map_info txq_stats_map_info[SXE2_TXQ_STATS_MAP_MAX_NUM]; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_drv_rx_map_req { uint16_t queue_id; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (11 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 12/13] net/sxe2: clean up structure definitions liujie5 @ 2026-08-18 2:15 ` liujie5 2026-08-26 8:53 ` [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes liujie5 ` (51 more replies) 2026-08-18 14:22 ` [PATCH v1 00/13] net/sxe2: fix bugs Stephen Hemminger 13 siblings, 52 replies; 278+ messages in thread From: liujie5 @ 2026-08-18 2:15 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This commit adds documentation for the acl-stat-type parameter which controls ACL statistics type used for ACL rule hit counting. - 1: Only count the number of packets - 2: Only count the number of bytes - 3: Count both packets and bytes (default) Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 33 ++++++++++----------------------- 1 file changed, 10 insertions(+), 23 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..008d944391 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,29 +98,16 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL statistics type + used for ACL rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). - ``no-sched-mode`` parameter [int] -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 @ 2026-08-26 8:53 ` liujie5 2026-08-26 17:07 ` Stephen Hemminger 2026-08-26 8:53 ` [PATCH v3 01/51] common/sxe2: fix null pointer in class driver remove liujie5 ` (50 subsequent siblings) 51 siblings, 1 reply; 278+ messages in thread From: liujie5 @ 2026-08-26 8:53 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> This series adds the Stars SXE2 (Wuxi Stars Micro System) Ethernet driver, including the common driver (drivers/common/sxe2), the net driver (drivers/net/sxe2), and its documentation. The driver supports: - Legacy and switchdev modes with VF representors - Scalar and vectorized (SSE/AVX2/AVX512/NEON) Rx/Tx paths - FNAV and ACL flow engines with per-flow statistics - RSS, QinQ, IPsec, Traffic Management and multi-process support In addition to the driver functionality, the series fixes a number of correctness issues found during review, including a security context leak in the device init error path, a NULL dereference in the vectorized Tx mbuf release path, an out-of-bounds representor ID access, and a representor LSC loop counter type mismatch. The command channel log messages and ioctl channel handling are also aligned with the reference implementation. This is v3 of the series, incorporating review feedback. All patches build independently and no ABI changes are introduced. Jie Liu (51): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore pf and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: validate IPsec key length against maximum limit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC and queue counts in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: probe all requested PF ports net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: guard Rx queue event FD free in unregister net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in udp tunnel port add net/sxe2: align flow meta proc priority handling with V3 net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow id assignment on filter add failure net/sxe2: fix command channel log messages net/sxe2: align command structs with historical kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-sw-stats parameter documentation net/sxe2: harden ACL flow count resource handling net/sxe2: fix device init and representor matching issues net/sxe2: use correct loop counter type for representor LSC net/sxe2: restore NULL check in vectorized Tx mbuf release net/sxe2: simplify Rx queue buffer split fill helper doc/guides/nics/sxe2.rst | 58 +---- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 18 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 200 +++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 45 ++-- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 202 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 13 +- drivers/net/sxe2/sxe2_flow.c | 250 +++++++++++++++++---- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 37 ++- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_ipsec.c | 5 + drivers/net/sxe2/sxe2_irq.c | 27 ++- drivers/net/sxe2/sxe2_mac.c | 9 +- drivers/net/sxe2/sxe2_mp.c | 59 ++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 16 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 19 +- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 73 +++--- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +---------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 +++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 8 +- 37 files changed, 964 insertions(+), 702 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* Re: [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes 2026-08-26 8:53 ` [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes liujie5 @ 2026-08-26 17:07 ` Stephen Hemminger 0 siblings, 0 replies; 278+ messages in thread From: Stephen Hemminger @ 2026-08-26 17:07 UTC (permalink / raw) To: liujie5; +Cc: dev On Wed, 26 Aug 2026 16:53:32 +0800 liujie5@linkdatatechnology.com wrote: > From: Jie Liu <liujie5@linkdatatechnology.com> > > This series adds the Stars SXE2 (Wuxi Stars Micro System) Ethernet > driver, including the common driver (drivers/common/sxe2), the net > driver (drivers/net/sxe2), and its documentation. > > The driver supports: > - Legacy and switchdev modes with VF representors > - Scalar and vectorized (SSE/AVX2/AVX512/NEON) Rx/Tx paths > - FNAV and ACL flow engines with per-flow statistics > - RSS, QinQ, IPsec, Traffic Management and multi-process support > > In addition to the driver functionality, the series fixes a number of > correctness issues found during review, including a security context > leak in the device init error path, a NULL dereference in the > vectorized Tx mbuf release path, an out-of-bounds representor ID > access, and a representor LSC loop counter type mismatch. The command > channel log messages and ioctl channel handling are also aligned with > the reference implementation. > > This is v3 of the series, incorporating review feedback. All patches > build independently and no ABI changes are introduced. Although I appreciate having each part broken into a patch for review; this large a series gets a little hard to review. You are posting large series where one patch is fixing a bug which was introduced by an earlier patch. That is a good way to do development but is not best practice for final submission. Please consolidate and reorder patches so that each patch builds, and after each patch there are no new bugs. The more verbose (sorry) AI review highlights this. Findings below come from applying the series and reading the resulting source. Numbers are the v3 patch numbers. Patches that fix earlier patches in the same series --------------------------------------------------- 09/51 fixed by 49/51 uint8_t vf_id vs uint16_t nb_repr_vf 15/51 fixed by 48/51 no_of_elements counts the terminator 22/51 fixed by 48/51 init_rss_err label placement 23/51 fixed by 48/51 PF match: all ports vs any port 27/51 fixed by 47/51 stat_index truncation, list handling 31/51 fixed by 50/51 NULL check in vec Tx mbuf release 40/51 fixed by 51/51 sxe2_rxq_buf_split_fill rewritten Please squash each fix into the patch that introduced the bug. 48/51 mixes three unrelated fixes, so split it first. Errors ------ 24/51 probe all requested PF ports sxe2_eth_pmd_probe_pf() has "uint16_t owner_id __rte_unused". The new loop calls it N times with nothing varying. The function calls rte_eth_dev_pci_allocate(pci_dev, ...), which derives the port name from the PCI device, so iteration 2 fails with -ENOMEM. The error path then calls sxe2_eth_pmd_remove(cdev), destroying the port that did probe. Multi-port devargs go from working to failing. Use owner_id, or drop the patch. 33/51 fix RSS action attribute validation sxe2_flow_check_rss_action_attr() starts with "int32_t ret = ENOTSUP" (no minus), so the three new goto l_end paths return a positive errno. The default: case above returns -EINVAL. Use -ENOTSUP. 44/51 align command structs with historical kernel layout Removing __rte_packed_begin moves fields in wire structures: sxe2_tm_add_mid_msg info offset 3 -> 4 sxe2_tm_add_queue_msg info offset 5 -> 8 sxe2_tm_res size 4 -> 2 The commit says members are kept as-is, but offsets change. If these are the offsets firmware expects, put the numbers in the commit message. Otherwise this breaks TM commands. 46/51 remove drv-sw-stats parameter documentation Removing the drv-sw-stats devarg text is right, the devarg is gone. Removing the "Receive Software Statistics" section is not: sxe2_stats.c still registers rx_sw_unicast_packets, rx_sw_broadcast_packets, rx_sw_multicast_packets, rx_sw_drop_packets and rx_sw_drop_bytes, and sxe2_rx_sw_stats_update() still runs. Keep that section, or remove the xstats too. Warnings -------- Tags 20 patches have Cc: stable with no Fixes: tag (05/51, and 33/51 through 51/51). sxe2 shipped in 26.07, so stable is correct, but each needs a Fixes: line. Seven Fixes: hashes are 10 characters; DPDK requires 12. All resolve to real commits: 635084db5d -> 635084db5d57 ac60f302cb -> ac60f302cbef 66a10eb60e -> 66a10eb60ebe d8e4e075ac -> d8e4e075acb4 83866f8d76 -> 83866f8d7638 8cebf80f1e -> 8cebf80f1eda a2b79a9351 -> a2b79a93515e 17/51, 30/51 and 39/51 are refactors carrying Fixes: and Cc: stable. They are not bug fixes; drop the tags. 35/51 has no functional change (else if -> nested else { if }). Please drop the patch. Commit message does not match the diff 31/51 describes a buffer ring union and a rename. It also removes #ifndef SXE2_TEST from the AVX512 file, deletes the AVX512 bulk free path, rewrites the NEON Rx path (ptype extraction, staterr, DD counting, shuffle masks) and adds sxe2_tx_desc_fill_4_neon_simple(). It also drops the per-load rte_atomic_thread_fence() calls in the NEON Rx loop. The result matches the ixgbe/i40e NEON idiom and looks correct, but a fast path memory ordering change must be described. This is four or more patches. 27/51 also sets rxq->fnav_enable in sxe2_queue.c, which is unrelated to ACL statistics. 32/51 bundles four changes: tx_pkt_prepare_dummy, the NEON simple/offload split, two debug logs, and the rx_free_thresh default. Other 27/51 is a new feature (acl-stat-type devarg) inside a fix series and has no release notes. No patch in the series touches doc/guides/rel_notes/. 15/51 sets RTE_ETH_RX_OFFLOAD_RSS_HASH twice: unconditionally, then again under SXE2_DEV_CAPS_OFFLOAD_RSS. One is dead. The same patch moves the PTP block below the IPsec block with no effect. 14/51 sets dev_info->nb_rx_queues and nb_tx_queues, but rte_eth_dev_info_get() overwrites both right after the PMD callback (lib/ethdev/rte_ethdev.c:4146). Keep the max_mac_addrs part, drop the queue counts. Info ---- 08/51 "vf" is passed as a %s argument; put it in the format string. Keying the name on cdev->dev->name means two PF ports on one PCI function would collide. 23/51 port_idx = UINT16_MAX is overwritten by the for loop. 25/51 rename left "sxe2_fnav_cid_mgr" in rte_zmalloc() and "sxe2vf_fnav_cid_mgr" in a log message. 27/51 the ACL devarg is range checked against SXE2_FNAV_STAT_ENA_*, and reuses the fnav req/resp structs. 31/51 continuation lines in sxe2_rx_desc_ptype_fill_neon() use tabs for alignment. DPDK uses tabs to indent and spaces to align. 32/51 0x%016x on a uint32_t is misleading. 36/51 sxe2_drv_mac_link_status_get() now reaches into rte_eth_devices[] and calls sxe2_link_update() from the command channel. It is safe, but it inverts layering. sxe2.ini lists only x86-32 and x86-64, although sxe2_txrx_vec_neon.c is built on arm. Pre-existing, but this series reworks NEON heavily. Several commit messages justify a change as "matching the V3 implementation". Reviewers cannot see V3. Please state what the code should do and why. ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v3 01/51] common/sxe2: fix null pointer in class driver remove 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 2026-08-26 8:53 ` [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes liujie5 @ 2026-08-26 8:53 ` liujie5 2026-08-26 8:53 ` [PATCH v3 02/51] common/sxe2: allow munmap during kernel reset liujie5 ` (49 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:53 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d76 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 02/51] common/sxe2: allow munmap during kernel reset 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 2026-08-26 8:53 ` [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-26 8:53 ` [PATCH v3 01/51] common/sxe2: fix null pointer in class driver remove liujie5 @ 2026-08-26 8:53 ` liujie5 2026-08-26 8:53 ` [PATCH v3 03/51] net/sxe2: fix VF PCI device ID liujie5 ` (48 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:53 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60e ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 03/51] net/sxe2: fix VF PCI device ID 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (2 preceding siblings ...) 2026-08-26 8:53 ` [PATCH v3 02/51] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-26 8:53 ` liujie5 2026-08-26 8:54 ` [PATCH v3 04/51] net/sxe2: fix MSIX register width in PF map table liujie5 ` (47 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:53 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075ac ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 04/51] net/sxe2: fix MSIX register width in PF map table 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (3 preceding siblings ...) 2026-08-26 8:53 ` [PATCH v3 03/51] net/sxe2: fix VF PCI device ID liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 05/51] net/sxe2: restore pf and port index caps assignment liujie5 ` (46 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60e ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 05/51] net/sxe2: restore pf and port index caps assignment 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (4 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 04/51] net/sxe2: fix MSIX register width in PF map table liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 06/51] net/sxe2: fix VSI lifecycle management liujie5 ` (45 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 06/51] net/sxe2: fix VSI lifecycle management 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (5 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 05/51] net/sxe2: restore pf and port index caps assignment liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 07/51] net/sxe2: initialize stats in representor device init liujie5 ` (44 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..ba4cc7414e 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -230,7 +230,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +283,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -357,4 +358,5 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 07/51] net/sxe2: initialize stats in representor device init 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (6 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 06/51] net/sxe2: fix VSI lifecycle management liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 08/51] net/sxe2: use base device name for representor naming liujie5 ` (43 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 08/51] net/sxe2: use base device name for representor naming 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (7 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 07/51] net/sxe2: initialize stats in representor device init liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 09/51] net/sxe2: propagate LSC event to VF representors liujie5 ` (42 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 09/51] net/sxe2: propagate LSC event to VF representors 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (8 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 08/51] net/sxe2: use base device name for representor naming liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 10/51] net/sxe2: validate IPsec key length against maximum limit liujie5 ` (41 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..53d49a4246 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint8_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 10/51] net/sxe2: validate IPsec key length against maximum limit 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (9 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 09/51] net/sxe2: propagate LSC event to VF representors liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 11/51] net/sxe2: rename representor VSI ID fields liujie5 ` (40 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add validation in sxe2_security_valid_key to ensure the source key length does not exceed SXE2_IPSEC_MAX_KEY_LEN, preventing potential buffer overflows when processing keys longer than the supported maximum. Also clear the security context pointer after releasing the security session during uninit. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ipsec.c | 5 +++++ drivers/net/sxe2/sxe2_security.c | 1 + 2 files changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ipsec.c b/drivers/net/sxe2/sxe2_ipsec.c index e783a51b85..622fd1adfe 100644 --- a/drivers/net/sxe2/sxe2_ipsec.c +++ b/drivers/net/sxe2/sxe2_ipsec.c @@ -254,6 +254,11 @@ static bool sxe2_security_valid_key(uint16_t src_key, uint16_t max_key, goto l_end; } + if (src_key > SXE2_IPSEC_MAX_KEY_LEN) { + is_valid = false; + goto l_end; + } + is_valid = true; l_end: diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 11/51] net/sxe2: rename representor VSI ID fields 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (10 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 10/51] net/sxe2: validate IPsec key length against maximum limit liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 12/51] net/sxe2: clean up duplicate function declarations liujie5 ` (39 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 12/51] net/sxe2: clean up duplicate function declarations 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (11 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 11/51] net/sxe2: rename representor VSI ID fields liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:54 ` [PATCH v3 13/51] net/sxe2: fix null VSI dereference in device info liujie5 ` (38 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 13/51] net/sxe2: fix null VSI dereference in device info 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (12 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 12/51] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-26 8:54 ` liujie5 2026-08-26 8:55 ` [PATCH v3 14/51] net/sxe2: fill MAC and queue counts " liujie5 ` (37 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:54 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075ac ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 14/51] net/sxe2: fill MAC and queue counts in device info 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (13 preceding siblings ...) 2026-08-26 8:54 ` [PATCH v3 13/51] net/sxe2: fix null VSI dereference in device info liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 15/51] net/sxe2: fix QinQ and RSS offload capability report liujie5 ` (36 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fill max_mac_addrs, nb_rx_queues and nb_tx_queues in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses and the queue counts. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85dee6b2c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | @@ -912,6 +913,8 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; + dev_info->nb_rx_queues = dev->data->nb_rx_queues; + dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 15/51] net/sxe2: fix QinQ and RSS offload capability report 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (14 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 14/51] net/sxe2: fill MAC and queue counts " liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 16/51] net/sxe2: use regular write for mapped registers liujie5 ` (35 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Advertise RTE_ETH_RX_OFFLOAD_RSS_HASH unconditionally and report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a9351 ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85dee6b2c..a8e16cdd0a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,11 +804,9 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | - RTE_ETH_RX_OFFLOAD_TCP_LRO; + RTE_ETH_RX_OFFLOAD_TCP_LRO | + RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | @@ -855,14 +853,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -936,7 +942,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -974,6 +980,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes); return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 16/51] net/sxe2: use regular write for mapped registers 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (15 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 15/51] net/sxe2: fix QinQ and RSS offload capability report liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 17/51] net/sxe2: move PCI register read macro to common header liujie5 ` (34 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1e ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index a8e16cdd0a..09f5daa715 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1443,7 +1443,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 17/51] net/sxe2: move PCI register read macro to common header 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (16 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 16/51] net/sxe2: use regular write for mapped registers liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 18/51] net/sxe2: validate PCI map resource type liujie5 ` (33 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Fixes: d8e4e075ac ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 18/51] net/sxe2: validate PCI map resource type 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (17 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 17/51] net/sxe2: move PCI register read macro to common header liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 19/51] net/sxe2: guard PCI BAR unmap when not initialized liujie5 ` (32 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60e ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 09f5daa715..f76d4db6f7 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1556,6 +1556,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 19/51] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (18 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 18/51] net/sxe2: validate PCI map resource type liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 20/51] net/sxe2: fix null dereference in dev uninit liujie5 ` (31 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60e ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index f76d4db6f7..7e3eb6432c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1777,14 +1777,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1795,7 +1794,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 20/51] net/sxe2: fix null dereference in dev uninit 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (19 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 19/51] net/sxe2: guard PCI BAR unmap when not initialized liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 21/51] net/sxe2: fix duplicated cleanup in dev close liujie5 ` (30 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7e3eb6432c..575ad299f1 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2078,9 +2078,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 21/51] net/sxe2: fix duplicated cleanup in dev close 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (20 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 20/51] net/sxe2: fix null dereference in dev uninit liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 22/51] net/sxe2: align dev init and cleanup order liujie5 ` (29 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_close() calls sxe2_switchdev_uninit() and sxe2_dev_pci_map_uinit() twice, and releases resources in an order that does not match the initialization sequence. Remove the duplicated calls and align the teardown order with the device init order. Fixes: 8cebf80f1e ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 575ad299f1..ce1e1cae34 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2045,17 +2045,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 22/51] net/sxe2: align dev init and cleanup order 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (21 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 21/51] net/sxe2: fix duplicated cleanup in dev close liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 23/51] net/sxe2: simplify switchdev representor matching liujie5 ` (28 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_eth_init() to be called before sxe2_sw_init() and rearrange the error cleanup labels so that resources are torn down in the reverse order of initialization. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ce1e1cae34..7787f5435e 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1946,6 +1946,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1958,12 +1964,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2015,15 +2015,15 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_fc_state_err: (void)sxe2_flow_uninit(dev); init_flow_err: -init_rss_err: sxe2_security_uinit(dev); +init_rss_err: init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 23/51] net/sxe2: simplify switchdev representor matching 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (22 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 22/51] net/sxe2: align dev init and cleanup order liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:55 ` [PATCH v3 24/51] net/sxe2: probe all requested PF ports liujie5 ` (27 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_match() encodes the kernel representor ID and compares it against each requested port, which is fragile. Match the PF number and VF ID directly against the switchdev representor info instead, and drop the sxe2_switchdev_repr_id_encode_get() helper. Fixes: 635084db5d ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 68 +++++++++++++++++----------------- drivers/net/sxe2/sxe2_ethdev.h | 3 -- 2 files changed, 33 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7787f5435e..1dd10cd515 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2153,42 +2153,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx = UINT16_MAX; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2201,15 +2184,30 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num != req_eth_da->ports[port_idx]) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf %u", + adapter->switchdev_info.pf_num, req_eth_da->ports[port_idx]); + rte_errno = EBUSY; + return false; + } + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index f2557b28c3..e818578319 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 24/51] net/sxe2: probe all requested PF ports 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (23 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 23/51] net/sxe2: simplify switchdev representor matching liujie5 @ 2026-08-26 8:55 ` liujie5 2026-08-26 8:56 ` [PATCH v3 25/51] net/sxe2: rename fnav cid manager symbols to flow liujie5 ` (26 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:55 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_eth_pmd_probe() always probes a single PF port (index 0) even when multiple ports are requested in the device arguments, so additional PF ports are never created. Loop over eth_da.nb_ports and probe each requested port, falling back to a single probe when no ports are specified. Fixes: d8e4e075ac ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 1dd10cd515..8e3afd6eed 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2325,6 +2325,7 @@ static int32_t sxe2_eth_pmd_probe(struct sxe2_common_device *cdev, { struct rte_eth_devargs eth_da = { .nb_ports = 0 }; int32_t ret = 0; + uint16_t port; ret = sxe2_parse_eth_devargs(cdev->dev, ð_da); if (ret != 0) { @@ -2332,7 +2333,18 @@ static int32_t sxe2_eth_pmd_probe(struct sxe2_common_device *cdev, goto l_end; } - ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, 0, kvargs); + if (eth_da.nb_ports > 0) { + for (port = 0; port < eth_da.nb_ports; port++) { + ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, port, kvargs); + if (ret != 0) { + PMD_LOG_ERR(INIT, "sxe2 eth pmd probe failed, ret=%d", ret); + (void)sxe2_eth_pmd_remove(cdev); + goto l_end; + } + } + } else { + ret = sxe2_eth_pmd_probe_pf(cdev, ð_da, 0, kvargs); + } l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 25/51] net/sxe2: rename fnav cid manager symbols to flow 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (24 preceding siblings ...) 2026-08-26 8:55 ` [PATCH v3 24/51] net/sxe2: probe all requested PF ports liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 26/51] net/sxe2: move tunnel port helpers into flow module liujie5 ` (25 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename the sxe2_fnav_cid_mgr, sxe2_fnav_cid_mgr_list_t, sxe2_fnav_count_resource and sxe2_fnav_get_filter_cid symbols to the sxe2_flow_* prefix for consistency with the flow module naming. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 +- drivers/net/sxe2/sxe2_cmd_chnl.h | 2 +- drivers/net/sxe2/sxe2_flow.c | 46 ++++++++++++++--------------- drivers/net/sxe2/sxe2_flow.h | 6 ++-- drivers/net/sxe2/sxe2_flow_define.h | 12 ++++---- 5 files changed, 34 insertions(+), 34 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..3229c72597 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1800,7 +1800,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 294ac15db4..cfea1a1f0e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -159,7 +159,7 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..a33b8606df 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,16 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1112,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1143,13 +1143,13 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; if (user_id == 0) { TAILQ_REMOVE(cid_mgr_list, mgr, next); @@ -1170,14 +1170,14 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; @@ -1218,7 +1218,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,7 +1348,7 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) adapter->flow_ctxt.hw_res.count_type = adapter->devargs.fnav_stat_type; @@ -1370,10 +1370,10 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; ret = sxe2_flow_flush(dev, &error); if (ret) diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..8a5d871978 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,18 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 26/51] net/sxe2: move tunnel port helpers into flow module 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (25 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 25/51] net/sxe2: rename fnav cid manager symbols to flow liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 27/51] net/sxe2: add ACL engine event statistics support liujie5 ` (24 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_flow_parse_pattern_ipip, sxe2_flow_add_udp_tunnel_port and sxe2_flow_add_tunnel_port from sxe2_flow_parse_pattern.c into sxe2_flow.c as static helpers, and drop the public declaration of sxe2_flow_add_tunnel_port from the header, keeping the tunnel port handling internal to the flow module. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 113 +++++++++++++++++++++ drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 --------------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 -- 3 files changed, 113 insertions(+), 119 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index a33b8606df..cd39385340 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -550,6 +550,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..69d83a6ea6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -37,10 +37,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, struct rte_flow_error *error, struct sxe2_flow *flow); -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 27/51] net/sxe2: add ACL engine event statistics support 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (26 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 26/51] net/sxe2: move tunnel port helpers into flow module liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 28/51] net/sxe2: guard Rx queue event FD free in unregister liujie5 ` (23 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for the ACL flow engine to track packet hits and bytes, enabling flow aging and traffic monitoring for ACL rules. - Add acl-stat-type devarg to configure the statistics type - Implement sxe2_drv_flow_acl_get_stat_id/free_stat/query_stat - Handle the ACL engine in flow create/destroy/query paths - Add fnav_hw_res and acl_hw_res count resources Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 11 +++ drivers/net/sxe2/sxe2_cmd_chnl.c | 71 +++++++++++++++++++ drivers/net/sxe2/sxe2_cmd_chnl.h | 7 ++ drivers/net/sxe2/sxe2_drv_cmd.h | 17 +++++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 23 +++++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 83 ++++++++++++++++++----- drivers/net/sxe2/sxe2_flow_define.h | 3 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 25 +++++-- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 215 insertions(+), 30 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..c5b400a8ba 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,6 +98,17 @@ Runtime Configuration Default value is 3 (count both packets and bytes). +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL flow engine statistics type + used for flow rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). + - ``drv-sw-stats`` parameter [int] This parameter controls whether per-packet software statistics (SW stats) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3229c72597..16a2c3fea4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1829,6 +1829,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_acl_query_stat_req req = { 0 }; + struct sxe2_drv_acl_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index cfea1a1f0e..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -161,6 +161,13 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, struct sxe2_flow_cid_mgr *mgr); +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..d332d15980 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -668,6 +668,18 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_fc_get_resp { uint8_t rsv[3]; } __rte_packed_end; +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_req { + uint32_t stat_id; + uint32_t stat_ctrl; + uint32_t is_clear; +} __rte_packed_end; + +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_resp { + uint32_t stat_index; + uint64_t stat_hits; + uint64_t stat_bytes; +} __rte_packed_end; + enum sxe2_drv_cmd_module { SXE2_DRV_CMD_MODULE_HANDSHAKE = 0, SXE2_DRV_CMD_MODULE_DEV = 1, @@ -824,6 +836,11 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8e3afd6eed..5735dd0ff3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -985,11 +986,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -997,19 +998,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1191,13 +1192,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2378,6 +2386,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index e818578319..e9f78fe57f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -135,6 +135,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cd39385340..46f5763f62 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1204,13 +1204,23 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1233,7 +1243,10 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1244,7 +1257,7 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1260,13 +1273,20 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1287,13 +1307,19 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1310,7 +1336,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1461,12 +1495,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1485,13 +1525,13 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) struct rte_flow_error error; struct sxe2_flow_cid_mgr *mgr = NULL; struct sxe2_flow_cid_mgr *temp = NULL; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1500,5 +1540,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 8a5d871978..f56f687dc7 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -118,7 +118,8 @@ struct sxe2_flow_count_resource { struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_flow_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..db70b146c6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -953,7 +953,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -988,7 +989,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { @@ -1037,11 +1039,24 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, if (engine_type == SXE2_FLOW_ENGINE_FNAV) { sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); act_count = action->conf; - flow->action.count.user_id = act_count->id; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++adapter->flow_ctxt.fnav_hw_res.global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) + if (flow->action.count.user_id == 0) { flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; + ++adapter->flow_ctxt.acl_hw_res.global_index; + } action_num[SXE2_FLOW_ACTION_COUNT]++; } else { rte_flow_error_set(error, ENOTSUP, diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 28/51] net/sxe2: guard Rx queue event FD free in unregister 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (27 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 27/51] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 29/51] net/sxe2: refactor primary process MP message handling liujie5 ` (22 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_rxq_intr_unregister() frees irq_ctxt->rxq_event_fd outside the rxq_event_fd NULL check. Move the free and NULL assignment inside the guard so the buffer is only released when it was allocated. Fixes: 8cebf80f1e ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 53d49a4246..7fe500b229 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -881,12 +881,11 @@ static void sxe2_rxq_intr_unregister(struct rte_eth_dev *dev) (void)sxe2_drv_dev_rxq_irq_set(adapter->cdev, i, &efd, 1); sxe2_rxq_intr_efd_free(irq_ctxt->rxq_event_fd[i]); } + rte_free(irq_ctxt->rxq_event_fd); + irq_ctxt->rxq_event_fd = NULL; } - rte_free(irq_ctxt->rxq_event_fd); - irq_ctxt->rxq_event_fd = NULL; rte_intr_vec_list_free(intr_handle); - rte_intr_nb_efd_set(intr_handle, 0); rte_intr_max_intr_set(intr_handle, 0); } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 29/51] net/sxe2: refactor primary process MP message handling 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (28 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 28/51] net/sxe2: guard Rx queue event FD free in unregister liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 30/51] net/sxe2: refactor Tx queue reset operations liujie5 ` (21 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the multi-process work logic into the sxe2_mp_do_primary_work helper and operate on a copy of the request in the primary handler so the original message is not modified. Simplify the reply construction and return -ENOENT instead of -EINVAL when no response is received from the primary process. Fixes: 5db446ba97b0 ("net/sxe2: support statistics and multi-process") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_mp.c | 59 ++++++++++++++++++++++---------------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 30/51] net/sxe2: refactor Tx queue reset operations 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (29 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 29/51] net/sxe2: refactor primary process MP message handling liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 31/51] net/sxe2: unify vectorized Tx buffer handling liujie5 ` (20 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the descriptor ring reset loop into a sxe2_tx_queue_desc_ring_reset helper and reuse it from both the scalar and vectorized queue reset paths. Add a sxe2_tx_queue_reset_vec entry point for vectorized queues, export sxe2_tx_buffer_ring_free for reuse outside the module (clearing the buffer ring pointer after freeing it), and add sxe2_tx_vec_ops_get to build the vectorized Tx queue operations table used by the vector path setup. Fixes: e2a4ee85a5bd ("net/sxe2: add queue setup and control") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_tx.c | 42 +++++++++++++++++++++++--------- drivers/net/sxe2/sxe2_tx.h | 4 +++ drivers/net/sxe2/sxe2_txrx_vec.c | 16 +++++++++++- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + 4 files changed, 51 insertions(+), 12 deletions(-) diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..9cfa565548 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,19 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void) +{ + static const struct sxe2_txq_ops ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, + }; + + return ops; +} + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -233,7 +246,8 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); continue; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops_get(); + txq->ops.queue_reset(txq); } return ret; } diff --git a/drivers/net/sxe2/sxe2_txrx_vec.h b/drivers/net/sxe2/sxe2_txrx_vec.h index c139aed776..b9bc4f9c27 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.h +++ b/drivers/net/sxe2/sxe2_txrx_vec.h @@ -89,6 +89,7 @@ uint16_t sxe2_rx_pkts_scattered_vec_neon_offload(void *rx_queue, struct rte_mbuf uint16_t sxe2_tx_pkts_vec_neon_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); #endif +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void); int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev); int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 31/51] net/sxe2: unify vectorized Tx buffer handling 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (30 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 30/51] net/sxe2: refactor Tx queue reset operations liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 32/51] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 ` (19 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add a union of the scalar and vectorized buffer ring pointers to the Tx queue structure so the vectorized path can use sxe2_tx_buffer_vec directly. Rename the mbuf fill helper to sxe2_tx_pkts_mbuf_fill_vec, switch the vectorized Tx burst and mbuf release paths to the buffer_ring_vec member, and drop the AVX512-specific fill handling and conditional branching. Fixes: ac60f302cb ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_txrx_vec.c | 63 ++----- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++++++-------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- 7 files changed, 179 insertions(+), 270 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 9cfa565548..05940c8cb5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -170,67 +170,28 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - - dev = &rte_eth_devices[txq->port_id]; - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } + for ( ; i < txq->next_use; ++i) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..0b139b8269 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,12 +34,58 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << + SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,18 +105,26 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -82,14 +136,23 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; @@ -150,22 +213,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -208,9 +273,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -267,23 +333,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -442,25 +491,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -480,7 +543,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -515,55 +579,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -587,12 +644,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 32/51] net/sxe2: refine vectorized Tx/Rx mode setup 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (31 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 31/51] net/sxe2: unify vectorized Tx buffer handling liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 33/51] net/sxe2: fix RSS action attribute validation liujie5 ` (18 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Set rte_eth_tx_pkt_prepare_dummy for the simple and vectorized Tx paths instead of leaving the prepare callback unset, and split the NEON simple/offload mode selection based on the offload flag. Log the selected Tx/Rx mode flags and apply the default Rx free threshold when the configured value is zero. Fixes: ac60f302cb ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_rx.c | 3 ++- drivers/net/sxe2/sxe2_txrx.c | 19 +++++++++++++------ 2 files changed, 15 insertions(+), 7 deletions(-) diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..3830c676d7 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..d27d2ce630 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,25 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; - } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +586,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 33/51] net/sxe2: fix RSS action attribute validation 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (32 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 32/51] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:56 ` [PATCH v3 34/51] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 ` (17 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The rss->level/key_len/queue_num checks only set the rte_flow_error but still return 0 (success), so invalid RSS configurations are accepted instead of being rejected with ENOTSUP. Return the error code from the validation checks, matching the behavior in the V3 implementation. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow_parse_action.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index db70b146c6..867d90ae1d 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 34/51] net/sxe2: restore PF-only guard in udp tunnel port add 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (33 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 33/51] net/sxe2: fix RSS action attribute validation liujie5 @ 2026-08-26 8:56 ` liujie5 2026-08-26 8:57 ` [PATCH v3 35/51] net/sxe2: align flow meta proc priority handling with V3 liujie5 ` (16 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:56 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_udp_tunnel_port_add_common() lost the check that restricts UDP tunnel port configuration to PF devices (not VF or representor), so VF/representor devices can now attempt to add UDP tunnel ports, which the hardware does not support. Restore the PF-only guard returning -ENOTSUP, matching the V3 implementation. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5735dd0ff3..88fe43298a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 35/51] net/sxe2: align flow meta proc priority handling with V3 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (34 preceding siblings ...) 2026-08-26 8:56 ` [PATCH v3 34/51] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 36/51] net/sxe2: restore link update call in status query liujie5 ` (15 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_flow_meta_proc() uses a flat else-if chain for the priority check, while the V3 implementation nests the switchdev mode check inside the else branch. Align the structure with V3 for consistency. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 46f5763f62..037d9e6f9c 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -285,14 +285,16 @@ static int32_t sxe2_flow_meta_proc(struct rte_eth_dev *dev, attr, "Only support priority 0."); ret = -rte_errno; goto l_end; - } else if (!adapter->switchdev_info.is_switchdev) { - PMD_LOG_ERR(DRV, "Legacy mode only support priority 0."); - rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ATTR_PRIORITY, - attr, "Legacy mode only priority 0."); - ret = -rte_errno; - goto l_end; } else { - flow->meta.flow_prio = attr->priority; + if (!adapter->switchdev_info.is_switchdev) { + PMD_LOG_ERR(DRV, "Legacy mode only support priority 0."); + rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ATTR_PRIORITY, + attr, "Legacy mode only priority 0."); + ret = -rte_errno; + goto l_end; + } else { + flow->meta.flow_prio = attr->priority; + } } } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 36/51] net/sxe2: restore link update call in status query 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (35 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 35/51] net/sxe2: align flow meta proc priority handling with V3 liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 37/51] net/sxe2: validate representor ID against VF count liujie5 ` (14 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_mac_link_status_get() no longer calls sxe2_link_update() after refreshing the link context, so the ethdev link state is only refreshed during device init (sxe2_link_update_init) and never updated when link status is queried at runtime, including on LSC interrupt events. Move the sxe2_link_update() call back into sxe2_drv_mac_link_status_get() and simplify sxe2_link_update_init() accordingly, matching the V3 implementation. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 ++ drivers/net/sxe2/sxe2_mac.c | 9 +-------- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 16a2c3fea4..705d259412 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -412,6 +412,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) { int32_t ret = 0; struct sxe2_common_device *cdev = adapter->cdev; + struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; struct sxe2_drv_cmd_params param = {0}; struct sxe2_drv_link_info_resp resp = {0}; @@ -425,6 +426,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) } adapter->link_ctxt.speed = resp.speed; adapter->link_ctxt.link_up = resp.status; + (void)sxe2_link_update(dev, 0); l_end: return ret; diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..7dbea92670 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,18 +448,11 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - (void)sxe2_link_update(dev, 0); - -l_end: return ret; } int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 37/51] net/sxe2: validate representor ID against VF count 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (36 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 36/51] net/sxe2: restore link update call in status query liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 38/51] net/sxe2: use primary VSI ID for representor VSI liujie5 ` (13 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_private_data_init() indexes parent_adapter->repr_ctxt.repr_vf_id[repr_id] without checking that repr_id is within the number of configured VFs, which can access out of bounds when an invalid representor ID is passed. Add a bounds check on repr_id against repr_ctxt.nb_vf and return -EINVAL on the error path. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..d0304ccc94 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,6 +312,12 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; + if (repr_id >= parent_adapter->repr_ctxt.nb_vf) { + PMD_LOG_ERR(INIT, "repr_id %u exceed max vf %u", + repr_id, parent_adapter->repr_ctxt.nb_vf); + ret = -EINVAL; + goto l_free; + } repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 38/51] net/sxe2: use primary VSI ID for representor VSI 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (37 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 37/51] net/sxe2: validate representor ID against VF count liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 39/51] net/sxe2: wrap command params fill debug log in macro liujie5 ` (12 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> repr_priv_data->repr_vf_vsi_id is assigned with a ternary that falls back to the backup (dpdk) VSI ID when the kernel VSI ID is invalid. The V3 implementation assigns it directly from repr_vf_primary_vsi_id. Align with the V3 implementation by assigning repr_vf_vsi_id from repr_vf_primary_vsi_id. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index d0304ccc94..81ced7b855 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -323,11 +323,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; + repr_priv_data->repr_vf_vsi_id = repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 39/51] net/sxe2: wrap command params fill debug log in macro 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (38 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 38/51] net/sxe2: use primary VSI ID for representor VSI liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 40/51] net/sxe2: restore Rx queue buffer split fill support liujie5 ` (11 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_cmd_params_fill() passes the opcode string as a parameter to __sxe2_drv_cmd_params_fill() just to emit a debug log, and the debug log is executed unconditionally on every command fill. Move the PMD_DEV_LOG_DEBUG into the macro body wrapped in a do/while block, dropping the opc_str parameter so the opcode stringization is performed at the call site and the macro is a proper multi-statement block. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 705d259412..b17d80d917 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,8 +43,10 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) - + do { \ + PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", #opc); \ + __sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len); \ + } while (0) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 40/51] net/sxe2: restore Rx queue buffer split fill support 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (39 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 39/51] net/sxe2: wrap command params fill debug log in macro liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 41/51] net/sxe2: skip tunnel config fill on get failure liujie5 ` (10 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The V4 branch dropped sxe2_rxq_buf_split_fill() and the buffer split handling in sxe2_rxq_ctxt_cfg_fill(), so the Rx buffer split offload (RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) is advertised in device info but the per-queue context never configures split_en/split_type_mask/ hdr_len, and buffer split packets are not handled correctly. Restore the sxe2_rxq_buf_split_fill() helper and the buffer split branch in sxe2_rxq_ctxt_cfg_fill(), matching the V3 implementation. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 106 +++++++++++++++++++++++++++++++ 1 file changed, 106 insertions(+) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b17d80d917..5102890107 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -194,6 +194,102 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + int32_t ret = 0; + uint32_t proto_hdr; + + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + ret = -1; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + goto l_end; + } + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + ret = -1; + } else { + ctxt->hdr_len = 0; + ctxt->split_type_mask = 0; + } +l_end: + return ret; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -227,7 +323,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 41/51] net/sxe2: skip tunnel config fill on get failure 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (40 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 40/51] net/sxe2: restore Rx queue buffer split fill support liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 42/51] net/sxe2: skip flow id assignment on filter add failure liujie5 ` (9 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_udp_tunnel_get() fills tunnel_config fields even when the firmware command fails, so a failed get overwrites the config with the (zero-initialized) response data instead of leaving it intact. Return early with the error code when sxe2_drv_cmd_exec() fails, matching the V3 implementation. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 5102890107..8c45554637 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1669,15 +1669,17 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; tunnel_config->fw_dst_en = resp.dst; tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; - +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 42/51] net/sxe2: skip flow id assignment on filter add failure 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (41 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 41/51] net/sxe2: skip tunnel config fill on get failure liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 43/51] net/sxe2: fix command channel log messages liujie5 ` (8 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_flow_filter_add() assigns flow->flow_id from the response even when the firmware command fails, overwriting any previously set flow id with the zero-initialized response value. Return early on command failure so flow->flow_id is preserved, and set flow->create_err on both the success and error paths. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 8c45554637..e0c45ae0e3 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1837,9 +1837,13 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + goto l_end; + } flow->flow_id = resp.flow_id; + +l_end: flow->create_err = ret; return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 43/51] net/sxe2: fix command channel log messages 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (42 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 42/51] net/sxe2: skip flow id assignment on filter add failure liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:57 ` [PATCH v3 44/51] net/sxe2: align command structs with historical kernel layout liujie5 ` (7 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Several error/warning messages in sxe2_cmd_chnl.c are inaccurate or lost context: - vsi_info_get: message lost the vsi id; restore it - rxq_bind_irq/rxq_unbind_irq: message lost the rxq index; restore it - promisc_config: fix "promic" typo in the message - queue_info_get_update/rxq_mapping_set: incorrect "get queue info map"/"get dev caps" wording; use "rx queue mapping failed" - txq_mapping_set: "Rx queue" should read "Tx queue"; incorrect "get dev caps" wording should read "tx queue mapping failed" Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index e0c45ae0e3..b4f8b337b5 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -498,7 +498,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -556,7 +556,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -576,7 +576,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -777,7 +777,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1702,7 +1702,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); goto l_end; } @@ -1746,7 +1746,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1763,7 +1763,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1777,7 +1777,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 44/51] net/sxe2: align command structs with historical kernel layout 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (43 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 43/51] net/sxe2: fix command channel log messages liujie5 @ 2026-08-26 8:57 ` liujie5 2026-08-26 8:58 ` [PATCH v3 45/51] common/sxe2: fix ioctl channel log and close handling liujie5 ` (6 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:57 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The sxe2_drv_cmd.h command structures must match the layout used by historical SXE2 kernel versions so the same firmware command ABI is shared. Several structures were declared with __rte_packed_begin/ __rte_packed_end and extra rsv padding that the kernel layout does not have: - sxe2_drv_link_info_resp: drop rsv[3] padding - sxe2_tm_res: drop rsv[2] padding and packed attribute - sxe2_tm_info: drop packed attribute - sxe2_tm_add_mid_msg: drop packed attribute - sxe2_tm_add_queue_msg: drop packed attribute - sxe2_drv_sfp_req: drop packed attribute - sxe2_drv_sfp_resp: drop packed attribute Keep the structure members as-is so the command ABI is compatible with the historical kernel driver. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index d332d15980..f66b574e83 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,31 +347,30 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { +struct sxe2_tm_add_mid_msg { uint16_t parent_teid; uint8_t adj_lvl; struct sxe2_tm_info info; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_queue_msg { +struct sxe2_tm_add_queue_msg { uint16_t parent_teid; uint16_t queue_id; uint8_t adj_lvl; struct sxe2_tm_info info; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_drv_ipsec_capa_resq { uint16_t tx_sa_cnt; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 45/51] common/sxe2: fix ioctl channel log and close handling 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (44 preceding siblings ...) 2026-08-26 8:57 ` [PATCH v3 44/51] net/sxe2: align command structs with historical kernel layout liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 46/51] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (5 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Compare sxe2_ioctl_chnl.c against the reference implementation and fix the following discrepancies: - sxe2_drv_dev_close: only log the closed fd when it is valid, move PMD_LOG_INFO inside the fd >= 0 check - sxe2_drv_dev_mmap: fix swapped format arguments in the debug log (cmd_fd and bar_idx were passed in the wrong order) - sxe2_drv_dev_dma_unmap: use PMD_LOG_ERR instead of PMD_LOG_INFO for the ioctl failure message Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index 3e2fbf572f..e62ca42a8f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -107,9 +107,11 @@ sxe2_drv_dev_close(struct sxe2_common_device *cdev) { int32_t fd = SXE2_CDEV_TO_CMD_FD(cdev); - if (fd >= 0) + if (fd >= 0) { close(fd); - PMD_LOG_INFO(COM, "closed device fd=%d", fd); + PMD_LOG_INFO(COM, "closed device fd=%d", fd); + } + SXE2_CDEV_TO_CMD_FD(cdev) = SXE2_CMD_FD_INVALID; } @@ -350,7 +352,7 @@ void } PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", src=0x%"PRIx64", offset=0x%"PRIx64"", - bar_idx, cmd_fd, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); + cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); virt = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, cmd_fd, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); @@ -477,7 +479,7 @@ sxe2_drv_dev_dma_unmap(struct sxe2_common_device *cdev, uint64_t iova) pthread_mutex_lock(&cdev->config.lock); ret = ioctl(cmd_fd, SXE2_COM_CMD_DMA_UNMAP, &cmd_params); if (ret < 0) { - PMD_LOG_INFO(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", + PMD_LOG_ERR(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", cmd_fd, ret, strerror(errno)); ret = -EIO; pthread_mutex_unlock(&cdev->config.lock); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 46/51] doc/sxe2: remove drv-sw-stats parameter documentation 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (45 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 45/51] common/sxe2: fix ioctl channel log and close handling liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 47/51] net/sxe2: harden ACL flow count resource handling liujie5 ` (4 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The drv-sw-stats devarg and the software receive statistics xstats that depend on it are no longer supported. Remove the parameter description from the Runtime Configuration section and the corresponding "Receive Software Statistics" subsection under Extended Statistics to keep the documentation consistent. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 49 ---------------------------------------- 1 file changed, 49 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index c5b400a8ba..d9be5ab693 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -109,30 +109,6 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. - - ``no-sched-mode`` parameter [int] This parameter enables non-scheduling mode (no-sched mode). @@ -197,31 +173,6 @@ Runtime Configuration Extended Statistics (xstats) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -The PMD provides the following extended statistics (xstats) -for detailed monitoring of receive-side packet classification -and software-level accounting. -The software statistics path is provided as a workaround -for hardware counter inaccuracies on certain packet types --- -it accumulates per-packet statistics directly in the Rx data path, -ensuring that unicast, multicast, broadcast, and drop counts -reflect the actual packets processed by the driver. - -Receive Software Statistics - These counters are collected in the Rx data path - when ``drv-sw-stats=1`` is configured (see the ``drv-sw-stats`` devarg above). - When ``drv-sw-stats`` is disabled (default), these xstats report zero. - - - ``rx_sw_unicast_packets``: Number of unicast packets received. - - ``rx_sw_multicast_packets``: Number of multicast packets received. - - ``rx_sw_broadcast_packets``: Number of broadcast packets received. - - ``rx_sw_drop_packets``: Number of packets dropped in the Rx data path. - - ``rx_sw_drop_bytes``: Number of bytes dropped in the Rx data path. - - When ``drv-sw-stats`` is enabled, the basic counters - ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) - also reflect the software-accumulated packet and byte counts. - Otherwise, they are reported from hardware counters. - Fnav Flow Engine Statistics The Fnav flow engine statistics type is controlled by the ``fnav-stat-type`` devarg (see above). -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 47/51] net/sxe2: harden ACL flow count resource handling 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (46 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 46/51] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 48/51] net/sxe2: fix device init and representor matching issues liujie5 ` (3 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fix issues found in the ACL flow count (statistics) support: - sxe2_flow_free_mgr(): when the flow engine type is neither ACL nor FNAV, the code skipped the TAILQ_REMOVE but still called rte_free() on the manager, leaving a freed pointer on the list. Return -ENOTSUP for an unknown engine type instead. - sxe2_flow_cid_mgr.stat_index is uint16_t while the firmware returns and consumes a uint32_t stat id; widen it to uint32_t to avoid silent truncation. - sxe2_drv_cmd_code: write the ACL STAT_ALLOC/STAT_FREE entries with an explicit SXE2_MK_DRV_CMD() value instead of relying on implicit increment over the encoded QUERY value. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 6 ++++-- drivers/net/sxe2/sxe2_flow.c | 6 ++++++ drivers/net/sxe2/sxe2_flow_define.h | 2 +- 3 files changed, 11 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index f66b574e83..8d907b3843 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -836,8 +836,10 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), - SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, - SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2), + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 3), }; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 037d9e6f9c..45ace5b848 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1288,6 +1288,12 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } else { + PMD_LOG_ERR(DRV, + "Failed to free flow count, unknown engine type: %d.", + flow->engine_type); + ret = -ENOTSUP; + return ret; } if (ret) { rte_flow_error_set(error, EIO, diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index f56f687dc7..d04499f5cb 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -100,7 +100,7 @@ TAILQ_HEAD(rte_flow_list_t, rte_flow); struct sxe2_flow_cid_mgr { TAILQ_ENTRY(sxe2_flow_cid_mgr) next; - uint16_t stat_index; + uint32_t stat_index; uint32_t user_id; uint32_t driver_id; uint32_t count_type; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 48/51] net/sxe2: fix device init and representor matching issues 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (47 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 47/51] net/sxe2: harden ACL flow count resource handling liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 49/51] net/sxe2: use correct loop counter type for representor LSC liujie5 ` (2 subsequent siblings) 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> - sxe2_dev_init(): move the init_rss_err label above sxe2_security_uinit() so an RSS init failure still unwinds the security context instead of leaking it. - sxe2_buffer_split_supported_hdr_ptypes_get(): exclude the trailing RTE_PTYPE_UNKNOWN terminator from no_of_elements so applications do not receive a bogus ptype entry. - sxe2_switchdev_repr_match(): match the PF when the adapter's pf_num is among the requested ports instead of requiring every requested port to equal pf_num, which could never succeed with multiple ports. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 88fe43298a..f4e65852d4 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -986,7 +986,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; - *no_of_elements = RTE_DIM(ptypes); + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } @@ -2028,8 +2028,8 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_fc_state_err: (void)sxe2_flow_uninit(dev); init_flow_err: - sxe2_security_uinit(dev); init_rss_err: + sxe2_security_uinit(dev); init_security_err: sxe2_intr_uninit(dev); init_irq_err: @@ -2198,12 +2198,14 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, } for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { - if (adapter->switchdev_info.pf_num != req_eth_da->ports[port_idx]) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf %u", - adapter->switchdev_info.pf_num, req_eth_da->ports[port_idx]); - rte_errno = EBUSY; - return false; - } + if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) + break; + } + if (port_idx == req_eth_da->nb_ports) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf", + adapter->switchdev_info.pf_num); + rte_errno = EBUSY; + return false; } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 49/51] net/sxe2: use correct loop counter type for representor LSC 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (48 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 48/51] net/sxe2: fix device init and representor matching issues liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 50/51] net/sxe2: restore NULL check in vectorized Tx mbuf release liujie5 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The LSC propagation loop uses uint8_t vf_id as the loop counter while adapter->repr_ctxt.nb_repr_vf is uint16_t. When more than 255 VFs are present, vf_id wraps and the loop runs forever. Use uint16_t for vf_id to match the nb_repr_vf type. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 7fe500b229..4e5339e24b 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -79,7 +79,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; struct rte_eth_dev *repr_eth_dev; struct sxe2_adapter *repr_adapter; - uint8_t vf_id; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 50/51] net/sxe2: restore NULL check in vectorized Tx mbuf release 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (49 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 49/51] net/sxe2: use correct loop counter type for representor LSC liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 51 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_tx_queue_mbufs_release_vec() calls rte_pktmbuf_free_seg() on each buffer entry without checking for NULL. rte_pktmbuf_free_seg() does not tolerate NULL and dereferences its argument, so a stop/start cycle or any unwritten slot in the release range can crash. Restore the NULL check before freeing each mbuf. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_txrx_vec.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 05940c8cb5..7c5da33dd5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -183,15 +183,19 @@ static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) if (txq->next_use < i) { for ( ; i < txq->ring_depth; ++i) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; + } } i = 0; } for ( ; i < txq->next_use; ++i) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; + } } } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 ` (50 preceding siblings ...) 2026-08-26 8:58 ` [PATCH v3 50/51] net/sxe2: restore NULL check in vectorized Tx mbuf release liujie5 @ 2026-08-26 8:58 ` liujie5 2026-08-27 2:36 ` [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes liujie5 ` (44 more replies) 51 siblings, 45 replies; 278+ messages in thread From: liujie5 @ 2026-08-26 8:58 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_rxq_buf_split_fill() re-tests the RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT offload flag even though the caller already guarantees it, leaving the else branch dead. It also returns -1 on failure instead of a standard errno. Drop the redundant flag test and dead else branch, set hdr_len once after the switch chain, and return -EINVAL for an unconfigured split protocol and -ENOTSUP for an unsupported one. Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 142 ++++++++++++++----------------- 1 file changed, 62 insertions(+), 80 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b4f8b337b5..9bd6e3355f 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -197,97 +197,79 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_ctxt *ctxt) { - int32_t ret = 0; uint32_t proto_hdr; - if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { - proto_hdr = rxq->rx_seg[0].proto_hdr; - if (proto_hdr == RTE_PTYPE_UNKNOWN) { - PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); - ret = -1; - goto l_end; - } + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + return -EINVAL; + } - switch (proto_hdr & RTE_PTYPE_L4_MASK) { - case RTE_PTYPE_L4_TCP: - ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_L4_UDP: - ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_L4_SCTP: - ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_L3_MASK) { - case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: - ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: - ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_L2_MASK) { - case RTE_PTYPE_L2_ETHER: - ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { - case RTE_PTYPE_INNER_L4_TCP: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_INNER_L4_UDP: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_INNER_L4_SCTP: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { - case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { - case RTE_PTYPE_INNER_L2_ETHER: - ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + goto l_end; + } - switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { - case RTE_PTYPE_TUNNEL_GRENAT: - ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; - ctxt->hdr_len = SXE2_RX_HDR_SIZE; - goto l_end; - } - PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); - ret = -1; - } else { - ctxt->hdr_len = 0; - ctxt->split_type_mask = 0; + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + goto l_end; } + + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + return -ENOTSUP; l_end: - return ret; + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + return 0; } static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 15:14 ` Stephen Hemminger 2026-08-27 2:36 ` [PATCH v4 01/44] common/sxe2: fix null pointer in class driver remove liujie5 ` (43 subsequent siblings) 44 siblings, 1 reply; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> This series adds the Stars SXE2 network driver together with a set of fixes accumulated while validating the driver against the historical kernel implementation and reviewing the code. This is the v4 revision. Changes since v3 address the community review of the v3 series: - Drop the "probe all requested PF ports" change. rte_eth_dev_pci_allocate() derives the port name from the PCI device and creates a single ethdev per PCI device, so probing multiple PF ports from one probe call is not supported. - Fix RSS action attribute validation to return the negative error code (-ENOTSUP) instead of a positive value so invalid RSS configurations are rejected. - Keep the packed attribute on sxe2_tm_add_mid_msg and sxe2_tm_add_queue_msg so the firmware command wire offsets (tm info offset, tm queue info offset) are preserved. Only drop the packed attribute and padding from the structs that do not have it in the historical kernel layout. - Keep the "Receive Software Statistics" xstats documentation section. The rx_sw_* counters are still accumulated in the Rx data path and reported through rte_eth_xstats_get(); only the removed drv-sw-stats devarg text is dropped. - Consolidate fix-on-fix commits into the commits that introduced the bugs so the series does not contain standalone fix patches for regressions introduced earlier in the same series. - Expand Fixes: hashes to the 12-character form and add the missing Fixes: tags on patches carrying Cc: stable@dpdk.org. - Drop a commit that only realigned code structure without any functional change. Jie Liu (44): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore pf and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: validate IPsec key length against maximum limit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC and queue counts in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: guard Rx queue event FD free in unregister net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in udp tunnel port add net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow id assignment on filter add failure net/sxe2: fix command channel log messages net/sxe2: align command structs with historical kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-sw-stats parameter documentation doc/guides/nics/sxe2.rst | 40 ++-- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 18 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 200 ++++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 37 +++- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 188 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 13 +- drivers/net/sxe2/sxe2_flow.c | 234 ++++++++++++++++++--- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 39 +++- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_ipsec.c | 5 + drivers/net/sxe2/sxe2_irq.c | 27 ++- drivers/net/sxe2/sxe2_mac.c | 9 +- drivers/net/sxe2/sxe2_mp.c | 59 +++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 16 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 19 +- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 73 +++---- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 8 +- 37 files changed, 941 insertions(+), 671 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* Re: [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes 2026-08-27 2:36 ` [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes liujie5 @ 2026-08-27 15:14 ` Stephen Hemminger 0 siblings, 0 replies; 278+ messages in thread From: Stephen Hemminger @ 2026-08-27 15:14 UTC (permalink / raw) To: liujie5; +Cc: dev On Thu, 27 Aug 2026 10:36:18 +0800 liujie5@linkdatatechnology.com wrote: > From: Jie Liu <liujie5@linkdatatechnology.com> > > This series adds the Stars SXE2 network driver together with a set of > fixes accumulated while validating the driver against the historical > kernel implementation and reviewing the code. > > This is the v4 revision. This is in much closer to being ready, AI still has some useful feedback. You don't have to address all of it but it is informative and helpful. Review of [PATCH v4 00/44] net/sxe2 fixes and improvements Reviewed against the series applied with git am on top of d55ccd4 ("pci: remove deprecated catch-all flag"). Findings are against the post-apply tree, not the diffs in isolation. Patches with no findings are omitted. Patch 06/44 - net/sxe2: fix VSI lifecycle management Warning: the patch fixes the dangling main_vsi pointer but leaves the same problem on other_vsi_list. sxe2_vsi_destroy() frees list members with a bare rte_free() and never unlinks them. The unlink lives in sxe2_vsi_node_free(), which only fires for SXE2_VSI_T_ESW: if (vsi->vsi_type == SXE2_VSI_T_ESW) TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); but sxe2_other_vsi_create() inserts nodes as SXE2_VSI_T_DPDK_ESW, and SXE2_VSI_T_ESW is never assigned anywhere in the driver. So the removal never happens, and after sxe2_vsi_uninit() the list head still points at freed memory. sxe2_switchdev_repr_private_data_init() reads that head via TAILQ_FIRST(). Either add TAILQ_REMOVE() to sxe2_vsi_destroy() for list members, or fix the type test in sxe2_vsi_node_free() to SXE2_VSI_T_DPDK_ESW. Patch 10/44 - net/sxe2: validate IPsec key length against maximum limit Error: the added check is dead code. sxe2_security_valid_key() already tests the same condition as its first statement in the base tree: static bool sxe2_security_valid_key(uint16_t src_key, ...) { bool is_valid = false; if (src_key > SXE2_IPSEC_MAX_KEY_LEN) { <-- pre-existing is_valid = false; goto l_end; } ... The new copy is placed after the increment check, where src_key has already been proven <= SXE2_IPSEC_MAX_KEY_LEN, so the branch can never be taken. The patch is a no-op and the buffer-overflow protection it describes is already present. Drop the patch. Patch 14/44 - net/sxe2: fill MAC and queue counts in device info Info: nb_rx_queues and nb_tx_queues are overwritten by ethdev immediately after the PMD callback returns: lib/ethdev/rte_ethdev.c:4146 dev_info->nb_rx_queues = dev->data->nb_rx_queues; dev_info->nb_tx_queues = dev->data->nb_tx_queues; Those two lines have no effect. max_mac_addrs is the useful part of the patch; consider dropping the queue-count hunk and adjusting the commit message. Patch 15/44 - net/sxe2: fix QinQ and RSS offload capability report Error: neither capability the patch claims to gate is actually gated. RTE_ETH_TX_OFFLOAD_QINQ_INSERT is still in the unconditional tx_offload_capa initialiser and is OR'd in again inside the port-VLAN branch, so it is always advertised: dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | RTE_ETH_TX_OFFLOAD_QINQ_INSERT | <-- still here ... if (!sxe2_dev_port_vlan_check(dev)) { dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; RTE_ETH_RX_OFFLOAD_RSS_HASH is added unconditionally to the base list and is still set under the capability test, which now cannot make any difference: dev_info->rx_offload_capa = ... | RTE_ETH_RX_OFFLOAD_RSS_HASH; ... if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; Advertising RSS_HASH when SXE2_DEV_CAPS_OFFLOAD_RSS is clear tells the application the PMD can deliver an RSS hash on a device that has no RSS capability. Remove QINQ_INSERT from the base tx list, and pick one place for RSS_HASH. The RTE_ETH_RX_OFFLOAD_QINQ_STRIP hunk is correct - it is removed from the base list and only added under the guard. Patches 21/44 and 22/44 - dev close / dev init ordering Warning: after both patches the two teardown paths still disagree on switchdev, and dev_close does not follow reverse-init order for fc_state. sxe2_dev_init() error unwind: sw_uninit -> eth_uinit -> switchdev_uninit -> vsi_uninit sxe2_dev_close(): switchdev_uninit -> sw_uninit -> eth_uinit -> vsi_uninit sxe2_fc_state_init() runs before sxe2_sched_init() in dev_init, so reverse order puts sxe2_fc_state_uinit() right after sxe2_sched_uinit() in close; it is currently the last call in the function. Since 21/44 is specifically "align dev init and cleanup order", it would be good to finish the job so the two paths are identical. Patch 23/44 - net/sxe2: simplify switchdev representor matching Error: this breaks the common representor devarg form. The new PF match loop is: for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) break; if (port_idx == req_eth_da->nb_ports) { rte_errno = EBUSY; return false; } rte_eth_devargs_parse_representor_ports() only fills eth_da->ports and nb_ports when the devarg carries a "pf#" prefix (see lib/ethdev/ethdev_private.c). For "representor=vf0", "representor=[0-3]" and the legacy bare-number form, nb_ports stays 0. The loop body then never executes, port_idx == 0 == nb_ports, and the function returns false. sxe2_eth_pmd_probe_pf() turns that into -ENOTSUP and no representor is ever created. The old code read ports[0] (zero when unset), so it happened to work. The fix needs to treat nb_ports == 0 as "no PF constraint given" and skip the check. Warning: the RTE_ETH_REPRESENTOR_PF case now falls through to the same loop that matches representor_ports[] against repr_vf_id[i].func_id. For a PF representor those entries are PF indices, not VF function IDs, so the comparison is against the wrong table. The driver only ever creates VF representors (sxe2_switchdev_repr_devs_init() formats names as "..._representor_vf%u"), so it may be simpler to reject RTE_ETH_REPRESENTOR_PF outright. Info: dead store. uint16_t port_idx = UINT16_MAX; is unconditionally overwritten by the for loop initialiser on the next use. Drop the initialiser. Patch 26/44 - net/sxe2: add ACL engine event statistics support Warning: two unrelated changes are bundled in. First, the act_count NULL guard is applied to the existing FNAV path, not just the new ACL path: act_count = action->conf; flow->action.count.user_id = (act_count == NULL) ? 0 : act_count->id; That is a NULL-dereference fix for RTE_FLOW_ACTION_TYPE_COUNT with a NULL conf, and it belongs in its own patch with a Fixes: tag and Cc: stable@dpdk.org. Second, the sxe2_queue.c hunk if (adapter->flow_ctxt.fnav_inited) rxq->fnav_enable = true; has nothing to do with ACL statistics and is not mentioned in the commit message. Info: widening sxe2_flow_cid_mgr.stat_index from uint16_t to uint32_t fixes a real truncation on the existing FNAV path, since sxe2_drv_flow_fnav_get_stat_id() returns a uint32_t stat id. Worth calling out in the commit message (or splitting out) rather than folding it in silently. Info: sxe2_drv_acl_query_stat_req and sxe2_drv_acl_query_stat_resp are byte-for-byte identical to the existing sxe2_drv_flow_fnav_query_stat_req and sxe2_drv_flow_fnav_query_stat_resp. Reuse the existing types, or give them a neutral name shared by both engines. Info: the FNAV and ACL arms in sxe2_flow_parse_action() are ten-line copies of each other differing only in fnav_hw_res vs acl_hw_res. Select the resource pointer first and share the body. Patch 30/44 - net/sxe2: unify vectorized Tx buffer handling Warning: the subject and commit message describe Tx buffer handling only, but the patch also rewrites a large part of the NEON Rx data path: - sxe2_rx_desc_ptype_fill_neon() changes signature, input vector and packet-to-lane mapping - the staterr construction changes from vzip2q_u32 on 32-bit lanes to vzip2q_u16 on 16-bit lanes - the DD count changes from rte_popcount64() of the DD bits to rte_ctz64() of the inverted mask, which changes the result when DD bits are not contiguous - the eop, umbcast and rxe shuffle masks and constants all change - three rte_atomic_thread_fence(rte_memory_order_acquire) calls between the descriptor loads are removed - the #ifndef SXE2_TEST guard around the whole AVX512 file is dropped Several of these look like genuine fixes, and dropping the fences does match what ixgbe's NEON path does, but none of it is described and none of it can be reviewed as part of a Tx patch. Please split the NEON Rx work into its own patch (or patches) with its own rationale, especially the fence removal and the DD-count change. Info: sxe2_tx_desc_fill_4_neon_simple() uses vst1q_u64_x4(), which is not used anywhere else in DPDK. It is aarch64-only and needs a reasonably recent toolchain; worth confirming against the oldest supported ARM compilers. Info: *(uint32_t *)umbcast_flags = vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); replaces vst1q_lane_u32(). The plain store through a cast pointer assumes umbcast_flags is 4-byte aligned; the NEON store did not. If the alignment is not guaranteed, keep vst1q_lane_u32(). Patch 31/44 - net/sxe2: refine vectorized Tx/Rx mode setup Warning: on arm64 the reworked NEON branch can leave tx_pkt_burst unset. sxe2_tx_vec_support_check() unconditionally sets *vec_flags = SXE2_TX_MODE_VEC_SIMPLE; on success, and SXE2_TX_MODE_VEC_SIMPLE is part of SXE2_TX_MODE_VEC_SET_MASK. So tx_mode_flags can satisfy if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) without SXE2_TX_MODE_VEC_NEON being set, because NEON is only OR'd in when rte_cpu_get_flag_enabled(RTE_CPUFLAG_NEON) == 1. Before the patch the else arm caught that case and installed sxe2_tx_pkts_vec_neon_simple(); now the whole block is skipped, tx_pkt_prepare is set to the dummy, and tx_pkt_burst keeps whatever it had. Restore a fallback for the non-NEON case, or make the x86 style "else" explicit. Info: the rx_free_thresh change is a separate bug fix. With rx_free_thresh == 0, sxe2_rx_queue_init() computes rxq->batch_alloc_trigger = rxq->rx_free_thresh - 1; which underflows to 65535. That deserves its own patch with a Fixes: tag rather than being folded into a mode-setup patch. Info: tx_mode_flags and rx_mode_flags are uint32_t, so "0x%016x" prints a 32-bit value zero-padded to 16 digits. "%#x" or "0x%08x" would be clearer. Patch 33/44 - net/sxe2: restore PF-only guard in udp tunnel port add Warning: the guard is asymmetric. sxe2_udp_tunnel_port_del_common() and sxe2_udp_tunnel_port_clear() have no equivalent check, so a VF or representor can still reach sxe2_drv_udp_tunnel_del() through .udp_tunnel_port_del and through sxe2_dev_close(). Either add the same guard there, or hoist it into the sxe2_udp_tunnel_port_add() / sxe2_udp_tunnel_port_del() dev_ops wrappers where both paths pass through. Patch 34/44 - net/sxe2: restore link update call in status query Warning: layering. sxe2_drv_mac_link_status_get() is a command-channel function in sxe2_cmd_chnl.c; it now indexes the global rte_eth_devices array and calls the ethdev-level sxe2_link_update(): struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; ... (void)sxe2_link_update(dev, 0); The underlying problem is real - the LSC handler updates link_ctxt but never pushes it into rte_eth_link, so callbacks fire with a stale link - but the fix reads better in the two callers. Calling sxe2_link_update() from sxe2_event_irq_common_handler() (which already has the rte_eth_dev) and from sxe2_link_update_init() keeps the command layer free of ethdev side effects and avoids the global lookup. Note also that the unconditional dereference of adapter->dev_info.dev_data at the top of the function is reachable after sxe2_dev_pci_map_uinit() sets that pointer to NULL (patch 19/44). Info: the patch removes two unrelated blank lines in sxe2_link_update_init(). Unnecessary churn in a fix patch. Patch 37/44 - net/sxe2: wrap command params fill debug log in macro Info: the commit message says "the debug log is executed unconditionally on every command fill", implying the change avoids that. It does not - PMD_DEV_LOG_DEBUG is level-gated either way, and moving it into the macro leaves the call frequency unchanged. The actual effect is that #opc is stringized at the call site and the helper loses a parameter. Please reword. Info: adapter is now evaluated twice by the macro (once in the log, once in the call). All current callers pass a plain variable, so this is latent, but it is worth a comment or an inline helper. Patch 42/44 - net/sxe2: align command structs with historical kernel layout Warning: sxe2_tm_res changes size from 4 to 2 bytes, and it is used as both request and response buffer with sizeof(): struct sxe2_tm_res tm_resp; sxe2_drv_cmd_params_fill(adapter, ¶m, SXE2_DRV_CMD_SCHED_ROOT_TREE_ALLOC, NULL, 0, &tm_resp, sizeof(tm_resp)); out_len for ROOT_TREE_ALLOC and for SCHED_TM_ADD_MID_NODE / SCHED_TM_ADD_QUEUE_NODE drops from 4 to 2. If the firmware still writes the historical 4 bytes this overruns a stack object. Please confirm against the firmware side and say so in the commit message, since this is the one hunk in the patch that changes anything observable. Note that tm_resp in sxe2_drv_root_tree_alloc() is the only one of the four sxe2_tm_res objects left uninitialized; the other three use "= {0}". Worth making consistent while touching this. Warning: the commit message lists - sxe2_tm_add_mid_msg: drop packed attribute - sxe2_tm_add_queue_msg: drop packed attribute but the patch does not touch either struct. Both still carry __rte_aligned(4) __rte_packed_begin / __rte_packed_end in the applied tree. Drop those two bullets, or make the change. Info: the sxe2_drv_link_info_resp, sxe2_tm_info, sxe2_drv_sfp_req and sxe2_drv_sfp_resp hunks do not change any member offset or any struct size. For sxe2_drv_link_info_resp the retained __rte_aligned(4) pads the size back to 8 after rsv[3] is removed; for the other three the packed and unpacked layouts are already identical because every member is naturally aligned. Saying this in the commit message would make clear that sxe2_tm_res is the only hunk that needs testing. Patch 43/44 - common/sxe2: fix ioctl channel log and close handling Info: the cmd_fd/bar_idx swap is fixed, but the remaining two conversions are still mislabelled - "src=" prints the raw offset and "offset=" prints SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset): PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64 ", src=0x%"PRIx64", offset=0x%"PRIx64"", cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); "offset=" and "pci_offset=" would read correctly. Patches with no findings: 01, 02, 03, 04, 05, 07, 08, 09, 11, 12, 13, 16, 17, 18, 19, 20, 24, 25, 27, 28, 29, 32, 35, 36, 38, 39, 40, 41, 44. ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v4 01/44] common/sxe2: fix null pointer in class driver remove 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 2026-08-27 2:36 ` [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:36 ` [PATCH v4 02/44] common/sxe2: allow munmap during kernel reset liujie5 ` (42 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 02/44] common/sxe2: allow munmap during kernel reset 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 2026-08-27 2:36 ` [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-27 2:36 ` [PATCH v4 01/44] common/sxe2: fix null pointer in class driver remove liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:36 ` [PATCH v4 03/44] net/sxe2: fix VF PCI device ID liujie5 ` (41 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 03/44] net/sxe2: fix VF PCI device ID 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (2 preceding siblings ...) 2026-08-27 2:36 ` [PATCH v4 02/44] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:36 ` [PATCH v4 04/44] net/sxe2: fix MSIX register width in PF map table liujie5 ` (40 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 04/44] net/sxe2: fix MSIX register width in PF map table 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (3 preceding siblings ...) 2026-08-27 2:36 ` [PATCH v4 03/44] net/sxe2: fix VF PCI device ID liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:36 ` [PATCH v4 05/44] net/sxe2: restore pf and port index caps assignment liujie5 ` (39 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 05/44] net/sxe2: restore pf and port index caps assignment 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (4 preceding siblings ...) 2026-08-27 2:36 ` [PATCH v4 04/44] net/sxe2: fix MSIX register width in PF map table liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:36 ` [PATCH v4 06/44] net/sxe2: fix VSI lifecycle management liujie5 ` (38 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 06/44] net/sxe2: fix VSI lifecycle management 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (5 preceding siblings ...) 2026-08-27 2:36 ` [PATCH v4 05/44] net/sxe2: restore pf and port index caps assignment liujie5 @ 2026-08-27 2:36 ` liujie5 2026-08-27 2:37 ` [PATCH v4 07/44] net/sxe2: initialize stats in representor device init liujie5 ` (37 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..ba4cc7414e 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -230,7 +230,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +283,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -357,4 +358,5 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 07/44] net/sxe2: initialize stats in representor device init 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (6 preceding siblings ...) 2026-08-27 2:36 ` [PATCH v4 06/44] net/sxe2: fix VSI lifecycle management liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 08/44] net/sxe2: use base device name for representor naming liujie5 ` (36 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 08/44] net/sxe2: use base device name for representor naming 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (7 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 07/44] net/sxe2: initialize stats in representor device init liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 09/44] net/sxe2: propagate LSC event to VF representors liujie5 ` (35 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 09/44] net/sxe2: propagate LSC event to VF representors 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (8 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 08/44] net/sxe2: use base device name for representor naming liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 10/44] net/sxe2: validate IPsec key length against maximum limit liujie5 ` (34 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..ba764dd5e4 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 10/44] net/sxe2: validate IPsec key length against maximum limit 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (9 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 09/44] net/sxe2: propagate LSC event to VF representors liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 11/44] net/sxe2: rename representor VSI ID fields liujie5 ` (33 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add validation in sxe2_security_valid_key to ensure the source key length does not exceed SXE2_IPSEC_MAX_KEY_LEN, preventing potential buffer overflows when processing keys longer than the supported maximum. Also clear the security context pointer after releasing the security session during uninit. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ipsec.c | 5 +++++ drivers/net/sxe2/sxe2_security.c | 1 + 2 files changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ipsec.c b/drivers/net/sxe2/sxe2_ipsec.c index e783a51b85..622fd1adfe 100644 --- a/drivers/net/sxe2/sxe2_ipsec.c +++ b/drivers/net/sxe2/sxe2_ipsec.c @@ -254,6 +254,11 @@ static bool sxe2_security_valid_key(uint16_t src_key, uint16_t max_key, goto l_end; } + if (src_key > SXE2_IPSEC_MAX_KEY_LEN) { + is_valid = false; + goto l_end; + } + is_valid = true; l_end: diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 11/44] net/sxe2: rename representor VSI ID fields 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (10 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 10/44] net/sxe2: validate IPsec key length against maximum limit liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 12/44] net/sxe2: clean up duplicate function declarations liujie5 ` (32 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 12/44] net/sxe2: clean up duplicate function declarations 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (11 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 11/44] net/sxe2: rename representor VSI ID fields liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 13/44] net/sxe2: fix null VSI dereference in device info liujie5 ` (31 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 13/44] net/sxe2: fix null VSI dereference in device info 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (12 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 12/44] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 14/44] net/sxe2: fill MAC and queue counts " liujie5 ` (30 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 14/44] net/sxe2: fill MAC and queue counts in device info 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (13 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 13/44] net/sxe2: fix null VSI dereference in device info liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 15/44] net/sxe2: fix QinQ and RSS offload capability report liujie5 ` (29 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fill max_mac_addrs, nb_rx_queues and nb_tx_queues in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses and the queue counts. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85dee6b2c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | @@ -912,6 +913,8 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; + dev_info->nb_rx_queues = dev->data->nb_rx_queues; + dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 15/44] net/sxe2: fix QinQ and RSS offload capability report 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (14 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 14/44] net/sxe2: fill MAC and queue counts " liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 16/44] net/sxe2: use regular write for mapped registers liujie5 ` (28 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Advertise RTE_ETH_RX_OFFLOAD_RSS_HASH unconditionally and report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85dee6b2c..fb7f14fd44 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,11 +804,9 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | - RTE_ETH_RX_OFFLOAD_TCP_LRO; + RTE_ETH_RX_OFFLOAD_TCP_LRO | + RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | @@ -855,14 +853,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -936,7 +942,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -974,6 +980,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 16/44] net/sxe2: use regular write for mapped registers 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (15 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 15/44] net/sxe2: fix QinQ and RSS offload capability report liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:37 ` [PATCH v4 17/44] net/sxe2: move PCI register read macro to common header liujie5 ` (27 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index fb7f14fd44..96b437c6a9 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1443,7 +1443,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 17/44] net/sxe2: move PCI register read macro to common header 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (16 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 16/44] net/sxe2: use regular write for mapped registers liujie5 @ 2026-08-27 2:37 ` liujie5 2026-08-27 2:38 ` [PATCH v4 18/44] net/sxe2: validate PCI map resource type liujie5 ` (26 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 18/44] net/sxe2: validate PCI map resource type 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (17 preceding siblings ...) 2026-08-27 2:37 ` [PATCH v4 17/44] net/sxe2: move PCI register read macro to common header liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 19/44] net/sxe2: guard PCI BAR unmap when not initialized liujie5 ` (25 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 96b437c6a9..7646f6b309 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1556,6 +1556,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 19/44] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (18 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 18/44] net/sxe2: validate PCI map resource type liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 20/44] net/sxe2: fix null dereference in dev uninit liujie5 ` (24 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7646f6b309..05a57548e7 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1777,14 +1777,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1795,7 +1794,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 20/44] net/sxe2: fix null dereference in dev uninit 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (19 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 19/44] net/sxe2: guard PCI BAR unmap when not initialized liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 21/44] net/sxe2: fix duplicated cleanup in dev close liujie5 ` (23 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 05a57548e7..6222a319af 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2078,9 +2078,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 21/44] net/sxe2: fix duplicated cleanup in dev close 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (20 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 20/44] net/sxe2: fix null dereference in dev uninit liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 22/44] net/sxe2: align dev init and cleanup order liujie5 ` (22 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_close() calls sxe2_switchdev_uninit() and sxe2_dev_pci_map_uinit() twice, and releases resources in an order that does not match the initialization sequence. Remove the duplicated calls and align the teardown order with the device init order. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 6222a319af..1ffaf9cb9f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2045,17 +2045,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 22/44] net/sxe2: align dev init and cleanup order 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (21 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 21/44] net/sxe2: fix duplicated cleanup in dev close liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 23/44] net/sxe2: simplify switchdev representor matching liujie5 ` (21 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_eth_init() to be called before sxe2_sw_init() and rearrange the error cleanup labels so that resources are torn down in the reverse order of initialization. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 1ffaf9cb9f..72aae84ae3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1946,6 +1946,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1958,12 +1964,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2018,12 +2018,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_rss_err: sxe2_security_uinit(dev); init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 23/44] net/sxe2: simplify switchdev representor matching 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (22 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 22/44] net/sxe2: align dev init and cleanup order liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 24/44] net/sxe2: rename fnav cid manager symbols to flow liujie5 ` (20 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_match() encodes the kernel representor ID and compares it against each requested port, which is fragile. Match the PF number and VF ID directly against the switchdev representor info instead, and drop the sxe2_switchdev_repr_id_encode_get() helper. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 70 +++++++++++++++++----------------- drivers/net/sxe2/sxe2_ethdev.h | 3 -- 2 files changed, 35 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 72aae84ae3..7ba73aea6f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2153,42 +2153,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx = UINT16_MAX; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2201,15 +2184,32 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) + break; + } + if (port_idx == req_eth_da->nb_ports) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf", + adapter->switchdev_info.pf_num); + rte_errno = EBUSY; + return false; + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index f2557b28c3..e818578319 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 24/44] net/sxe2: rename fnav cid manager symbols to flow 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (23 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 23/44] net/sxe2: simplify switchdev representor matching liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 25/44] net/sxe2: move tunnel port helpers into flow module liujie5 ` (19 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename the sxe2_fnav_cid_mgr, sxe2_fnav_cid_mgr_list_t, sxe2_fnav_count_resource and sxe2_fnav_get_filter_cid symbols to the sxe2_flow_* prefix for consistency with the flow module naming. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 +- drivers/net/sxe2/sxe2_cmd_chnl.h | 2 +- drivers/net/sxe2/sxe2_flow.c | 46 ++++++++++++++--------------- drivers/net/sxe2/sxe2_flow.h | 6 ++-- drivers/net/sxe2/sxe2_flow_define.h | 12 ++++---- 5 files changed, 34 insertions(+), 34 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..3229c72597 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1800,7 +1800,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 294ac15db4..cfea1a1f0e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -159,7 +159,7 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..a33b8606df 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,16 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1112,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1143,13 +1143,13 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; if (user_id == 0) { TAILQ_REMOVE(cid_mgr_list, mgr, next); @@ -1170,14 +1170,14 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; @@ -1218,7 +1218,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,7 +1348,7 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) adapter->flow_ctxt.hw_res.count_type = adapter->devargs.fnav_stat_type; @@ -1370,10 +1370,10 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; ret = sxe2_flow_flush(dev, &error); if (ret) diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..8a5d871978 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,18 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 25/44] net/sxe2: move tunnel port helpers into flow module 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (24 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 24/44] net/sxe2: rename fnav cid manager symbols to flow liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 26/44] net/sxe2: add ACL engine event statistics support liujie5 ` (18 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_flow_parse_pattern_ipip, sxe2_flow_add_udp_tunnel_port and sxe2_flow_add_tunnel_port from sxe2_flow_parse_pattern.c into sxe2_flow.c as static helpers, and drop the public declaration of sxe2_flow_add_tunnel_port from the header, keeping the tunnel port handling internal to the flow module. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 113 +++++++++++++++++++++ drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 --------------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 -- 3 files changed, 113 insertions(+), 119 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index a33b8606df..cd39385340 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -550,6 +550,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..69d83a6ea6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -37,10 +37,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, struct rte_flow_error *error, struct sxe2_flow *flow); -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 26/44] net/sxe2: add ACL engine event statistics support 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (25 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 25/44] net/sxe2: move tunnel port helpers into flow module liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:38 ` [PATCH v4 27/44] net/sxe2: guard Rx queue event FD free in unregister liujie5 ` (17 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for the ACL flow engine to track packet hits and bytes, enabling flow aging and traffic monitoring for ACL rules. - Add acl-stat-type devarg to configure the statistics type - Implement sxe2_drv_flow_acl_get_stat_id/free_stat/query_stat - Handle the ACL engine in flow create/destroy/query paths - Add fnav_hw_res and acl_hw_res count resources Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 11 +++ drivers/net/sxe2/sxe2_cmd_chnl.c | 71 ++++++++++++++++++ drivers/net/sxe2/sxe2_cmd_chnl.h | 7 ++ drivers/net/sxe2/sxe2_drv_cmd.h | 19 +++++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 23 ++++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 89 ++++++++++++++++++----- drivers/net/sxe2/sxe2_flow_define.h | 5 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 25 +++++-- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 224 insertions(+), 31 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..c5b400a8ba 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,6 +98,17 @@ Runtime Configuration Default value is 3 (count both packets and bytes). +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL flow engine statistics type + used for flow rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). + - ``drv-sw-stats`` parameter [int] This parameter controls whether per-packet software statistics (SW stats) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3229c72597..16a2c3fea4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1829,6 +1829,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_acl_query_stat_req req = { 0 }; + struct sxe2_drv_acl_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index cfea1a1f0e..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -161,6 +161,13 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, struct sxe2_flow_cid_mgr *mgr); +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..cc71e2364e 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -668,6 +668,18 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_fc_get_resp { uint8_t rsv[3]; } __rte_packed_end; +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_req { + uint32_t stat_id; + uint32_t stat_ctrl; + uint32_t is_clear; +} __rte_packed_end; + +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_resp { + uint32_t stat_index; + uint64_t stat_hits; + uint64_t stat_bytes; +} __rte_packed_end; + enum sxe2_drv_cmd_module { SXE2_DRV_CMD_MODULE_HANDSHAKE = 0, SXE2_DRV_CMD_MODULE_DEV = 1, @@ -824,6 +836,13 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2), + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 3), + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7ba73aea6f..19f81f47c9 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -985,11 +986,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -997,19 +998,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1191,13 +1192,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2368,6 +2376,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index e818578319..e9f78fe57f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -135,6 +135,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cd39385340..d82d3bbd02 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1204,13 +1204,23 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1233,7 +1243,10 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1244,7 +1257,7 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1260,13 +1273,26 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } else { + PMD_LOG_ERR(DRV, + "Failed to free flow count, unknown engine type: %d.", + flow->engine_type); + ret = -ENOTSUP; + return ret; + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1287,13 +1313,19 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1310,7 +1342,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1461,12 +1501,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1485,13 +1531,13 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) struct rte_flow_error error; struct sxe2_flow_cid_mgr *mgr = NULL; struct sxe2_flow_cid_mgr *temp = NULL; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1500,5 +1546,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 8a5d871978..d04499f5cb 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -100,7 +100,7 @@ TAILQ_HEAD(rte_flow_list_t, rte_flow); struct sxe2_flow_cid_mgr { TAILQ_ENTRY(sxe2_flow_cid_mgr) next; - uint16_t stat_index; + uint32_t stat_index; uint32_t user_id; uint32_t driver_id; uint32_t count_type; @@ -118,7 +118,8 @@ struct sxe2_flow_count_resource { struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_flow_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..db70b146c6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -953,7 +953,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -988,7 +989,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { @@ -1037,11 +1039,24 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, if (engine_type == SXE2_FLOW_ENGINE_FNAV) { sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); act_count = action->conf; - flow->action.count.user_id = act_count->id; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++adapter->flow_ctxt.fnav_hw_res.global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) + if (flow->action.count.user_id == 0) { flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; + ++adapter->flow_ctxt.acl_hw_res.global_index; + } action_num[SXE2_FLOW_ACTION_COUNT]++; } else { rte_flow_error_set(error, ENOTSUP, diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 27/44] net/sxe2: guard Rx queue event FD free in unregister 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (26 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 26/44] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-27 2:38 ` liujie5 2026-08-27 2:39 ` [PATCH v4 28/44] net/sxe2: refactor primary process MP message handling liujie5 ` (16 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_rxq_intr_unregister() frees irq_ctxt->rxq_event_fd outside the rxq_event_fd NULL check. Move the free and NULL assignment inside the guard so the buffer is only released when it was allocated. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index ba764dd5e4..4e5339e24b 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -881,12 +881,11 @@ static void sxe2_rxq_intr_unregister(struct rte_eth_dev *dev) (void)sxe2_drv_dev_rxq_irq_set(adapter->cdev, i, &efd, 1); sxe2_rxq_intr_efd_free(irq_ctxt->rxq_event_fd[i]); } + rte_free(irq_ctxt->rxq_event_fd); + irq_ctxt->rxq_event_fd = NULL; } - rte_free(irq_ctxt->rxq_event_fd); - irq_ctxt->rxq_event_fd = NULL; rte_intr_vec_list_free(intr_handle); - rte_intr_nb_efd_set(intr_handle, 0); rte_intr_max_intr_set(intr_handle, 0); } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 28/44] net/sxe2: refactor primary process MP message handling 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (27 preceding siblings ...) 2026-08-27 2:38 ` [PATCH v4 27/44] net/sxe2: guard Rx queue event FD free in unregister liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 29/44] net/sxe2: refactor Tx queue reset operations liujie5 ` (15 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the multi-process work logic into the sxe2_mp_do_primary_work helper and operate on a copy of the request in the primary handler so the original message is not modified. Simplify the reply construction and return -ENOENT instead of -EINVAL when no response is received from the primary process. Fixes: 5db446ba97b0 ("net/sxe2: support statistics and multi-process") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_mp.c | 59 ++++++++++++++++++++++---------------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 29/44] net/sxe2: refactor Tx queue reset operations 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (28 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 28/44] net/sxe2: refactor primary process MP message handling liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 30/44] net/sxe2: unify vectorized Tx buffer handling liujie5 ` (14 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the descriptor ring reset loop into a sxe2_tx_queue_desc_ring_reset helper and reuse it from both the scalar and vectorized queue reset paths. Add a sxe2_tx_queue_reset_vec entry point for vectorized queues, export sxe2_tx_buffer_ring_free for reuse outside the module (clearing the buffer ring pointer after freeing it), and add sxe2_tx_vec_ops_get to build the vectorized Tx queue operations table used by the vector path setup. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_tx.c | 42 +++++++++++++++++++++++--------- drivers/net/sxe2/sxe2_tx.h | 4 +++ drivers/net/sxe2/sxe2_txrx_vec.c | 16 +++++++++++- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + 4 files changed, 51 insertions(+), 12 deletions(-) diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..9cfa565548 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,19 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void) +{ + static const struct sxe2_txq_ops ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, + }; + + return ops; +} + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -233,7 +246,8 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); continue; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops_get(); + txq->ops.queue_reset(txq); } return ret; } diff --git a/drivers/net/sxe2/sxe2_txrx_vec.h b/drivers/net/sxe2/sxe2_txrx_vec.h index c139aed776..b9bc4f9c27 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.h +++ b/drivers/net/sxe2/sxe2_txrx_vec.h @@ -89,6 +89,7 @@ uint16_t sxe2_rx_pkts_scattered_vec_neon_offload(void *rx_queue, struct rte_mbuf uint16_t sxe2_tx_pkts_vec_neon_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); #endif +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void); int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev); int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 30/44] net/sxe2: unify vectorized Tx buffer handling 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (29 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 29/44] net/sxe2: refactor Tx queue reset operations liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 31/44] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 ` (13 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add a union of the scalar and vectorized buffer ring pointers to the Tx queue structure so the vectorized path can use sxe2_tx_buffer_vec directly. Rename the mbuf fill helper to sxe2_tx_pkts_mbuf_fill_vec, switch the vectorized Tx burst and mbuf release paths to the buffer_ring_vec member, and drop the AVX512-specific fill handling and conditional branching. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_txrx_vec.c | 57 ++---- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++++++-------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- 7 files changed, 178 insertions(+), 265 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 9cfa565548..7c5da33dd5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -170,66 +170,31 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - dev = &rte_eth_devices[txq->port_id]; - - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { if (buffer_vec[i].mbuf != NULL) { rte_pktmbuf_free_seg(buffer_vec[i].mbuf); buffer_vec[i].mbuf = NULL; } } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; - } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; + for ( ; i < txq->next_use; ++i) { + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } } diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..0b139b8269 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,12 +34,58 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << + SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,18 +105,26 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -82,14 +136,23 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; @@ -150,22 +213,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -208,9 +273,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -267,23 +333,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -442,25 +491,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -480,7 +543,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -515,55 +579,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -587,12 +644,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 31/44] net/sxe2: refine vectorized Tx/Rx mode setup 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (30 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 30/44] net/sxe2: unify vectorized Tx buffer handling liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 32/44] net/sxe2: fix RSS action attribute validation liujie5 ` (12 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Set rte_eth_tx_pkt_prepare_dummy for the simple and vectorized Tx paths instead of leaving the prepare callback unset, and split the NEON simple/offload mode selection based on the offload flag. Log the selected Tx/Rx mode flags and apply the default Rx free threshold when the configured value is zero. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_rx.c | 3 ++- drivers/net/sxe2/sxe2_txrx.c | 19 +++++++++++++------ 2 files changed, 15 insertions(+), 7 deletions(-) diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..3830c676d7 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..d27d2ce630 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,25 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; - } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +586,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 32/44] net/sxe2: fix RSS action attribute validation 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (31 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 31/44] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 33/44] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 ` (11 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The rss->level/key_len/queue_num checks only set the rte_flow_error but still return 0 (success), so invalid RSS configurations are accepted instead of being rejected with ENOTSUP. Return the error code from the validation checks, matching the behavior in the V3 implementation. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow_parse_action.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index db70b146c6..b0275321be 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -12,7 +12,7 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss *rss, struct rte_flow_error *error) { - int32_t ret = ENOTSUP; + int32_t ret = -ENOTSUP; switch (rss->func) { case RTE_ETH_HASH_FUNCTION_DEFAULT: case RTE_ETH_HASH_FUNCTION_TOEPLITZ: @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 33/44] net/sxe2: restore PF-only guard in udp tunnel port add 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (32 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 32/44] net/sxe2: fix RSS action attribute validation liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 34/44] net/sxe2: restore link update call in status query liujie5 ` (10 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_udp_tunnel_port_add_common() lost the check that restricts UDP tunnel port configuration to PF devices (not VF or representor), so VF/representor devices can now attempt to add UDP tunnel ports, which the hardware does not support. Restore the PF-only guard returning -ENOTSUP, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 19f81f47c9..0ddc0e1e0e 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 34/44] net/sxe2: restore link update call in status query 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (33 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 33/44] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 35/44] net/sxe2: validate representor ID against VF count liujie5 ` (9 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_mac_link_status_get() no longer calls sxe2_link_update() after refreshing the link context, so the ethdev link state is only refreshed during device init (sxe2_link_update_init) and never updated when link status is queried at runtime, including on LSC interrupt events. Move the sxe2_link_update() call back into sxe2_drv_mac_link_status_get() and simplify sxe2_link_update_init() accordingly, matching the V3 implementation. Fixes: 1d7fd921beef ("net/sxe2: support link update") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 ++ drivers/net/sxe2/sxe2_mac.c | 9 +-------- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 16a2c3fea4..705d259412 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -412,6 +412,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) { int32_t ret = 0; struct sxe2_common_device *cdev = adapter->cdev; + struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; struct sxe2_drv_cmd_params param = {0}; struct sxe2_drv_link_info_resp resp = {0}; @@ -425,6 +426,7 @@ int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter) } adapter->link_ctxt.speed = resp.speed; adapter->link_ctxt.link_up = resp.status; + (void)sxe2_link_update(dev, 0); l_end: return ret; diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..7dbea92670 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,18 +448,11 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - (void)sxe2_link_update(dev, 0); - -l_end: return ret; } int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 35/44] net/sxe2: validate representor ID against VF count 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (34 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 34/44] net/sxe2: restore link update call in status query liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 36/44] net/sxe2: use primary VSI ID for representor VSI liujie5 ` (8 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_private_data_init() indexes parent_adapter->repr_ctxt.repr_vf_id[repr_id] without checking that repr_id is within the number of configured VFs, which can access out of bounds when an invalid representor ID is passed. Add a bounds check on repr_id against repr_ctxt.nb_vf and return -EINVAL on the error path. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..d0304ccc94 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,6 +312,12 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; + if (repr_id >= parent_adapter->repr_ctxt.nb_vf) { + PMD_LOG_ERR(INIT, "repr_id %u exceed max vf %u", + repr_id, parent_adapter->repr_ctxt.nb_vf); + ret = -EINVAL; + goto l_free; + } repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 36/44] net/sxe2: use primary VSI ID for representor VSI 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (35 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 35/44] net/sxe2: validate representor ID against VF count liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:39 ` [PATCH v4 37/44] net/sxe2: wrap command params fill debug log in macro liujie5 ` (7 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> repr_priv_data->repr_vf_vsi_id is assigned with a ternary that falls back to the backup (dpdk) VSI ID when the kernel VSI ID is invalid. The V3 implementation assigns it directly from repr_vf_primary_vsi_id. Align with the V3 implementation by assigning repr_vf_vsi_id from repr_vf_primary_vsi_id. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index d0304ccc94..81ced7b855 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -323,11 +323,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; + repr_priv_data->repr_vf_vsi_id = repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 37/44] net/sxe2: wrap command params fill debug log in macro 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (36 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 36/44] net/sxe2: use primary VSI ID for representor VSI liujie5 @ 2026-08-27 2:39 ` liujie5 2026-08-27 2:40 ` [PATCH v4 38/44] net/sxe2: restore Rx queue buffer split fill support liujie5 ` (6 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_cmd_params_fill() passes the opcode string as a parameter to __sxe2_drv_cmd_params_fill() just to emit a debug log, and the debug log is executed unconditionally on every command fill. Move the PMD_DEV_LOG_DEBUG into the macro body wrapped in a do/while block, dropping the opc_str parameter so the opcode stringization is performed at the call site and the macro is a proper multi-statement block. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 705d259412..b17d80d917 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,8 +43,10 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) - + do { \ + PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", #opc); \ + __sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len); \ + } while (0) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 38/44] net/sxe2: restore Rx queue buffer split fill support 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (37 preceding siblings ...) 2026-08-27 2:39 ` [PATCH v4 37/44] net/sxe2: wrap command params fill debug log in macro liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 39/44] net/sxe2: skip tunnel config fill on get failure liujie5 ` (5 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The V4 branch dropped sxe2_rxq_buf_split_fill() and the buffer split handling in sxe2_rxq_ctxt_cfg_fill(), so the Rx buffer split offload (RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) is advertised in device info but the per-queue context never configures split_en/split_type_mask/ hdr_len, and buffer split packets are not handled correctly. Restore the sxe2_rxq_buf_split_fill() helper and the buffer split branch in sxe2_rxq_ctxt_cfg_fill(), matching the V3 implementation. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 88 ++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b17d80d917..ce74af87cc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -194,6 +194,84 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + uint32_t proto_hdr; + + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + return -EINVAL; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + goto l_end; + } + + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + return -ENOTSUP; +l_end: + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + return 0; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -227,7 +305,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 39/44] net/sxe2: skip tunnel config fill on get failure 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (38 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 38/44] net/sxe2: restore Rx queue buffer split fill support liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 40/44] net/sxe2: skip flow id assignment on filter add failure liujie5 ` (4 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_udp_tunnel_get() fills tunnel_config fields even when the firmware command fails, so a failed get overwrites the config with the (zero-initialized) response data instead of leaving it intact. Return early with the error code when sxe2_drv_cmd_exec() fails, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index ce74af87cc..c5bd73244b 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1651,15 +1651,17 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; tunnel_config->fw_dst_en = resp.dst; tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; - +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 40/44] net/sxe2: skip flow id assignment on filter add failure 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (39 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 39/44] net/sxe2: skip tunnel config fill on get failure liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 41/44] net/sxe2: fix command channel log messages liujie5 ` (3 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_flow_filter_add() assigns flow->flow_id from the response even when the firmware command fails, overwriting any previously set flow id with the zero-initialized response value. Return early on command failure so flow->flow_id is preserved, and set flow->create_err on both the success and error paths. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index c5bd73244b..fa73b8a8b7 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1819,9 +1819,13 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + goto l_end; + } flow->flow_id = resp.flow_id; + +l_end: flow->create_err = ret; return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 41/44] net/sxe2: fix command channel log messages 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (40 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 40/44] net/sxe2: skip flow id assignment on filter add failure liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 42/44] net/sxe2: align command structs with historical kernel layout liujie5 ` (2 subsequent siblings) 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Several error/warning messages in sxe2_cmd_chnl.c are inaccurate or lost context: - vsi_info_get: message lost the vsi id; restore it - rxq_bind_irq/rxq_unbind_irq: message lost the rxq index; restore it - promisc_config: fix "promic" typo in the message - queue_info_get_update/rxq_mapping_set: incorrect "get queue info map"/"get dev caps" wording; use "rx queue mapping failed" - txq_mapping_set: "Rx queue" should read "Tx queue"; incorrect "get dev caps" wording should read "tx queue mapping failed" Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index fa73b8a8b7..9bd6e3355f 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -480,7 +480,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -538,7 +538,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -558,7 +558,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -759,7 +759,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1684,7 +1684,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); goto l_end; } @@ -1728,7 +1728,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1745,7 +1745,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1759,7 +1759,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 42/44] net/sxe2: align command structs with historical kernel layout 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (41 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 41/44] net/sxe2: fix command channel log messages liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 43/44] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The sxe2_drv_cmd.h command structures must match the layout used by historical SXE2 kernel versions so the same firmware command ABI is shared. Several structures were declared with __rte_packed_begin/ __rte_packed_end and extra rsv padding that the kernel layout does not have: - sxe2_drv_link_info_resp: drop rsv[3] padding - sxe2_tm_res: drop rsv[2] padding and packed attribute - sxe2_tm_info: drop packed attribute - sxe2_tm_add_mid_msg: drop packed attribute - sxe2_tm_add_queue_msg: drop packed attribute - sxe2_drv_sfp_req: drop packed attribute - sxe2_drv_sfp_resp: drop packed attribute Keep the structure members as-is so the command ABI is compatible with the historical kernel driver. Fixes: 9c894f75113f ("net/sxe2: support TM hierarchy and shaping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index cc71e2364e..5274b59a6a 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,18 +347,17 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { uint16_t parent_teid; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 43/44] common/sxe2: fix ioctl channel log and close handling 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (42 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 42/44] net/sxe2: align command structs with historical kernel layout liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 44 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Compare sxe2_ioctl_chnl.c against the reference implementation and fix the following discrepancies: - sxe2_drv_dev_close: only log the closed fd when it is valid, move PMD_LOG_INFO inside the fd >= 0 check - sxe2_drv_dev_mmap: fix swapped format arguments in the debug log (cmd_fd and bar_idx were passed in the wrong order) - sxe2_drv_dev_dma_unmap: use PMD_LOG_ERR instead of PMD_LOG_INFO for the ioctl failure message Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index 3e2fbf572f..e62ca42a8f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -107,9 +107,11 @@ sxe2_drv_dev_close(struct sxe2_common_device *cdev) { int32_t fd = SXE2_CDEV_TO_CMD_FD(cdev); - if (fd >= 0) + if (fd >= 0) { close(fd); - PMD_LOG_INFO(COM, "closed device fd=%d", fd); + PMD_LOG_INFO(COM, "closed device fd=%d", fd); + } + SXE2_CDEV_TO_CMD_FD(cdev) = SXE2_CMD_FD_INVALID; } @@ -350,7 +352,7 @@ void } PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", src=0x%"PRIx64", offset=0x%"PRIx64"", - bar_idx, cmd_fd, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); + cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); virt = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, cmd_fd, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); @@ -477,7 +479,7 @@ sxe2_drv_dev_dma_unmap(struct sxe2_common_device *cdev, uint64_t iova) pthread_mutex_lock(&cdev->config.lock); ret = ioctl(cmd_fd, SXE2_COM_CMD_DMA_UNMAP, &cmd_params); if (ret < 0) { - PMD_LOG_INFO(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", + PMD_LOG_ERR(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", cmd_fd, ret, strerror(errno)); ret = -EIO; pthread_mutex_unlock(&cdev->config.lock); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 ` (43 preceding siblings ...) 2026-08-27 2:40 ` [PATCH v4 43/44] common/sxe2: fix ioctl channel log and close handling liujie5 @ 2026-08-27 2:40 ` liujie5 2026-08-28 3:23 ` [PATCH v5 00/45] net/sxe2: add Stars SXE2 net driver with fixes liujie5 ` (45 more replies) 44 siblings, 46 replies; 278+ messages in thread From: liujie5 @ 2026-08-27 2:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The drv-sw-stats devarg is no longer supported. Remove its parameter description from the Runtime Configuration section. The "Receive Software Statistics" xstats section is kept because the rx_sw_* counters are still accumulated in the Rx data path and reported through rte_eth_xstats_get(). Fixes: 9e95b2b3859c ("doc: update sxe2 guide and features") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 31 ++----------------------------- 1 file changed, 2 insertions(+), 29 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index c5b400a8ba..fe4f9f916b 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -109,30 +109,6 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. - - ``no-sched-mode`` parameter [int] This parameter enables non-scheduling mode (no-sched mode). @@ -208,8 +184,7 @@ reflect the actual packets processed by the driver. Receive Software Statistics These counters are collected in the Rx data path - when ``drv-sw-stats=1`` is configured (see the ``drv-sw-stats`` devarg above). - When ``drv-sw-stats`` is disabled (default), these xstats report zero. + on every received packet. - ``rx_sw_unicast_packets``: Number of unicast packets received. - ``rx_sw_multicast_packets``: Number of multicast packets received. @@ -217,10 +192,8 @@ Receive Software Statistics - ``rx_sw_drop_packets``: Number of packets dropped in the Rx data path. - ``rx_sw_drop_bytes``: Number of bytes dropped in the Rx data path. - When ``drv-sw-stats`` is enabled, the basic counters - ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) + The basic counters ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) also reflect the software-accumulated packet and byte counts. - Otherwise, they are reported from hardware counters. Fnav Flow Engine Statistics The Fnav flow engine statistics type is controlled by -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 00/45] net/sxe2: add Stars SXE2 net driver with fixes 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 01/45] common/sxe2: fix null pointer in class driver remove liujie5 ` (44 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> This series adds the Stars SXE2 network driver together with a set of fixes accumulated while validating the driver against the historical kernel implementation and reviewing the code. This is the v5 revision. Changes since v4 address the community review of the v4 series: - Drop the ineffective IPsec key length check in sxe2_security_valid_key() (the same limit is already enforced at the top of the function) and keep only the security context pointer cleanup, which is now its own commit. - Make the QinQ and RSS offload capability gating actually effective: RTE_ETH_TX_OFFLOAD_QINQ_INSERT is removed from the unconditional capability list and only advertised when no port VLAN is configured; RTE_ETH_RX_OFFLOAD_RSS_HASH is advertised only when the RSS offload capability flag is set. - Fix switchdev representor matching so the common devarg forms (e.g. "representor=vf0", bare-number form) that leave nb_ports == 0 are treated as "no PF constraint" instead of being rejected. - Fix the representor VSI teardown: sxe2_vsi_destroy() now unlinks SXE2_VSI_T_DPDK_ESW nodes from other_vsi_list before freeing them. - Restore a scalar Tx fallback on arm64 when NEON is not available so tx_pkt_burst is always installed. - Add the same PF-only guard to the UDP tunnel port delete and clear paths that add already has. - Move sxe2_link_update() out of the command-channel link status query into the two callers, keeping the command layer free of ethdev side effects and avoiding the dev_data dereference. - Evaluate the adapter argument exactly once in the command params fill macro. - Remove ineffective nb_rx_queues/nb_tx_queues assignments from device info (ethdev overwrites them after the PMD callback) and from the representor device info (new commit with a Fixes: tag). - Fix the ioctl mmap debug log labels and reword the commit messages for the security context, command fill macro and command struct alignment commits. Patch 30/44 of the v4 series still bundles unrelated NEON Rx data path changes into the vectorized Tx commit, and patches 21/22 still leave the dev_close and dev_init teardown orders slightly different; these are left for a follow-up. Jie Liu (45): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore pf and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: clear security context pointer on uninit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC and queue counts in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: guard Rx queue event FD free in unregister net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in udp tunnel port add net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow id assignment on filter add failure net/sxe2: fix command channel log messages net/sxe2: align command structs with historical kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-sw-stats parameter documentation net/sxe2: remove ineffective queue counts in representor info doc/guides/nics/sxe2.rst | 40 ++-- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 20 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 199 ++++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 37 +++- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 192 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 15 +- drivers/net/sxe2/sxe2_flow.c | 234 ++++++++++++++++++--- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 39 +++- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_irq.c | 29 ++- drivers/net/sxe2/sxe2_mac.c | 11 +- drivers/net/sxe2/sxe2_mp.c | 59 +++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 16 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 20 +- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 73 +++---- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 10 +- 36 files changed, 948 insertions(+), 673 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v5 01/45] common/sxe2: fix null pointer in class driver remove 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 3:23 ` [PATCH v5 00/45] net/sxe2: add Stars SXE2 net driver with fixes liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 02/45] common/sxe2: allow munmap during kernel reset liujie5 ` (43 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 02/45] common/sxe2: allow munmap during kernel reset 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 3:23 ` [PATCH v5 00/45] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-28 3:23 ` [PATCH v5 01/45] common/sxe2: fix null pointer in class driver remove liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 03/45] net/sxe2: fix VF PCI device ID liujie5 ` (42 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 03/45] net/sxe2: fix VF PCI device ID 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (2 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 02/45] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 ` (41 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 04/45] net/sxe2: fix MSIX register width in PF map table 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (3 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 03/45] net/sxe2: fix VF PCI device ID liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 05/45] net/sxe2: restore pf and port index caps assignment liujie5 ` (40 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 05/45] net/sxe2: restore pf and port index caps assignment 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (4 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 06/45] net/sxe2: fix VSI lifecycle management liujie5 ` (39 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 06/45] net/sxe2: fix VSI lifecycle management 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (5 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 05/45] net/sxe2: restore pf and port index caps assignment liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 07/45] net/sxe2: initialize stats in representor device init liujie5 ` (38 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..dea3f58997 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -131,6 +131,8 @@ static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *v } l_free: + if (vsi->vsi_type == SXE2_VSI_T_DPDK_ESW) + TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); rte_free(vsi); vsi = NULL; @@ -230,7 +232,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +285,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -357,4 +360,5 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 07/45] net/sxe2: initialize stats in representor device init 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (6 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 06/45] net/sxe2: fix VSI lifecycle management liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 08/45] net/sxe2: use base device name for representor naming liujie5 ` (37 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 08/45] net/sxe2: use base device name for representor naming 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (7 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 07/45] net/sxe2: initialize stats in representor device init liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:23 ` [PATCH v5 09/45] net/sxe2: propagate LSC event to VF representors liujie5 ` (36 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 09/45] net/sxe2: propagate LSC event to VF representors 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (8 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 08/45] net/sxe2: use base device name for representor naming liujie5 @ 2026-08-28 3:23 ` liujie5 2026-08-28 3:24 ` [PATCH v5 10/45] net/sxe2: clear security context pointer on uninit liujie5 ` (35 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:23 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..ba764dd5e4 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 10/45] net/sxe2: clear security context pointer on uninit 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (9 preceding siblings ...) 2026-08-28 3:23 ` [PATCH v5 09/45] net/sxe2: propagate LSC event to VF representors liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 11/45] net/sxe2: rename representor VSI ID fields liujie5 ` (34 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_security_uinit() frees the security session but leaves dev->security_ctx pointing at the freed memory. Set dev->security_ctx to NULL after releasing the security context so a later access does not dereference a dangling pointer. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_security.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 11/45] net/sxe2: rename representor VSI ID fields 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (10 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 10/45] net/sxe2: clear security context pointer on uninit liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 12/45] net/sxe2: clean up duplicate function declarations liujie5 ` (33 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 12/45] net/sxe2: clean up duplicate function declarations 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (11 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 11/45] net/sxe2: rename representor VSI ID fields liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 13/45] net/sxe2: fix null VSI dereference in device info liujie5 ` (32 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 13/45] net/sxe2: fix null VSI dereference in device info 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (12 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 12/45] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 14/45] net/sxe2: fill MAC and queue counts " liujie5 ` (31 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 14/45] net/sxe2: fill MAC and queue counts in device info 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (13 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 13/45] net/sxe2: fix null VSI dereference in device info liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 ` (30 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fill max_mac_addrs, nb_rx_queues and nb_tx_queues in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses and the queue counts. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85e34aa1a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 15/45] net/sxe2: fix QinQ and RSS offload capability report 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (14 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 14/45] net/sxe2: fill MAC and queue counts " liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 16/45] net/sxe2: use regular write for mapped registers liujie5 ` (29 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Advertise RTE_ETH_RX_OFFLOAD_RSS_HASH unconditionally and report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85e34aa1a..7a11a93dff 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,15 +804,11 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | RTE_ETH_RX_OFFLOAD_TCP_LRO; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | - RTE_ETH_TX_OFFLOAD_QINQ_INSERT | RTE_ETH_TX_OFFLOAD_MULTI_SEGS | RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE | RTE_ETH_TX_OFFLOAD_IPV4_CKSUM | @@ -855,14 +851,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -934,7 +938,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -972,6 +976,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 16/45] net/sxe2: use regular write for mapped registers 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (15 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 17/45] net/sxe2: move PCI register read macro to common header liujie5 ` (28 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7a11a93dff..589f09c113 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1439,7 +1439,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 17/45] net/sxe2: move PCI register read macro to common header 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (16 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 16/45] net/sxe2: use regular write for mapped registers liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 18/45] net/sxe2: validate PCI map resource type liujie5 ` (27 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 18/45] net/sxe2: validate PCI map resource type 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (17 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 17/45] net/sxe2: move PCI register read macro to common header liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:24 ` [PATCH v5 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 ` (26 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 589f09c113..9ef93b8076 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1552,6 +1552,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 19/45] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (18 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 18/45] net/sxe2: validate PCI map resource type liujie5 @ 2026-08-28 3:24 ` liujie5 2026-08-28 3:25 ` [PATCH v5 20/45] net/sxe2: fix null dereference in dev uninit liujie5 ` (25 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:24 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 9ef93b8076..fdff4ae10f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1773,14 +1773,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1791,7 +1790,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 20/45] net/sxe2: fix null dereference in dev uninit 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (19 preceding siblings ...) 2026-08-28 3:24 ` [PATCH v5 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 ` (24 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index fdff4ae10f..41ea67a607 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2074,9 +2074,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 21/45] net/sxe2: fix duplicated cleanup in dev close 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (20 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 20/45] net/sxe2: fix null dereference in dev uninit liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 22/45] net/sxe2: align dev init and cleanup order liujie5 ` (23 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_close() calls sxe2_switchdev_uninit() and sxe2_dev_pci_map_uinit() twice, and releases resources in an order that does not match the initialization sequence. Remove the duplicated calls and align the teardown order with the device init order. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 41ea67a607..5d14e28d96 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2041,17 +2041,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 22/45] net/sxe2: align dev init and cleanup order 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (21 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 23/45] net/sxe2: simplify switchdev representor matching liujie5 ` (22 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_eth_init() to be called before sxe2_sw_init() and rearrange the error cleanup labels so that resources are torn down in the reverse order of initialization. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d14e28d96..5bce710b29 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1942,6 +1942,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1954,12 +1960,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2014,12 +2014,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_rss_err: sxe2_security_uinit(dev); init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 23/45] net/sxe2: simplify switchdev representor matching 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (22 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 22/45] net/sxe2: align dev init and cleanup order liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 ` (21 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_match() encodes the kernel representor ID and compares it against each requested port, which is fragile. Match the PF number and VF ID directly against the switchdev representor info instead, and drop the sxe2_switchdev_repr_id_encode_get() helper. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 72 +++++++++++++++++----------------- drivers/net/sxe2/sxe2_ethdev.h | 3 -- 2 files changed, 37 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5bce710b29..08986e384f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2149,42 +2149,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2197,15 +2180,34 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + if (req_eth_da->nb_ports > 0) { + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) + break; + } + if (port_idx == req_eth_da->nb_ports) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf", + adapter->switchdev_info.pf_num); + rte_errno = EBUSY; + return false; + } + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index f2557b28c3..e818578319 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 24/45] net/sxe2: rename fnav cid manager symbols to flow 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (23 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 23/45] net/sxe2: simplify switchdev representor matching liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 ` (20 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename the sxe2_fnav_cid_mgr, sxe2_fnav_cid_mgr_list_t, sxe2_fnav_count_resource and sxe2_fnav_get_filter_cid symbols to the sxe2_flow_* prefix for consistency with the flow module naming. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 +- drivers/net/sxe2/sxe2_cmd_chnl.h | 2 +- drivers/net/sxe2/sxe2_flow.c | 46 ++++++++++++++--------------- drivers/net/sxe2/sxe2_flow.h | 6 ++-- drivers/net/sxe2/sxe2_flow_define.h | 12 ++++---- 5 files changed, 34 insertions(+), 34 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..3229c72597 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1800,7 +1800,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 294ac15db4..cfea1a1f0e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -159,7 +159,7 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..a33b8606df 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,16 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1112,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1143,13 +1143,13 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; if (user_id == 0) { TAILQ_REMOVE(cid_mgr_list, mgr, next); @@ -1170,14 +1170,14 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; @@ -1218,7 +1218,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,7 +1348,7 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) adapter->flow_ctxt.hw_res.count_type = adapter->devargs.fnav_stat_type; @@ -1370,10 +1370,10 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; ret = sxe2_flow_flush(dev, &error); if (ret) diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..8a5d871978 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,18 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 25/45] net/sxe2: move tunnel port helpers into flow module 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (24 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 26/45] net/sxe2: add ACL engine event statistics support liujie5 ` (19 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_flow_parse_pattern_ipip, sxe2_flow_add_udp_tunnel_port and sxe2_flow_add_tunnel_port from sxe2_flow_parse_pattern.c into sxe2_flow.c as static helpers, and drop the public declaration of sxe2_flow_add_tunnel_port from the header, keeping the tunnel port handling internal to the flow module. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 113 +++++++++++++++++++++ drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 --------------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 -- 3 files changed, 113 insertions(+), 119 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index a33b8606df..cd39385340 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -550,6 +550,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..69d83a6ea6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -37,10 +37,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, struct rte_flow_error *error, struct sxe2_flow *flow); -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 26/45] net/sxe2: add ACL engine event statistics support 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (25 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 ` (18 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for the ACL flow engine to track packet hits and bytes, enabling flow aging and traffic monitoring for ACL rules. - Add acl-stat-type devarg to configure the statistics type - Implement sxe2_drv_flow_acl_get_stat_id/free_stat/query_stat - Handle the ACL engine in flow create/destroy/query paths - Add fnav_hw_res and acl_hw_res count resources Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 11 +++ drivers/net/sxe2/sxe2_cmd_chnl.c | 71 ++++++++++++++++++ drivers/net/sxe2/sxe2_cmd_chnl.h | 7 ++ drivers/net/sxe2/sxe2_drv_cmd.h | 19 +++++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 23 ++++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 89 ++++++++++++++++++----- drivers/net/sxe2/sxe2_flow_define.h | 5 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 25 +++++-- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 224 insertions(+), 31 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..c5b400a8ba 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,6 +98,17 @@ Runtime Configuration Default value is 3 (count both packets and bytes). +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL flow engine statistics type + used for flow rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). + - ``drv-sw-stats`` parameter [int] This parameter controls whether per-packet software statistics (SW stats) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3229c72597..16a2c3fea4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1829,6 +1829,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_acl_query_stat_req req = { 0 }; + struct sxe2_drv_acl_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index cfea1a1f0e..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -161,6 +161,13 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, struct sxe2_flow_cid_mgr *mgr); +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..cc71e2364e 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -668,6 +668,18 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_fc_get_resp { uint8_t rsv[3]; } __rte_packed_end; +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_req { + uint32_t stat_id; + uint32_t stat_ctrl; + uint32_t is_clear; +} __rte_packed_end; + +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_resp { + uint32_t stat_index; + uint64_t stat_hits; + uint64_t stat_bytes; +} __rte_packed_end; + enum sxe2_drv_cmd_module { SXE2_DRV_CMD_MODULE_HANDSHAKE = 0, SXE2_DRV_CMD_MODULE_DEV = 1, @@ -824,6 +836,13 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2), + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 3), + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 08986e384f..77a31eb8a1 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -981,11 +982,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -993,19 +994,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1187,13 +1188,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2366,6 +2374,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index e818578319..e9f78fe57f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -135,6 +135,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cd39385340..d82d3bbd02 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1204,13 +1204,23 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1233,7 +1243,10 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1244,7 +1257,7 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1260,13 +1273,26 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } else { + PMD_LOG_ERR(DRV, + "Failed to free flow count, unknown engine type: %d.", + flow->engine_type); + ret = -ENOTSUP; + return ret; + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1287,13 +1313,19 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1310,7 +1342,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1461,12 +1501,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1485,13 +1531,13 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) struct rte_flow_error error; struct sxe2_flow_cid_mgr *mgr = NULL; struct sxe2_flow_cid_mgr *temp = NULL; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1500,5 +1546,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 8a5d871978..d04499f5cb 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -100,7 +100,7 @@ TAILQ_HEAD(rte_flow_list_t, rte_flow); struct sxe2_flow_cid_mgr { TAILQ_ENTRY(sxe2_flow_cid_mgr) next; - uint16_t stat_index; + uint32_t stat_index; uint32_t user_id; uint32_t driver_id; uint32_t count_type; @@ -118,7 +118,8 @@ struct sxe2_flow_count_resource { struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_flow_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..db70b146c6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -953,7 +953,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -988,7 +989,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { @@ -1037,11 +1039,24 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, if (engine_type == SXE2_FLOW_ENGINE_FNAV) { sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); act_count = action->conf; - flow->action.count.user_id = act_count->id; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++adapter->flow_ctxt.fnav_hw_res.global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) + if (flow->action.count.user_id == 0) { flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; + ++adapter->flow_ctxt.acl_hw_res.global_index; + } action_num[SXE2_FLOW_ACTION_COUNT]++; } else { rte_flow_error_set(error, ENOTSUP, diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 27/45] net/sxe2: guard Rx queue event FD free in unregister 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (26 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 26/45] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 28/45] net/sxe2: refactor primary process MP message handling liujie5 ` (17 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_rxq_intr_unregister() frees irq_ctxt->rxq_event_fd outside the rxq_event_fd NULL check. Move the free and NULL assignment inside the guard so the buffer is only released when it was allocated. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index ba764dd5e4..4e5339e24b 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -881,12 +881,11 @@ static void sxe2_rxq_intr_unregister(struct rte_eth_dev *dev) (void)sxe2_drv_dev_rxq_irq_set(adapter->cdev, i, &efd, 1); sxe2_rxq_intr_efd_free(irq_ctxt->rxq_event_fd[i]); } + rte_free(irq_ctxt->rxq_event_fd); + irq_ctxt->rxq_event_fd = NULL; } - rte_free(irq_ctxt->rxq_event_fd); - irq_ctxt->rxq_event_fd = NULL; rte_intr_vec_list_free(intr_handle); - rte_intr_nb_efd_set(intr_handle, 0); rte_intr_max_intr_set(intr_handle, 0); } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 28/45] net/sxe2: refactor primary process MP message handling 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (27 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:25 ` [PATCH v5 29/45] net/sxe2: refactor Tx queue reset operations liujie5 ` (16 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the multi-process work logic into the sxe2_mp_do_primary_work helper and operate on a copy of the request in the primary handler so the original message is not modified. Simplify the reply construction and return -ENOENT instead of -EINVAL when no response is received from the primary process. Fixes: 5db446ba97b0 ("net/sxe2: support statistics and multi-process") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_mp.c | 59 ++++++++++++++++++++++---------------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 29/45] net/sxe2: refactor Tx queue reset operations 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (28 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 28/45] net/sxe2: refactor primary process MP message handling liujie5 @ 2026-08-28 3:25 ` liujie5 2026-08-28 3:26 ` [PATCH v5 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 ` (15 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:25 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the descriptor ring reset loop into a sxe2_tx_queue_desc_ring_reset helper and reuse it from both the scalar and vectorized queue reset paths. Add a sxe2_tx_queue_reset_vec entry point for vectorized queues, export sxe2_tx_buffer_ring_free for reuse outside the module (clearing the buffer ring pointer after freeing it), and add sxe2_tx_vec_ops_get to build the vectorized Tx queue operations table used by the vector path setup. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_tx.c | 42 +++++++++++++++++++++++--------- drivers/net/sxe2/sxe2_tx.h | 4 +++ drivers/net/sxe2/sxe2_txrx_vec.c | 16 +++++++++++- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + 4 files changed, 51 insertions(+), 12 deletions(-) diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..9cfa565548 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,19 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void) +{ + static const struct sxe2_txq_ops ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, + }; + + return ops; +} + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -233,7 +246,8 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); continue; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops_get(); + txq->ops.queue_reset(txq); } return ret; } diff --git a/drivers/net/sxe2/sxe2_txrx_vec.h b/drivers/net/sxe2/sxe2_txrx_vec.h index c139aed776..b9bc4f9c27 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.h +++ b/drivers/net/sxe2/sxe2_txrx_vec.h @@ -89,6 +89,7 @@ uint16_t sxe2_rx_pkts_scattered_vec_neon_offload(void *rx_queue, struct rte_mbuf uint16_t sxe2_tx_pkts_vec_neon_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); #endif +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void); int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev); int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 30/45] net/sxe2: unify vectorized Tx buffer handling 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (29 preceding siblings ...) 2026-08-28 3:25 ` [PATCH v5 29/45] net/sxe2: refactor Tx queue reset operations liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 ` (14 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add a union of the scalar and vectorized buffer ring pointers to the Tx queue structure so the vectorized path can use sxe2_tx_buffer_vec directly. Rename the mbuf fill helper to sxe2_tx_pkts_mbuf_fill_vec, switch the vectorized Tx burst and mbuf release paths to the buffer_ring_vec member, and drop the AVX512-specific fill handling and conditional branching. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_txrx_vec.c | 57 ++---- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++++++-------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- 7 files changed, 178 insertions(+), 265 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 9cfa565548..7c5da33dd5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -170,66 +170,31 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - dev = &rte_eth_devices[txq->port_id]; - - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { if (buffer_vec[i].mbuf != NULL) { rte_pktmbuf_free_seg(buffer_vec[i].mbuf); buffer_vec[i].mbuf = NULL; } } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; - } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; + for ( ; i < txq->next_use; ++i) { + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } } diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..0b139b8269 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,12 +34,58 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << + SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,18 +105,26 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -82,14 +136,23 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; @@ -150,22 +213,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -208,9 +273,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -267,23 +333,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -442,25 +491,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -480,7 +543,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -515,55 +579,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -587,12 +644,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 31/45] net/sxe2: refine vectorized Tx/Rx mode setup 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (30 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 32/45] net/sxe2: fix RSS action attribute validation liujie5 ` (13 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Set rte_eth_tx_pkt_prepare_dummy for the simple and vectorized Tx paths instead of leaving the prepare callback unset, and split the NEON simple/offload mode selection based on the offload flag. Log the selected Tx/Rx mode flags and apply the default Rx free threshold when the configured value is zero. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_rx.c | 3 ++- drivers/net/sxe2/sxe2_txrx.c | 20 +++++++++++++++----- 2 files changed, 17 insertions(+), 6 deletions(-) diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..3830c676d7 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..f7276f6a19 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,28 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts; } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +589,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 32/45] net/sxe2: fix RSS action attribute validation 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (31 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 ` (12 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The rss->level/key_len/queue_num checks only set the rte_flow_error but still return 0 (success), so invalid RSS configurations are accepted instead of being rejected with ENOTSUP. Return the error code from the validation checks, matching the behavior in the V3 implementation. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow_parse_action.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index db70b146c6..b0275321be 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -12,7 +12,7 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss *rss, struct rte_flow_error *error) { - int32_t ret = ENOTSUP; + int32_t ret = -ENOTSUP; switch (rss->func) { case RTE_ETH_HASH_FUNCTION_DEFAULT: case RTE_ETH_HASH_FUNCTION_TOEPLITZ: @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 33/45] net/sxe2: restore PF-only guard in udp tunnel port add 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (32 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 32/45] net/sxe2: fix RSS action attribute validation liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 34/45] net/sxe2: restore link update call in status query liujie5 ` (11 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_udp_tunnel_port_add_common() lost the check that restricts UDP tunnel port configuration to PF devices (not VF or representor), so VF/representor devices can now attempt to add UDP tunnel ports, which the hardware does not support. Restore the PF-only guard returning -ENOTSUP, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 77a31eb8a1..8c60c9cfde 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } @@ -669,6 +674,9 @@ int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -703,6 +711,9 @@ static int32_t sxe2_udp_tunnel_port_clear(struct rte_eth_dev *dev) int32_t ret = 0; uint16_t tunnel_proto = 0; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); for (tunnel_proto = 0; tunnel_proto < SXE2_UDP_TUNNEL_MAX; tunnel_proto++) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 34/45] net/sxe2: restore link update call in status query 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (33 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 35/45] net/sxe2: validate representor ID against VF count liujie5 ` (10 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_mac_link_status_get() no longer calls sxe2_link_update() after refreshing the link context, so the ethdev link state is only refreshed during device init (sxe2_link_update_init) and never updated when link status is queried at runtime, including on LSC interrupt events. Move the sxe2_link_update() call back into sxe2_drv_mac_link_status_get() and simplify sxe2_link_update_init() accordingly, matching the V3 implementation. Fixes: 1d7fd921beef ("net/sxe2: support link update") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 2 ++ drivers/net/sxe2/sxe2_mac.c | 11 +++-------- 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 4e5339e24b..b0e1552d5f 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -84,6 +84,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); + (void)sxe2_link_update(dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, @@ -96,6 +97,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t continue; repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); (void)sxe2_drv_mac_link_status_get(repr_adapter); + (void)sxe2_link_update(repr_eth_dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(repr_eth_dev, RTE_ETH_EVENT_INTR_LSC, diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..ab9bd5355b 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,18 +448,13 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - - (void)sxe2_link_update(dev, 0); + else + (void)sxe2_link_update(dev, 0); -l_end: return ret; } int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 35/45] net/sxe2: validate representor ID against VF count 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (34 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 34/45] net/sxe2: restore link update call in status query liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 ` (9 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_private_data_init() indexes parent_adapter->repr_ctxt.repr_vf_id[repr_id] without checking that repr_id is within the number of configured VFs, which can access out of bounds when an invalid representor ID is passed. Add a bounds check on repr_id against repr_ctxt.nb_vf and return -EINVAL on the error path. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..d0304ccc94 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,6 +312,12 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; + if (repr_id >= parent_adapter->repr_ctxt.nb_vf) { + PMD_LOG_ERR(INIT, "repr_id %u exceed max vf %u", + repr_id, parent_adapter->repr_ctxt.nb_vf); + ret = -EINVAL; + goto l_free; + } repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 36/45] net/sxe2: use primary VSI ID for representor VSI 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (35 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 35/45] net/sxe2: validate representor ID against VF count liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 ` (8 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> repr_priv_data->repr_vf_vsi_id is assigned with a ternary that falls back to the backup (dpdk) VSI ID when the kernel VSI ID is invalid. The V3 implementation assigns it directly from repr_vf_primary_vsi_id. Align with the V3 implementation by assigning repr_vf_vsi_id from repr_vf_primary_vsi_id. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index d0304ccc94..81ced7b855 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -323,11 +323,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; + repr_priv_data->repr_vf_vsi_id = repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 37/45] net/sxe2: wrap command params fill debug log in macro 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (36 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 ` (7 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_cmd_params_fill() passes the opcode string as a parameter to __sxe2_drv_cmd_params_fill() just to emit a debug log. The debug log is level-gated by PMD_DEV_LOG_DEBUG either way; moving it into the macro body only consolidates the call sites. Wrap the log and the fill helper in a do/while block, dropping the opc_str parameter so the opcode stringization happens at the call site. Evaluate the adapter argument exactly once through a local variable. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 16a2c3fea4..84fe401ec4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,8 +43,11 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) - + do { \ + struct sxe2_adapter *__adapter = (adapter); \ + PMD_DEV_LOG_DEBUG(__adapter, DRV, "cmd opcode:%s", #opc); \ + __sxe2_drv_cmd_params_fill(__adapter, cmd, opc, in_data, in_len, out_data, out_len); \ + } while (0) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 38/45] net/sxe2: restore Rx queue buffer split fill support 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (37 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:26 ` [PATCH v5 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 ` (6 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The V4 branch dropped sxe2_rxq_buf_split_fill() and the buffer split handling in sxe2_rxq_ctxt_cfg_fill(), so the Rx buffer split offload (RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) is advertised in device info but the per-queue context never configures split_en/split_type_mask/ hdr_len, and buffer split packets are not handled correctly. Restore the sxe2_rxq_buf_split_fill() helper and the buffer split branch in sxe2_rxq_ctxt_cfg_fill(), matching the V3 implementation. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 88 ++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 84fe401ec4..3998309bb1 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -195,6 +195,84 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + uint32_t proto_hdr; + + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + return -EINVAL; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + goto l_end; + } + + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + return -ENOTSUP; +l_end: + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + return 0; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -228,7 +306,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 39/45] net/sxe2: skip tunnel config fill on get failure 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (38 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 @ 2026-08-28 3:26 ` liujie5 2026-08-28 3:27 ` [PATCH v5 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 ` (5 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:26 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_udp_tunnel_get() fills tunnel_config fields even when the firmware command fails, so a failed get overwrites the config with the (zero-initialized) response data instead of leaving it intact. Return early with the error code when sxe2_drv_cmd_exec() fails, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3998309bb1..581026e81d 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1650,15 +1650,17 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; tunnel_config->fw_dst_en = resp.dst; tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; - +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 40/45] net/sxe2: skip flow id assignment on filter add failure 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (39 preceding siblings ...) 2026-08-28 3:26 ` [PATCH v5 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 3:27 ` [PATCH v5 41/45] net/sxe2: fix command channel log messages liujie5 ` (4 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_flow_filter_add() assigns flow->flow_id from the response even when the firmware command fails, overwriting any previously set flow id with the zero-initialized response value. Return early on command failure so flow->flow_id is preserved, and set flow->create_err on both the success and error paths. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 581026e81d..89829f29be 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1818,9 +1818,13 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + goto l_end; + } flow->flow_id = resp.flow_id; + +l_end: flow->create_err = ret; return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 41/45] net/sxe2: fix command channel log messages 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (40 preceding siblings ...) 2026-08-28 3:27 ` [PATCH v5 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 3:27 ` [PATCH v5 42/45] net/sxe2: align command structs with historical kernel layout liujie5 ` (3 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Several error/warning messages in sxe2_cmd_chnl.c are inaccurate or lost context: - vsi_info_get: message lost the vsi id; restore it - rxq_bind_irq/rxq_unbind_irq: message lost the rxq index; restore it - promisc_config: fix "promic" typo in the message - queue_info_get_update/rxq_mapping_set: incorrect "get queue info map"/"get dev caps" wording; use "rx queue mapping failed" - txq_mapping_set: "Rx queue" should read "Tx queue"; incorrect "get dev caps" wording should read "tx queue mapping failed" Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 89829f29be..0d81da542e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -481,7 +481,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -537,7 +537,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -557,7 +557,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -758,7 +758,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1683,7 +1683,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); goto l_end; } @@ -1727,7 +1727,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1744,7 +1744,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1758,7 +1758,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 42/45] net/sxe2: align command structs with historical kernel layout 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (41 preceding siblings ...) 2026-08-28 3:27 ` [PATCH v5 41/45] net/sxe2: fix command channel log messages liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 3:27 ` [PATCH v5 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 ` (2 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The sxe2_drv_cmd.h command structures must match the layout used by historical SXE2 kernel versions so the same firmware command ABI is shared. Several structures were declared with __rte_packed_begin/__rte_packed_end and extra rsv padding that the kernel layout does not have: - sxe2_drv_link_info_resp: drop rsv[3] padding - sxe2_tm_res: drop rsv[2] padding and packed attribute - sxe2_tm_info: drop packed attribute - sxe2_drv_sfp_req: drop packed attribute - sxe2_drv_sfp_resp: drop packed attribute sxe2_tm_add_mid_msg and sxe2_tm_add_queue_msg keep the packed attribute so the firmware command wire offsets (tm info offset, tm queue info offset) are preserved. Keep the structure members as-is so the command ABI is compatible with the historical kernel driver. Fixes: 9c894f75113f ("net/sxe2: support TM hierarchy and shaping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index cc71e2364e..5274b59a6a 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,18 +347,17 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { uint16_t parent_teid; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 43/45] common/sxe2: fix ioctl channel log and close handling 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (42 preceding siblings ...) 2026-08-28 3:27 ` [PATCH v5 42/45] net/sxe2: align command structs with historical kernel layout liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 3:27 ` [PATCH v5 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Compare sxe2_ioctl_chnl.c against the reference implementation and fix the following discrepancies: - sxe2_drv_dev_close: only log the closed fd when it is valid, move PMD_LOG_INFO inside the fd >= 0 check - sxe2_drv_dev_mmap: fix swapped format arguments in the debug log (cmd_fd and bar_idx were passed in the wrong order) - sxe2_drv_dev_dma_unmap: use PMD_LOG_ERR instead of PMD_LOG_INFO for the ioctl failure message Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index 3e2fbf572f..b006e296c6 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -107,9 +107,11 @@ sxe2_drv_dev_close(struct sxe2_common_device *cdev) { int32_t fd = SXE2_CDEV_TO_CMD_FD(cdev); - if (fd >= 0) + if (fd >= 0) { close(fd); - PMD_LOG_INFO(COM, "closed device fd=%d", fd); + PMD_LOG_INFO(COM, "closed device fd=%d", fd); + } + SXE2_CDEV_TO_CMD_FD(cdev) = SXE2_CMD_FD_INVALID; } @@ -349,8 +351,8 @@ void goto l_err; } - PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", src=0x%"PRIx64", offset=0x%"PRIx64"", - bar_idx, cmd_fd, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); + PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", offset=0x%"PRIx64", pci_offset=0x%"PRIx64"", + cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); virt = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, cmd_fd, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); @@ -477,7 +479,7 @@ sxe2_drv_dev_dma_unmap(struct sxe2_common_device *cdev, uint64_t iova) pthread_mutex_lock(&cdev->config.lock); ret = ioctl(cmd_fd, SXE2_COM_CMD_DMA_UNMAP, &cmd_params); if (ret < 0) { - PMD_LOG_INFO(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", + PMD_LOG_ERR(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", cmd_fd, ret, strerror(errno)); ret = -EIO; pthread_mutex_unlock(&cdev->config.lock); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 44/45] doc/sxe2: remove drv-sw-stats parameter documentation 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (43 preceding siblings ...) 2026-08-28 3:27 ` [PATCH v5 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The drv-sw-stats devarg is no longer supported. Remove its parameter description from the Runtime Configuration section. The "Receive Software Statistics" xstats section is kept because the rx_sw_* counters are still accumulated in the Rx data path and reported through rte_eth_xstats_get(). Fixes: 9e95b2b3859c ("doc: update sxe2 guide and features") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 31 ++----------------------------- 1 file changed, 2 insertions(+), 29 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index c5b400a8ba..fe4f9f916b 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -109,30 +109,6 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. - - ``no-sched-mode`` parameter [int] This parameter enables non-scheduling mode (no-sched mode). @@ -208,8 +184,7 @@ reflect the actual packets processed by the driver. Receive Software Statistics These counters are collected in the Rx data path - when ``drv-sw-stats=1`` is configured (see the ``drv-sw-stats`` devarg above). - When ``drv-sw-stats`` is disabled (default), these xstats report zero. + on every received packet. - ``rx_sw_unicast_packets``: Number of unicast packets received. - ``rx_sw_multicast_packets``: Number of multicast packets received. @@ -217,10 +192,8 @@ Receive Software Statistics - ``rx_sw_drop_packets``: Number of packets dropped in the Rx data path. - ``rx_sw_drop_bytes``: Number of bytes dropped in the Rx data path. - When ``drv-sw-stats`` is enabled, the basic counters - ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) + The basic counters ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) also reflect the software-accumulated packet and byte counts. - Otherwise, they are reported from hardware counters. Fnav Flow Engine Statistics The Fnav flow engine statistics type is controlled by -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 ` (44 preceding siblings ...) 2026-08-28 3:27 ` [PATCH v5 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 @ 2026-08-28 3:27 ` liujie5 2026-08-28 7:36 ` [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver liujie5 ` (45 more replies) 45 siblings, 46 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 3:27 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> rte_eth_dev_info_get() overwrites dev_info->nb_rx_queues and dev_info->nb_tx_queues from dev->data after the PMD dev_infos_get callback returns, so assigning them in sxe2_repr_dev_infos_get() has no effect. Remove the ineffective assignments. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index b7096f5927..5490fea10b 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -195,8 +195,6 @@ static int32_t sxe2_repr_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; - dev_info->nb_rx_queues = dev->data->nb_rx_queues; - dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 @ 2026-08-28 7:36 ` liujie5 2026-08-28 16:49 ` Stephen Hemminger 2026-08-28 7:36 ` [PATCH v6 01/45] common/sxe2: fix null pointer in class driver remove liujie5 ` (44 subsequent siblings) 45 siblings, 1 reply; 278+ messages in thread From: liujie5 @ 2026-08-28 7:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> This series updates the SXE2 poll mode driver (drivers/net/sxe2) and its common library (drivers/common/sxe2), fixing issues found in the previous versions and re-aligning the driver with the reference implementation. - common/sxe2: fix null pointer and munmap handling, fix ioctl channel log and close handling - net/sxe2: fix VF PCI device ID and MSIX register width, restore PF and port index caps assignment - net/sxe2: fix VSI lifecycle and representor handling - net/sxe2: restore Rx queue buffer split fill support, fix RSS action attribute validation - net/sxe2: fix command channel log messages, align command structs with the historical kernel layout - net/sxe2: add ACL engine event statistics support - net/sxe2: unify and refine the vectorized Tx/Rx path - doc/sxe2: remove stale drv-sw-stats parameter documentation Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> Jie Liu (45): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore pf and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: clear security context pointer on uninit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC and queue counts in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: guard Rx queue event FD free in unregister net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in udp tunnel port add net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow id assignment on filter add failure net/sxe2: fix command channel log messages net/sxe2: align command structs with historical kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-sw-stats parameter documentation net/sxe2: remove ineffective queue counts in representor info doc/guides/nics/sxe2.rst | 40 ++-- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 20 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 199 ++++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 37 +++- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 192 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 17 +- drivers/net/sxe2/sxe2_flow.c | 234 ++++++++++++++++++--- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 39 +++- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_irq.c | 29 ++- drivers/net/sxe2/sxe2_mac.c | 11 +- drivers/net/sxe2/sxe2_mp.c | 59 +++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 16 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 20 +- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 73 +++---- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 10 +- 36 files changed, 949 insertions(+), 674 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* Re: [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver 2026-08-28 7:36 ` [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver liujie5 @ 2026-08-28 16:49 ` Stephen Hemminger 0 siblings, 0 replies; 278+ messages in thread From: Stephen Hemminger @ 2026-08-28 16:49 UTC (permalink / raw) To: liujie5; +Cc: dev On Fri, 28 Aug 2026 15:36:33 +0800 liujie5@linkdatatechnology.com wrote: > From: Jie Liu <liujie5@linkdatatechnology.com> > > This series updates the SXE2 poll mode driver (drivers/net/sxe2) and > its common library (drivers/common/sxe2), fixing issues found in the > previous versions and re-aligning the driver with the reference > implementation. Looking good, AI review is mostly happy (with Claude Opus). But still a couple of nits worth resolving in commit messages. Review of v6 sxe2 series (45 patches) ===================================== Series applies cleanly on current main. All findings below were verified against the post-apply tree rather than the diffs alone. All v5 findings are resolved in code: the dead IPsec key-length hunk is gone (10/45), the representor nb_ports==0 case is handled (23/45), sxe2_vsi_destroy() now unlinks DPDK_ESW nodes (6/45), the ineffective queue-count assignments are dropped (14/45), and the duplicate unconditional RSS_HASH is gone (15/45). Two of those patches still carry commit messages describing the old code; see below. Patch 14/45: fill MAC and queue counts in device info ----------------------------------------------------- Warning: the commit message no longer matches the patch. It says "Fill max_mac_addrs, nb_rx_queues and nb_tx_queues ... so applications can query the maximum number of MAC addresses and the queue counts", but the diff now adds only max_mac_addrs. Please retitle and rewrite the body to describe just that. Patch 15/45: fix QinQ and RSS offload capability report -------------------------------------------------------- Warning: same problem. The body still says "Advertise RTE_ETH_RX_OFFLOAD_RSS_HASH unconditionally", but the code keeps the capability-gated form: if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; which is the correct behaviour. Drop that sentence. Patch 6/45: fix VSI lifecycle management ----------------------------------------- Info: with sxe2_vsi_destroy() now doing the unlink, the test left in sxe2_vsi_node_free() is dead: if (vsi->vsi_type == SXE2_VSI_T_ESW) TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); Both sites that insert into other_vsi_list use SXE2_VSI_T_DPDK_ESW (sxe2_vsi.c:193 and :218), so SXE2_VSI_T_ESW never appears on that list. Every caller of sxe2_vsi_node_free() passes a node that is not linked. Because this now sits next to the almost-identical DPDK_ESW test in sxe2_vsi_destroy(), a reader will take it for the list-removal path and the two can drift. Suggest deleting it. Patch 26/45: add ACL engine event statistics support ----------------------------------------------------- Warning: the two new command structures are byte-for-byte copies of the existing fnav ones: struct sxe2_drv_acl_query_stat_req { stat_id, stat_ctrl, is_clear } struct sxe2_drv_flow_fnav_query_stat_req { stat_id, stat_ctrl, is_clear } and likewise for _resp. The same patch already reuses sxe2_drv_flow_fnav_get_stat_id_req and sxe2_drv_flow_fnav_free_stat_id_req for the ACL alloc and free commands, so the query path is the odd one out. Either reuse the fnav structs throughout or add ACL variants throughout; as written it adds command-ABI surface for no benefit. Info: sxe2_flow_get_filter_cid() silently succeeds on an unknown engine type. The new prologue does } else { goto l_end; } with ret still 0, jumping past the SXE2_FLOW_ACTION_COUNT block. A flow carrying a COUNT action then returns success without stat_index ever being set. sxe2_flow_free_mgr() and sxe2_flow_query_mgr() both return -ENOTSUP in the same situation; this one should too. Info: the FNAV and ACL arms added to RTE_FLOW_ACTION_TYPE_COUNT in sxe2_flow_parse_action() are identical apart from which hw_res.global_index is incremented. Picking the resource struct first and sharing one body would halve it. Patch 27/45: guard Rx queue event FD free in unregister -------------------------------------------------------- Warning: this does not fix a bug. rte_free(NULL) is a documented no-op, so the pre-patch code was already safe when rxq_event_fd was NULL; moving the call inside the existing "if (irq_ctxt->rxq_event_fd)" guard changes nothing observable. The commit message claims "the buffer is only released when it was allocated", which was already true. Please drop the Fixes: and Cc: stable@dpdk.org tags, or drop the patch. Patch 29/45: refactor Tx queue reset operations ------------------------------------------------ Info: sxe2_tx_vec_ops_get() builds and returns a three-pointer struct by value on every call. The scalar side already uses the simpler form: const struct sxe2_txq_ops sxe2_default_txq_ops = { ... }; A file-scope "static const struct sxe2_txq_ops sxe2_tx_vec_ops" plus "txq->ops = sxe2_tx_vec_ops;" would match it and keep the table in .rodata. Info: sxe2_tx_queues_vec_prepare() still returns 0 on every path, so the caller's ret = sxe2_tx_queues_vec_prepare(dev); if (ret != 0) tx_mode_flags &= ~SXE2_TX_MODE_VEC_SET_MASK; is dead. Either make the NULL-txq case an error or make the function void. Patch 30/45: unify vectorized Tx buffer handling -------------------------------------------------- The core fix is real and worth having: the old sxe2_tx_queue_mbufs_release_vec() left "buffer" unassigned on the AVX512 branch and then dereferenced it in the trailing loop, and it also contained a duplicated "buffer = txq->buffer_ring;". Both go away with the union. Warning: the patch is far wider than its commit message, and all of it is going to stable. Beyond the buffer_ring/buffer_ring_vec unification it also: - deletes sxe2_tx_bufs_free_vec_avx512(), which implemented the RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE bulk path with _mm512_loadu_si512 into the mempool cache. AVX512 Tx now uses the generic sxe2_tx_bufs_free_vec(). That is a performance regression, not a fix. - adds sxe2_tx_desc_fill_4_neon_simple(), a new four-wide descriptor fill using vst1q_u64_x4 and uint64x2x4_t. This is a new optimisation. (The descriptor words it produces do match sxe2_tx_desc_fill_one_neon() with with_offloads=false, and the "i + 3 < n" bounds are correct.) - changes the Rx packet_type lane mapping in sxe2_rx_desc_ptype_fill_neon() from pkt0/1/2/3 <- lane 5/1/7/3 to lane 1/3/5/7, and switches the input from staterr to desc_lo with a different mask. - removes three of the four rte_atomic_thread_fence(acquire) calls between descriptor loads in sxe2_rx_pkts_common_vec_neon(). The last two are Rx correctness and memory-ordering changes in the fast path and are not mentioned anywhere in the commit message. Please split: the union fix (with the Fixes:/stable tags) in one patch, the NEON Tx optimisation in another, and the NEON Rx ptype and fence changes in a third with their own justification. If the AVX512 fast-free removal is intentional, say so and why. Patch 36/45: use primary VSI ID for representor VSI ----------------------------------------------------- Error: this drops the guard against an invalid kernel VSI. - repr_priv_data->repr_vf_vsi_id = - ...kernel_vsi_id != SXE2_INVALID_VSI_ID ? - ...kernel_vsi_id : ...dpdk_vsi_id; + repr_priv_data->repr_vf_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id; repr_vf_primary_vsi_id is kernel_vsi_id, so repr_vf_vsi_id can now hold SXE2_INVALID_VSI_ID. No consumer tests for it: sxe2_txrx_poll.c:506 (repr_vf_vsi_id & 0x3FFULL) is written straight into a Tx descriptor field sxe2_flow.c:317 flow->meta.flow_src_vsi = repr_vf_vsi_id sxe2_flow_parse_action.c:240 *vsi_index = repr_vf_vsi_id kernel_vsi_id is genuinely optional -- sxe2_vsi_uninit() tests "kernel_vsi_id != SXE2_INVALID_VSI_ID" before using it -- and the ternary being removed is direct evidence the author expected the invalid case. repr_vf_backup_vsi_id (the dpdk_vsi_id) is still stored and still used at sxe2_flow.c:383, so the backup ID has not become redundant. "Matching the V3 implementation" is not sufficient justification here. Either keep the fallback, or explain why kernel_vsi_id is guaranteed valid for a representor and drop repr_vf_backup_vsi_id too. Patch 37/45: wrap command params fill debug log in macro ---------------------------------------------------------- Warning: __adapter is a reserved identifier. C11 7.1.3 reserves all identifiers beginning with two underscores for the implementation, in every scope. Rename it, e.g. do { \ struct sxe2_adapter *_ad = (adapter); \ PMD_DEV_LOG_DEBUG(_ad, DRV, "cmd opcode:%s", #opc); \ __sxe2_drv_cmd_params_fill(_ad, cmd, opc, ...); \ } while (0) Patch 41/45: fix command channel log messages ----------------------------------------------- Info: one of the replacements is less accurate than what it replaces. sxe2_drv_queue_info_get_update() issues SXE2_DRV_CMD_TX_RX_MAP_GET and fills both q_ipackets/q_ibytes and q_opackets/q_obytes, but the message became PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); The old "get queue info map failed" covered both directions. Something like "tx/rx queue map get failed" would be better. Warning: this is a pure log-wording patch tagged Fixes: and Cc: stable@dpdk.org. Log text corrections do not warrant a stable backport; please drop those tags. Patch 42/45: align command structs with historical kernel layout ----------------------------------------------------------------- Error: sxe2_tm_res changes size, which changes the payload length of four live firmware commands. I compiled the before and after definitions to be sure: sxe2_drv_link_info_resp 8 -> 8 (unchanged) sxe2_tm_res 4 -> 2 (CHANGED) sxe2_tm_info 12 -> 12 (unchanged) sxe2_tm_add_mid_msg 16 -> 16 (info still at offset 3) sxe2_tm_add_queue_msg 20 -> 20 (info still at offset 5) sizeof(struct sxe2_tm_res) is passed directly as the command in/out length at four call sites in sxe2_cmd_chnl.c: 1226 SCHED_ROOT_TREE_ALLOC out_len 4 -> 2 1250 SCHED_ROOT_TREE_RELEASE in_len 4 -> 2 1292 (sxe2_drv_tm_commit_node) 1354 SCHED_ROOT_CHILDREN_DELETE in_len 4 -> 2 The commit message says "Keep the structure members as-is so the command ABI is compatible with the historical kernel driver", which contradicts what the patch does to this one structure. Either the message is wrong and the length change is the intended fix -- in which case say so explicitly, since it is the only behavioural change in the patch -- or sxe2_tm_res should keep its rsv[2] and __rte_aligned(4). For the record, the other four structures are genuinely no-ops. Removing rsv[3] from sxe2_drv_link_info_resp does not shrink it, because __rte_aligned(4) still rounds 5 bytes up to 8; the padding is merely implicit now, which for a wire format is a readability step backwards. The sfp structures keep the same offsets and sizes without the packed attribute. Positive note: dropping __rte_aligned(4) from sxe2_tm_info removes two -Wpacked-not-aligned warnings, since info sits at offset 3 and 5 inside the packed message structures. That is worth mentioning in the commit message, as it is the clearest benefit of the patch. Verified clean -------------- 1-5, 7-13, 16-25, 28, 31-35, 38-40, 43-45. Some of these I checked specifically rather than by inspection: 31/45 rte_eth_tx_pkt_prepare_dummy is in ethdev_driver.h and is the right thing for a PMD to install; SXE2_DEFAULT_RX_FREE_THRESH (32) matches the default_rxconf advertised in dev_info. The ARM64 fallback fix is correct -- the old else branch installed sxe2_tx_pkts_vec_neon_simple when NEON was not detected. 33/45 sxe2_udp_tunnel_port_clear() returning -ENOTSUP for representors is harmless; its only caller discards the result with a (void) cast. 35/45 the bounds check is placed before the first repr_vf_id[repr_id] dereference. 44/45 drv-sw-stats is genuinely absent from the code -- not in RTE_PMD_REGISTER_PARAM_STRING, no parse callback -- and the sw_stats counters really are updated on every packet, so the reworded xstats section matches the code. Things I checked and found not to be problems, in case they come up again: the memset in sxe2_tx_queue_reset_vec() is in bounds, since the buffer ring is always allocated at the larger sizeof(struct sxe2_tx_buffer) stride regardless of mode; mbuf_free_arr[64] cannot overflow because sxe2_tx_vec_support_check() rejects rs_thresh > SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC before vector mode is selected; and sxe2_tx_queues_vec_prepare() is reached only on the RTE_PROC_PRIMARY path from sxe2_dev_start(), after sxe2_queues_init() and before the queues are started, so the new queue_reset() call cannot disturb a running datapath. ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v6 01/45] common/sxe2: fix null pointer in class driver remove 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-28 7:36 ` [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver liujie5 @ 2026-08-28 7:36 ` liujie5 2026-08-28 7:36 ` [PATCH v6 02/45] common/sxe2: allow munmap during kernel reset liujie5 ` (43 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 02/45] common/sxe2: allow munmap during kernel reset 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-28 7:36 ` [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver liujie5 2026-08-28 7:36 ` [PATCH v6 01/45] common/sxe2: fix null pointer in class driver remove liujie5 @ 2026-08-28 7:36 ` liujie5 2026-08-28 7:36 ` [PATCH v6 03/45] net/sxe2: fix VF PCI device ID liujie5 ` (42 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 03/45] net/sxe2: fix VF PCI device ID 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (2 preceding siblings ...) 2026-08-28 7:36 ` [PATCH v6 02/45] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-28 7:36 ` liujie5 2026-08-28 7:37 ` [PATCH v6 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 ` (41 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:36 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 04/45] net/sxe2: fix MSIX register width in PF map table 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (3 preceding siblings ...) 2026-08-28 7:36 ` [PATCH v6 03/45] net/sxe2: fix VF PCI device ID liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 05/45] net/sxe2: restore pf and port index caps assignment liujie5 ` (40 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 05/45] net/sxe2: restore pf and port index caps assignment 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (4 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 06/45] net/sxe2: fix VSI lifecycle management liujie5 ` (39 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 06/45] net/sxe2: fix VSI lifecycle management 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (5 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 05/45] net/sxe2: restore pf and port index caps assignment liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 07/45] net/sxe2: initialize stats in representor device init liujie5 ` (38 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..dea3f58997 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -131,6 +131,8 @@ static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *v } l_free: + if (vsi->vsi_type == SXE2_VSI_T_DPDK_ESW) + TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); rte_free(vsi); vsi = NULL; @@ -230,7 +232,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +285,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -357,4 +360,5 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 07/45] net/sxe2: initialize stats in representor device init 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (6 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 06/45] net/sxe2: fix VSI lifecycle management liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 08/45] net/sxe2: use base device name for representor naming liujie5 ` (37 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 08/45] net/sxe2: use base device name for representor naming 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (7 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 07/45] net/sxe2: initialize stats in representor device init liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 09/45] net/sxe2: propagate LSC event to VF representors liujie5 ` (36 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 09/45] net/sxe2: propagate LSC event to VF representors 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (8 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 08/45] net/sxe2: use base device name for representor naming liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 10/45] net/sxe2: clear security context pointer on uninit liujie5 ` (35 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..ba764dd5e4 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 10/45] net/sxe2: clear security context pointer on uninit 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (9 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 09/45] net/sxe2: propagate LSC event to VF representors liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 11/45] net/sxe2: rename representor VSI ID fields liujie5 ` (34 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_security_uinit() frees the security session but leaves dev->security_ctx pointing at the freed memory. Set dev->security_ctx to NULL after releasing the security context so a later access does not dereference a dangling pointer. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_security.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 11/45] net/sxe2: rename representor VSI ID fields 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (10 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 10/45] net/sxe2: clear security context pointer on uninit liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 12/45] net/sxe2: clean up duplicate function declarations liujie5 ` (33 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 12/45] net/sxe2: clean up duplicate function declarations 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (11 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 11/45] net/sxe2: rename representor VSI ID fields liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 13/45] net/sxe2: fix null VSI dereference in device info liujie5 ` (32 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 13/45] net/sxe2: fix null VSI dereference in device info 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (12 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 12/45] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:37 ` [PATCH v6 14/45] net/sxe2: fill MAC and queue counts " liujie5 ` (31 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 14/45] net/sxe2: fill MAC and queue counts in device info 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (13 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 13/45] net/sxe2: fix null VSI dereference in device info liujie5 @ 2026-08-28 7:37 ` liujie5 2026-08-28 7:38 ` [PATCH v6 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 ` (30 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:37 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Fill max_mac_addrs, nb_rx_queues and nb_tx_queues in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses and the queue counts. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85e34aa1a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 15/45] net/sxe2: fix QinQ and RSS offload capability report 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (14 preceding siblings ...) 2026-08-28 7:37 ` [PATCH v6 14/45] net/sxe2: fill MAC and queue counts " liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 16/45] net/sxe2: use regular write for mapped registers liujie5 ` (29 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Advertise RTE_ETH_RX_OFFLOAD_RSS_HASH unconditionally and report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85e34aa1a..7a11a93dff 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,15 +804,11 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | RTE_ETH_RX_OFFLOAD_TCP_LRO; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | - RTE_ETH_TX_OFFLOAD_QINQ_INSERT | RTE_ETH_TX_OFFLOAD_MULTI_SEGS | RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE | RTE_ETH_TX_OFFLOAD_IPV4_CKSUM | @@ -855,14 +851,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -934,7 +938,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -972,6 +976,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 16/45] net/sxe2: use regular write for mapped registers 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (15 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 17/45] net/sxe2: move PCI register read macro to common header liujie5 ` (28 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7a11a93dff..589f09c113 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1439,7 +1439,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 17/45] net/sxe2: move PCI register read macro to common header 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (16 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 16/45] net/sxe2: use regular write for mapped registers liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 18/45] net/sxe2: validate PCI map resource type liujie5 ` (27 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 18/45] net/sxe2: validate PCI map resource type 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (17 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 17/45] net/sxe2: move PCI register read macro to common header liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 ` (26 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 589f09c113..9ef93b8076 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1552,6 +1552,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 19/45] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (18 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 18/45] net/sxe2: validate PCI map resource type liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 20/45] net/sxe2: fix null dereference in dev uninit liujie5 ` (25 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 9ef93b8076..fdff4ae10f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1773,14 +1773,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1791,7 +1790,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 20/45] net/sxe2: fix null dereference in dev uninit 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (19 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 ` (24 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index fdff4ae10f..41ea67a607 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2074,9 +2074,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 21/45] net/sxe2: fix duplicated cleanup in dev close 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (20 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 20/45] net/sxe2: fix null dereference in dev uninit liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 22/45] net/sxe2: align dev init and cleanup order liujie5 ` (23 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_close() calls sxe2_switchdev_uninit() and sxe2_dev_pci_map_uinit() twice, and releases resources in an order that does not match the initialization sequence. Remove the duplicated calls and align the teardown order with the device init order. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 41ea67a607..5d14e28d96 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2041,17 +2041,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 22/45] net/sxe2: align dev init and cleanup order 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (21 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 23/45] net/sxe2: simplify switchdev representor matching liujie5 ` (22 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_eth_init() to be called before sxe2_sw_init() and rearrange the error cleanup labels so that resources are torn down in the reverse order of initialization. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d14e28d96..5bce710b29 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1942,6 +1942,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1954,12 +1960,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2014,12 +2014,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_rss_err: sxe2_security_uinit(dev); init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 23/45] net/sxe2: simplify switchdev representor matching 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (22 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 22/45] net/sxe2: align dev init and cleanup order liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:38 ` [PATCH v6 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 ` (21 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_match() encodes the kernel representor ID and compares it against each requested port, which is fragile. Match the PF number and VF ID directly against the switchdev representor info instead, and drop the sxe2_switchdev_repr_id_encode_get() helper. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 72 +++++++++++++++++----------------- drivers/net/sxe2/sxe2_ethdev.h | 3 -- 2 files changed, 37 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5bce710b29..08986e384f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2149,42 +2149,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2197,15 +2180,34 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + if (req_eth_da->nb_ports > 0) { + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) + break; + } + if (port_idx == req_eth_da->nb_ports) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf", + adapter->switchdev_info.pf_num); + rte_errno = EBUSY; + return false; + } + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index f2557b28c3..e818578319 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 24/45] net/sxe2: rename fnav cid manager symbols to flow 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (23 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 23/45] net/sxe2: simplify switchdev representor matching liujie5 @ 2026-08-28 7:38 ` liujie5 2026-08-28 7:39 ` [PATCH v6 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 ` (20 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:38 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Rename the sxe2_fnav_cid_mgr, sxe2_fnav_cid_mgr_list_t, sxe2_fnav_count_resource and sxe2_fnav_get_filter_cid symbols to the sxe2_flow_* prefix for consistency with the flow module naming. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 +- drivers/net/sxe2/sxe2_cmd_chnl.h | 2 +- drivers/net/sxe2/sxe2_flow.c | 46 ++++++++++++++--------------- drivers/net/sxe2/sxe2_flow.h | 6 ++-- drivers/net/sxe2/sxe2_flow_define.h | 12 ++++---- 5 files changed, 34 insertions(+), 34 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..3229c72597 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1800,7 +1800,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 294ac15db4..cfea1a1f0e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -159,7 +159,7 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..a33b8606df 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,16 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1112,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1143,13 +1143,13 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; if (user_id == 0) { TAILQ_REMOVE(cid_mgr_list, mgr, next); @@ -1170,14 +1170,14 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; @@ -1218,7 +1218,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,7 +1348,7 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) adapter->flow_ctxt.hw_res.count_type = adapter->devargs.fnav_stat_type; @@ -1370,10 +1370,10 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; ret = sxe2_flow_flush(dev, &error); if (ret) diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..8a5d871978 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,18 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 25/45] net/sxe2: move tunnel port helpers into flow module 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (24 preceding siblings ...) 2026-08-28 7:38 ` [PATCH v6 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 26/45] net/sxe2: add ACL engine event statistics support liujie5 ` (19 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_flow_parse_pattern_ipip, sxe2_flow_add_udp_tunnel_port and sxe2_flow_add_tunnel_port from sxe2_flow_parse_pattern.c into sxe2_flow.c as static helpers, and drop the public declaration of sxe2_flow_add_tunnel_port from the header, keeping the tunnel port handling internal to the flow module. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 113 +++++++++++++++++++++ drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 --------------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 -- 3 files changed, 113 insertions(+), 119 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index a33b8606df..cd39385340 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -550,6 +550,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..69d83a6ea6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -37,10 +37,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, struct rte_flow_error *error, struct sxe2_flow *flow); -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 26/45] net/sxe2: add ACL engine event statistics support 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (25 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 ` (18 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for the ACL flow engine to track packet hits and bytes, enabling flow aging and traffic monitoring for ACL rules. - Add acl-stat-type devarg to configure the statistics type - Implement sxe2_drv_flow_acl_get_stat_id/free_stat/query_stat - Handle the ACL engine in flow create/destroy/query paths - Add fnav_hw_res and acl_hw_res count resources Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 11 +++ drivers/net/sxe2/sxe2_cmd_chnl.c | 71 ++++++++++++++++++ drivers/net/sxe2/sxe2_cmd_chnl.h | 7 ++ drivers/net/sxe2/sxe2_drv_cmd.h | 19 +++++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 23 ++++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 89 ++++++++++++++++++----- drivers/net/sxe2/sxe2_flow_define.h | 5 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 25 +++++-- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 224 insertions(+), 31 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..c5b400a8ba 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,6 +98,17 @@ Runtime Configuration Default value is 3 (count both packets and bytes). +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL flow engine statistics type + used for flow rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). + - ``drv-sw-stats`` parameter [int] This parameter controls whether per-packet software statistics (SW stats) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3229c72597..16a2c3fea4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1829,6 +1829,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_acl_query_stat_req req = { 0 }; + struct sxe2_drv_acl_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index cfea1a1f0e..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -161,6 +161,13 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, struct sxe2_flow_cid_mgr *mgr); +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..cc71e2364e 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -668,6 +668,18 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_fc_get_resp { uint8_t rsv[3]; } __rte_packed_end; +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_req { + uint32_t stat_id; + uint32_t stat_ctrl; + uint32_t is_clear; +} __rte_packed_end; + +struct __rte_aligned(4) __rte_packed_begin sxe2_drv_acl_query_stat_resp { + uint32_t stat_index; + uint64_t stat_hits; + uint64_t stat_bytes; +} __rte_packed_end; + enum sxe2_drv_cmd_module { SXE2_DRV_CMD_MODULE_HANDSHAKE = 0, SXE2_DRV_CMD_MODULE_DEV = 1, @@ -824,6 +836,13 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2), + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 3), + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 08986e384f..77a31eb8a1 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -981,11 +982,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -993,19 +994,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1187,13 +1188,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2366,6 +2374,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index e818578319..e9f78fe57f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -135,6 +135,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cd39385340..d82d3bbd02 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1204,13 +1204,23 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1233,7 +1243,10 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1244,7 +1257,7 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1260,13 +1273,26 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } else { + PMD_LOG_ERR(DRV, + "Failed to free flow count, unknown engine type: %d.", + flow->engine_type); + ret = -ENOTSUP; + return ret; + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1287,13 +1313,19 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1310,7 +1342,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1461,12 +1501,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1485,13 +1531,13 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) struct rte_flow_error error; struct sxe2_flow_cid_mgr *mgr = NULL; struct sxe2_flow_cid_mgr *temp = NULL; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1500,5 +1546,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 8a5d871978..d04499f5cb 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -100,7 +100,7 @@ TAILQ_HEAD(rte_flow_list_t, rte_flow); struct sxe2_flow_cid_mgr { TAILQ_ENTRY(sxe2_flow_cid_mgr) next; - uint16_t stat_index; + uint32_t stat_index; uint32_t user_id; uint32_t driver_id; uint32_t count_type; @@ -118,7 +118,8 @@ struct sxe2_flow_count_resource { struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_flow_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..db70b146c6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -953,7 +953,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -988,7 +989,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { @@ -1037,11 +1039,24 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, if (engine_type == SXE2_FLOW_ENGINE_FNAV) { sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); act_count = action->conf; - flow->action.count.user_id = act_count->id; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++adapter->flow_ctxt.fnav_hw_res.global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) + if (flow->action.count.user_id == 0) { flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; + ++adapter->flow_ctxt.acl_hw_res.global_index; + } action_num[SXE2_FLOW_ACTION_COUNT]++; } else { rte_flow_error_set(error, ENOTSUP, diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 27/45] net/sxe2: guard Rx queue event FD free in unregister 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (26 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 26/45] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 28/45] net/sxe2: refactor primary process MP message handling liujie5 ` (17 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_rxq_intr_unregister() frees irq_ctxt->rxq_event_fd outside the rxq_event_fd NULL check. Move the free and NULL assignment inside the guard so the buffer is only released when it was allocated. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index ba764dd5e4..4e5339e24b 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -881,12 +881,11 @@ static void sxe2_rxq_intr_unregister(struct rte_eth_dev *dev) (void)sxe2_drv_dev_rxq_irq_set(adapter->cdev, i, &efd, 1); sxe2_rxq_intr_efd_free(irq_ctxt->rxq_event_fd[i]); } + rte_free(irq_ctxt->rxq_event_fd); + irq_ctxt->rxq_event_fd = NULL; } - rte_free(irq_ctxt->rxq_event_fd); - irq_ctxt->rxq_event_fd = NULL; rte_intr_vec_list_free(intr_handle); - rte_intr_nb_efd_set(intr_handle, 0); rte_intr_max_intr_set(intr_handle, 0); } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 28/45] net/sxe2: refactor primary process MP message handling 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (27 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 29/45] net/sxe2: refactor Tx queue reset operations liujie5 ` (16 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the multi-process work logic into the sxe2_mp_do_primary_work helper and operate on a copy of the request in the primary handler so the original message is not modified. Simplify the reply construction and return -ENOENT instead of -EINVAL when no response is received from the primary process. Fixes: 5db446ba97b0 ("net/sxe2: support statistics and multi-process") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_mp.c | 59 ++++++++++++++++++++++---------------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 29/45] net/sxe2: refactor Tx queue reset operations 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (28 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 28/45] net/sxe2: refactor primary process MP message handling liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 ` (15 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Extract the descriptor ring reset loop into a sxe2_tx_queue_desc_ring_reset helper and reuse it from both the scalar and vectorized queue reset paths. Add a sxe2_tx_queue_reset_vec entry point for vectorized queues, export sxe2_tx_buffer_ring_free for reuse outside the module (clearing the buffer ring pointer after freeing it), and add sxe2_tx_vec_ops_get to build the vectorized Tx queue operations table used by the vector path setup. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_tx.c | 42 +++++++++++++++++++++++--------- drivers/net/sxe2/sxe2_tx.h | 4 +++ drivers/net/sxe2/sxe2_txrx_vec.c | 16 +++++++++++- drivers/net/sxe2/sxe2_txrx_vec.h | 1 + 4 files changed, 51 insertions(+), 12 deletions(-) diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..9cfa565548 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,19 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void) +{ + static const struct sxe2_txq_ops ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, + }; + + return ops; +} + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -233,7 +246,8 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); continue; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops_get(); + txq->ops.queue_reset(txq); } return ret; } diff --git a/drivers/net/sxe2/sxe2_txrx_vec.h b/drivers/net/sxe2/sxe2_txrx_vec.h index c139aed776..b9bc4f9c27 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.h +++ b/drivers/net/sxe2/sxe2_txrx_vec.h @@ -89,6 +89,7 @@ uint16_t sxe2_rx_pkts_scattered_vec_neon_offload(void *rx_queue, struct rte_mbuf uint16_t sxe2_tx_pkts_vec_neon_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t nb_pkts); #endif +struct sxe2_txq_ops sxe2_tx_vec_ops_get(void); int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev); int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 30/45] net/sxe2: unify vectorized Tx buffer handling 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (29 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 29/45] net/sxe2: refactor Tx queue reset operations liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 ` (14 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Add a union of the scalar and vectorized buffer ring pointers to the Tx queue structure so the vectorized path can use sxe2_tx_buffer_vec directly. Rename the mbuf fill helper to sxe2_tx_pkts_mbuf_fill_vec, switch the vectorized Tx burst and mbuf release paths to the buffer_ring_vec member, and drop the AVX512-specific fill handling and conditional branching. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_txrx_vec.c | 57 ++---- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++++++-------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- 7 files changed, 178 insertions(+), 265 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 9cfa565548..7c5da33dd5 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -170,66 +170,31 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - dev = &rte_eth_devices[txq->port_id]; - - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { if (buffer_vec[i].mbuf != NULL) { rte_pktmbuf_free_seg(buffer_vec[i].mbuf); buffer_vec[i].mbuf = NULL; } } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; - } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; + for ( ; i < txq->next_use; ++i) { + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } } diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..0b139b8269 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,12 +34,58 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << + SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,18 +105,26 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -82,14 +136,23 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; @@ -150,22 +213,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -208,9 +273,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -267,23 +333,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -442,25 +491,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -480,7 +543,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -515,55 +579,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -587,12 +644,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 31/45] net/sxe2: refine vectorized Tx/Rx mode setup 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (30 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 32/45] net/sxe2: fix RSS action attribute validation liujie5 ` (13 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Set rte_eth_tx_pkt_prepare_dummy for the simple and vectorized Tx paths instead of leaving the prepare callback unset, and split the NEON simple/offload mode selection based on the offload flag. Log the selected Tx/Rx mode flags and apply the default Rx free threshold when the configured value is zero. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_rx.c | 3 ++- drivers/net/sxe2/sxe2_txrx.c | 20 +++++++++++++++----- 2 files changed, 17 insertions(+), 6 deletions(-) diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..3830c676d7 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..f7276f6a19 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,28 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts; } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +589,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 32/45] net/sxe2: fix RSS action attribute validation 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (31 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 ` (12 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The rss->level/key_len/queue_num checks only set the rte_flow_error but still return 0 (success), so invalid RSS configurations are accepted instead of being rejected with ENOTSUP. Return the error code from the validation checks, matching the behavior in the V3 implementation. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow_parse_action.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index db70b146c6..b0275321be 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -12,7 +12,7 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss *rss, struct rte_flow_error *error) { - int32_t ret = ENOTSUP; + int32_t ret = -ENOTSUP; switch (rss->func) { case RTE_ETH_HASH_FUNCTION_DEFAULT: case RTE_ETH_HASH_FUNCTION_TOEPLITZ: @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 33/45] net/sxe2: restore PF-only guard in udp tunnel port add 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (32 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 32/45] net/sxe2: fix RSS action attribute validation liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 34/45] net/sxe2: restore link update call in status query liujie5 ` (11 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_udp_tunnel_port_add_common() lost the check that restricts UDP tunnel port configuration to PF devices (not VF or representor), so VF/representor devices can now attempt to add UDP tunnel ports, which the hardware does not support. Restore the PF-only guard returning -ENOTSUP, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 77a31eb8a1..8c60c9cfde 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } @@ -669,6 +674,9 @@ int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -703,6 +711,9 @@ static int32_t sxe2_udp_tunnel_port_clear(struct rte_eth_dev *dev) int32_t ret = 0; uint16_t tunnel_proto = 0; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); for (tunnel_proto = 0; tunnel_proto < SXE2_UDP_TUNNEL_MAX; tunnel_proto++) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 34/45] net/sxe2: restore link update call in status query 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (33 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:39 ` [PATCH v6 35/45] net/sxe2: validate representor ID against VF count liujie5 ` (10 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_mac_link_status_get() no longer calls sxe2_link_update() after refreshing the link context, so the ethdev link state is only refreshed during device init (sxe2_link_update_init) and never updated when link status is queried at runtime, including on LSC interrupt events. Move the sxe2_link_update() call back into sxe2_drv_mac_link_status_get() and simplify sxe2_link_update_init() accordingly, matching the V3 implementation. Fixes: 1d7fd921beef ("net/sxe2: support link update") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 2 ++ drivers/net/sxe2/sxe2_mac.c | 11 +++-------- 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 4e5339e24b..b0e1552d5f 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -84,6 +84,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); + (void)sxe2_link_update(dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, @@ -96,6 +97,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t continue; repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); (void)sxe2_drv_mac_link_status_get(repr_adapter); + (void)sxe2_link_update(repr_eth_dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(repr_eth_dev, RTE_ETH_EVENT_INTR_LSC, diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..ab9bd5355b 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,18 +448,13 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - - (void)sxe2_link_update(dev, 0); + else + (void)sxe2_link_update(dev, 0); -l_end: return ret; } int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 35/45] net/sxe2: validate representor ID against VF count 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (34 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 34/45] net/sxe2: restore link update call in status query liujie5 @ 2026-08-28 7:39 ` liujie5 2026-08-28 7:40 ` [PATCH v6 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 ` (9 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:39 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_private_data_init() indexes parent_adapter->repr_ctxt.repr_vf_id[repr_id] without checking that repr_id is within the number of configured VFs, which can access out of bounds when an invalid representor ID is passed. Add a bounds check on repr_id against repr_ctxt.nb_vf and return -EINVAL on the error path. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..d0304ccc94 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,6 +312,12 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; + if (repr_id >= parent_adapter->repr_ctxt.nb_vf) { + PMD_LOG_ERR(INIT, "repr_id %u exceed max vf %u", + repr_id, parent_adapter->repr_ctxt.nb_vf); + ret = -EINVAL; + goto l_free; + } repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 36/45] net/sxe2: use primary VSI ID for representor VSI 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (35 preceding siblings ...) 2026-08-28 7:39 ` [PATCH v6 35/45] net/sxe2: validate representor ID against VF count liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 ` (8 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> repr_priv_data->repr_vf_vsi_id is assigned with a ternary that falls back to the backup (dpdk) VSI ID when the kernel VSI ID is invalid. The V3 implementation assigns it directly from repr_vf_primary_vsi_id. Align with the V3 implementation by assigning repr_vf_vsi_id from repr_vf_primary_vsi_id. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index d0304ccc94..81ced7b855 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -323,11 +323,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; - repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; + repr_priv_data->repr_vf_vsi_id = repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 37/45] net/sxe2: wrap command params fill debug log in macro 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (36 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 ` (7 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_cmd_params_fill() passes the opcode string as a parameter to __sxe2_drv_cmd_params_fill() just to emit a debug log. The debug log is level-gated by PMD_DEV_LOG_DEBUG either way; moving it into the macro body only consolidates the call sites. Wrap the log and the fill helper in a do/while block, dropping the opc_str parameter so the opcode stringization happens at the call site. Evaluate the adapter argument exactly once through a local variable. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 16a2c3fea4..84fe401ec4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,8 +43,11 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) - + do { \ + struct sxe2_adapter *__adapter = (adapter); \ + PMD_DEV_LOG_DEBUG(__adapter, DRV, "cmd opcode:%s", #opc); \ + __sxe2_drv_cmd_params_fill(__adapter, cmd, opc, in_data, in_len, out_data, out_len); \ + } while (0) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 38/45] net/sxe2: restore Rx queue buffer split fill support 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (37 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 ` (6 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The V4 branch dropped sxe2_rxq_buf_split_fill() and the buffer split handling in sxe2_rxq_ctxt_cfg_fill(), so the Rx buffer split offload (RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) is advertised in device info but the per-queue context never configures split_en/split_type_mask/ hdr_len, and buffer split packets are not handled correctly. Restore the sxe2_rxq_buf_split_fill() helper and the buffer split branch in sxe2_rxq_ctxt_cfg_fill(), matching the V3 implementation. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 88 ++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 84fe401ec4..3998309bb1 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -195,6 +195,84 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + uint32_t proto_hdr; + + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + return -EINVAL; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + goto l_end; + } + + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + return -ENOTSUP; +l_end: + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + return 0; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -228,7 +306,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 39/45] net/sxe2: skip tunnel config fill on get failure 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (38 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 ` (5 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_udp_tunnel_get() fills tunnel_config fields even when the firmware command fails, so a failed get overwrites the config with the (zero-initialized) response data instead of leaving it intact. Return early with the error code when sxe2_drv_cmd_exec() fails, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3998309bb1..581026e81d 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1650,15 +1650,17 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; tunnel_config->fw_dst_en = resp.dst; tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; - +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 40/45] net/sxe2: skip flow id assignment on filter add failure 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (39 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 41/45] net/sxe2: fix command channel log messages liujie5 ` (4 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_flow_filter_add() assigns flow->flow_id from the response even when the firmware command fails, overwriting any previously set flow id with the zero-initialized response value. Return early on command failure so flow->flow_id is preserved, and set flow->create_err on both the success and error paths. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 581026e81d..89829f29be 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1818,9 +1818,13 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + goto l_end; + } flow->flow_id = resp.flow_id; + +l_end: flow->create_err = ret; return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 41/45] net/sxe2: fix command channel log messages 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (40 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 42/45] net/sxe2: align command structs with historical kernel layout liujie5 ` (3 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Several error/warning messages in sxe2_cmd_chnl.c are inaccurate or lost context: - vsi_info_get: message lost the vsi id; restore it - rxq_bind_irq/rxq_unbind_irq: message lost the rxq index; restore it - promisc_config: fix "promic" typo in the message - queue_info_get_update/rxq_mapping_set: incorrect "get queue info map"/"get dev caps" wording; use "rx queue mapping failed" - txq_mapping_set: "Rx queue" should read "Tx queue"; incorrect "get dev caps" wording should read "tx queue mapping failed" Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 89829f29be..0d81da542e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -481,7 +481,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -537,7 +537,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -557,7 +557,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -758,7 +758,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1683,7 +1683,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); goto l_end; } @@ -1727,7 +1727,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1744,7 +1744,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1758,7 +1758,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 42/45] net/sxe2: align command structs with historical kernel layout 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (41 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 41/45] net/sxe2: fix command channel log messages liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 ` (2 subsequent siblings) 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The sxe2_drv_cmd.h command structures must match the layout used by historical SXE2 kernel versions so the same firmware command ABI is shared. Several structures were declared with __rte_packed_begin/__rte_packed_end and extra rsv padding that the kernel layout does not have: - sxe2_drv_link_info_resp: drop rsv[3] padding - sxe2_tm_res: drop rsv[2] padding and packed attribute - sxe2_tm_info: drop packed attribute - sxe2_drv_sfp_req: drop packed attribute - sxe2_drv_sfp_resp: drop packed attribute sxe2_tm_add_mid_msg and sxe2_tm_add_queue_msg keep the packed attribute so the firmware command wire offsets (tm info offset, tm queue info offset) are preserved. Keep the structure members as-is so the command ABI is compatible with the historical kernel driver. Fixes: 9c894f75113f ("net/sxe2: support TM hierarchy and shaping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index cc71e2364e..5274b59a6a 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,18 +347,17 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { uint16_t parent_teid; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 43/45] common/sxe2: fix ioctl channel log and close handling 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (42 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 42/45] net/sxe2: align command structs with historical kernel layout liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> Compare sxe2_ioctl_chnl.c against the reference implementation and fix the following discrepancies: - sxe2_drv_dev_close: only log the closed fd when it is valid, move PMD_LOG_INFO inside the fd >= 0 check - sxe2_drv_dev_mmap: fix swapped format arguments in the debug log (cmd_fd and bar_idx were passed in the wrong order) - sxe2_drv_dev_dma_unmap: use PMD_LOG_ERR instead of PMD_LOG_INFO for the ioctl failure message Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index 3e2fbf572f..b006e296c6 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -107,9 +107,11 @@ sxe2_drv_dev_close(struct sxe2_common_device *cdev) { int32_t fd = SXE2_CDEV_TO_CMD_FD(cdev); - if (fd >= 0) + if (fd >= 0) { close(fd); - PMD_LOG_INFO(COM, "closed device fd=%d", fd); + PMD_LOG_INFO(COM, "closed device fd=%d", fd); + } + SXE2_CDEV_TO_CMD_FD(cdev) = SXE2_CMD_FD_INVALID; } @@ -349,8 +351,8 @@ void goto l_err; } - PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", src=0x%"PRIx64", offset=0x%"PRIx64"", - bar_idx, cmd_fd, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); + PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", offset=0x%"PRIx64", pci_offset=0x%"PRIx64"", + cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); virt = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, cmd_fd, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); @@ -477,7 +479,7 @@ sxe2_drv_dev_dma_unmap(struct sxe2_common_device *cdev, uint64_t iova) pthread_mutex_lock(&cdev->config.lock); ret = ioctl(cmd_fd, SXE2_COM_CMD_DMA_UNMAP, &cmd_params); if (ret < 0) { - PMD_LOG_INFO(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", + PMD_LOG_ERR(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", cmd_fd, ret, strerror(errno)); ret = -EIO; pthread_mutex_unlock(&cdev->config.lock); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 44/45] doc/sxe2: remove drv-sw-stats parameter documentation 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (43 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 45 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> The drv-sw-stats devarg is no longer supported. Remove its parameter description from the Runtime Configuration section. The "Receive Software Statistics" xstats section is kept because the rx_sw_* counters are still accumulated in the Rx data path and reported through rte_eth_xstats_get(). Fixes: 9e95b2b3859c ("doc: update sxe2 guide and features") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 31 ++----------------------------- 1 file changed, 2 insertions(+), 29 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index c5b400a8ba..fe4f9f916b 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -109,30 +109,6 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. - - ``no-sched-mode`` parameter [int] This parameter enables non-scheduling mode (no-sched mode). @@ -208,8 +184,7 @@ reflect the actual packets processed by the driver. Receive Software Statistics These counters are collected in the Rx data path - when ``drv-sw-stats=1`` is configured (see the ``drv-sw-stats`` devarg above). - When ``drv-sw-stats`` is disabled (default), these xstats report zero. + on every received packet. - ``rx_sw_unicast_packets``: Number of unicast packets received. - ``rx_sw_multicast_packets``: Number of multicast packets received. @@ -217,10 +192,8 @@ Receive Software Statistics - ``rx_sw_drop_packets``: Number of packets dropped in the Rx data path. - ``rx_sw_drop_bytes``: Number of bytes dropped in the Rx data path. - When ``drv-sw-stats`` is enabled, the basic counters - ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) + The basic counters ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) also reflect the software-accumulated packet and byte counts. - Otherwise, they are reported from hardware counters. Fnav Flow Engine Statistics The Fnav flow engine statistics type is controlled by -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (44 preceding siblings ...) 2026-08-28 7:40 ` [PATCH v6 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 @ 2026-08-28 7:40 ` liujie5 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (48 more replies) 45 siblings, 49 replies; 278+ messages in thread From: liujie5 @ 2026-08-28 7:40 UTC (permalink / raw) To: stephen; +Cc: dev From: Jie Liu <liujie5@linkdatatechnology.com> rte_eth_dev_info_get() overwrites dev_info->nb_rx_queues and dev_info->nb_tx_queues from dev->data after the PMD dev_infos_get callback returns, so assigning them in sxe2_repr_dev_infos_get() has no effect. Remove the ineffective assignments. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index b7096f5927..ec45187dc9 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -127,7 +127,7 @@ static int32_t sxe2_repr_dev_close(struct rte_eth_dev *dev) return 0; } -static int32_t sxe2_repr_dev_infos_get(struct rte_eth_dev *dev, +static int32_t sxe2_repr_dev_infos_get(__rte_unused struct rte_eth_dev *dev, struct rte_eth_dev_info *dev_info) { dev_info->max_rx_queues = 1; @@ -195,8 +195,6 @@ static int32_t sxe2_repr_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; - dev_info->nb_rx_queues = dev->data->nb_rx_queues; - dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove Jie Liu ` (19 more replies) 2026-08-31 2:41 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings liujie5 ` (47 subsequent siblings) 48 siblings, 20 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu This series updates the SXE2 poll mode driver (drivers/net/sxe2) and its common library (drivers/common/sxe2), fixing issues found in the previous version and re-aligning the driver with the reference implementation. Changes since v6: - drop the now-trivial sxe2_vsi_node_free() helper and inline rte_free() at its call sites - unify the duplicated FNAV/ACL COUNT action arms in the flow parser - use a file-scope static const ops table for the vectorized Tx path and fail sxe2_tx_queues_vec_prepare() on a NULL txq - split "unify vectorized Tx buffer handling" into three commits: the buffer_ring union fix, the NEON Tx 4-wide descriptor fill, and the NEON Rx ptype/memory-ordering fixes - use the primary VSI id directly for representors (the kernel guarantees it is always valid) - drop the packed/aligned attributes from the TM command message structs to match the historical kernel layout - fix VEC mode selection in the Tx/Rx mode set functions - clean up commit messages (headline case/length, missing Fixes tags) Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> Jie Liu (47): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore PF and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: clear security context pointer on uninit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC addresses in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: optimize NEON Tx descriptor fill net/sxe2: fix NEON Rx ptype mapping and memory ordering net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in UDP tunnel port add net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow ID assignment on filter add failure net/sxe2: correct command channel log messages net/sxe2: align command structs with kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-SW-stats parameter documentation net/sxe2: remove ineffective representor queue counts net/sxe2: fix VEC mode selection in mode set functions doc/guides/nics/sxe2.rst | 40 ++-- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 21 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 199 +++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 33 +-- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 192 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 17 +- drivers/net/sxe2/sxe2_flow.c | 235 ++++++++++++++++++--- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 42 ++-- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_irq.c | 24 ++- drivers/net/sxe2/sxe2_mac.c | 11 +- drivers/net/sxe2/sxe2_mp.c | 59 +++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 15 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 34 +-- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 74 +++---- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 31 +-- 35 files changed, 946 insertions(+), 707 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset Jie Liu ` (18 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu 2026-08-31 2:34 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID Jie Liu ` (17 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 03/47] net/sxe2: fix VF PCI device ID 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu 2026-08-31 2:34 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove Jie Liu 2026-08-31 2:34 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table Jie Liu ` (16 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (2 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment Jie Liu ` (15 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (3 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management Jie Liu ` (14 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (4 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init Jie Liu ` (13 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 31 ++++++++++--------------------- 1 file changed, 10 insertions(+), 21 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..e1a26fda6a 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -96,21 +96,6 @@ static struct sxe2_vsi *sxe2_vsi_node_create(struct sxe2_adapter *adapter, return vsi; } -static void sxe2_vsi_node_free(struct sxe2_vsi *vsi) -{ - struct sxe2_adapter *adapter; - - if (!vsi) - return; - - adapter = vsi->adapter; - if (vsi->vsi_type == SXE2_VSI_T_ESW) - TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); - - rte_free(vsi); - vsi = NULL; -} - static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) { int32_t ret = 0; @@ -131,6 +116,8 @@ static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *v } l_free: + if (vsi->vsi_type == SXE2_VSI_T_DPDK_ESW) + TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); rte_free(vsi); vsi = NULL; @@ -174,7 +161,7 @@ static int32_t sxe2_main_vsi_create(struct sxe2_adapter *adapter) goto l_end; l_free_vsi: - sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + rte_free(adapter->vsi_ctxt.main_vsi); adapter->vsi_ctxt.main_vsi = NULL; l_end: return ret; @@ -217,7 +204,7 @@ int32_t sxe2_other_vsi_create(struct sxe2_adapter *adapter, uint16_t cnt_vf) goto l_end; l_free_vsi: - sxe2_vsi_node_free(other_vsi); + rte_free(other_vsi); l_end: return ret; } @@ -230,7 +217,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +270,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -356,5 +344,6 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) { struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + rte_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 07/47] net/sxe2: initialize stats in representor device init 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (5 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming Jie Liu ` (12 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 08/47] net/sxe2: use base device name for representor naming 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (6 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors Jie Liu ` (11 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (7 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit Jie Liu ` (10 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..ba764dd5e4 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (8 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields Jie Liu ` (9 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen sxe2_security_uinit() frees the security session but leaves dev->security_ctx pointing at the freed memory. Set dev->security_ctx to NULL after releasing the security context so a later access does not dereference a dangling pointer. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_security.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (9 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations Jie Liu ` (8 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (10 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info Jie Liu ` (7 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (11 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " Jie Liu ` (6 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 14/47] net/sxe2: fill MAC addresses in device info 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (12 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report Jie Liu ` (5 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Fill max_mac_addrs in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses supported by the device. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85e34aa1a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (13 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers Jie Liu ` (4 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85e34aa1a..7a11a93dff 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,15 +804,11 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | RTE_ETH_RX_OFFLOAD_TCP_LRO; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | - RTE_ETH_TX_OFFLOAD_QINQ_INSERT | RTE_ETH_TX_OFFLOAD_MULTI_SEGS | RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE | RTE_ETH_TX_OFFLOAD_IPV4_CKSUM | @@ -855,14 +851,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -934,7 +938,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -972,6 +976,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 16/47] net/sxe2: use regular write for mapped registers 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (14 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header Jie Liu ` (3 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7a11a93dff..589f09c113 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1439,7 +1439,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (15 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type Jie Liu ` (2 subsequent siblings) 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stephen Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 18/47] net/sxe2: validate PCI map resource type 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (16 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized Jie Liu 2026-08-31 2:34 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit Jie Liu 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 589f09c113..9ef93b8076 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1552,6 +1552,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (17 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type Jie Liu @ 2026-08-31 2:34 ` Jie Liu 2026-08-31 2:34 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit Jie Liu 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 9ef93b8076..fdff4ae10f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1773,14 +1773,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1791,7 +1790,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu ` (18 preceding siblings ...) 2026-08-31 2:34 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized Jie Liu @ 2026-08-31 2:34 ` Jie Liu 19 siblings, 0 replies; 278+ messages in thread From: Jie Liu @ 2026-08-31 2:34 UTC (permalink / raw) To: dev; +Cc: Jie Liu, stable, stephen sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index fdff4ae10f..41ea67a607 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2074,9 +2074,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu @ 2026-08-31 2:41 ` liujie5 2026-08-31 7:46 ` David Marchand 2026-08-31 16:18 ` Stephen Hemminger 2026-08-31 2:41 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove liujie5 ` (46 subsequent siblings) 48 siblings, 2 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> This series updates the SXE2 poll mode driver (drivers/net/sxe2) and its common library (drivers/common/sxe2), fixing issues found in the previous version and re-aligning the driver with the reference implementation. Changes since v6: - drop the now-trivial sxe2_vsi_node_free() helper and inline rte_free() at its call sites - unify the duplicated FNAV/ACL COUNT action arms in the flow parser - use a file-scope static const ops table for the vectorized Tx path and fail sxe2_tx_queues_vec_prepare() on a NULL txq - split "unify vectorized Tx buffer handling" into three commits: the buffer_ring union fix, the NEON Tx 4-wide descriptor fill, and the NEON Rx ptype/memory-ordering fixes - use the primary VSI id directly for representors (the kernel guarantees it is always valid) - drop the packed/aligned attributes from the TM command message structs to match the historical kernel layout - fix VEC mode selection in the Tx/Rx mode set functions - clean up commit messages (headline case/length, missing Fixes tags) Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> Jie Liu (47): common/sxe2: fix null pointer in class driver remove common/sxe2: allow munmap during kernel reset net/sxe2: fix VF PCI device ID net/sxe2: fix MSIX register width in PF map table net/sxe2: restore PF and port index caps assignment net/sxe2: fix VSI lifecycle management net/sxe2: initialize stats in representor device init net/sxe2: use base device name for representor naming net/sxe2: propagate LSC event to VF representors net/sxe2: clear security context pointer on uninit net/sxe2: rename representor VSI ID fields net/sxe2: clean up duplicate function declarations net/sxe2: fix null VSI dereference in device info net/sxe2: fill MAC addresses in device info net/sxe2: fix QinQ and RSS offload capability report net/sxe2: use regular write for mapped registers net/sxe2: move PCI register read macro to common header net/sxe2: validate PCI map resource type net/sxe2: guard PCI BAR unmap when not initialized net/sxe2: fix null dereference in dev uninit net/sxe2: fix duplicated cleanup in dev close net/sxe2: align dev init and cleanup order net/sxe2: simplify switchdev representor matching net/sxe2: rename fnav cid manager symbols to flow net/sxe2: move tunnel port helpers into flow module net/sxe2: add ACL engine event statistics support net/sxe2: refactor primary process MP message handling net/sxe2: refactor Tx queue reset operations net/sxe2: unify vectorized Tx buffer handling net/sxe2: optimize NEON Tx descriptor fill net/sxe2: fix NEON Rx ptype mapping and memory ordering net/sxe2: refine vectorized Tx/Rx mode setup net/sxe2: fix RSS action attribute validation net/sxe2: restore PF-only guard in UDP tunnel port add net/sxe2: restore link update call in status query net/sxe2: validate representor ID against VF count net/sxe2: use primary VSI ID for representor VSI net/sxe2: wrap command params fill debug log in macro net/sxe2: restore Rx queue buffer split fill support net/sxe2: skip tunnel config fill on get failure net/sxe2: skip flow ID assignment on filter add failure net/sxe2: correct command channel log messages net/sxe2: align command structs with kernel layout common/sxe2: fix ioctl channel log and close handling doc/sxe2: remove drv-SW-stats parameter documentation net/sxe2: remove ineffective representor queue counts net/sxe2: fix VEC mode selection in mode set functions doc/guides/nics/sxe2.rst | 40 ++-- drivers/common/sxe2/sxe2_common.c | 6 +- drivers/common/sxe2/sxe2_ioctl_chnl.c | 21 +- drivers/net/sxe2/sxe2_cmd_chnl.c | 199 +++++++++++++++-- drivers/net/sxe2/sxe2_cmd_chnl.h | 15 +- drivers/net/sxe2/sxe2_drv_cmd.h | 33 +-- drivers/net/sxe2/sxe2_dump.c | 10 +- drivers/net/sxe2/sxe2_ethdev.c | 192 ++++++++++------- drivers/net/sxe2/sxe2_ethdev.h | 13 +- drivers/net/sxe2/sxe2_ethdev_repr.c | 17 +- drivers/net/sxe2/sxe2_flow.c | 235 ++++++++++++++++++--- drivers/net/sxe2/sxe2_flow.h | 6 +- drivers/net/sxe2/sxe2_flow_define.h | 15 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 42 ++-- drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 ---------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 - drivers/net/sxe2/sxe2_irq.c | 24 ++- drivers/net/sxe2/sxe2_mac.c | 11 +- drivers/net/sxe2/sxe2_mp.c | 59 +++--- drivers/net/sxe2/sxe2_queue.c | 2 + drivers/net/sxe2/sxe2_queue.h | 7 +- drivers/net/sxe2/sxe2_rx.c | 3 +- drivers/net/sxe2/sxe2_security.c | 1 + drivers/net/sxe2/sxe2_switchdev.c | 15 +- drivers/net/sxe2/sxe2_tx.c | 42 +++- drivers/net/sxe2/sxe2_tx.h | 4 + drivers/net/sxe2/sxe2_txrx.c | 34 +-- drivers/net/sxe2/sxe2_txrx_poll.h | 2 - drivers/net/sxe2/sxe2_txrx_vec.c | 74 +++---- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 219 ++++++++++++------- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- drivers/net/sxe2/sxe2_vsi.c | 31 +-- 35 files changed, 946 insertions(+), 707 deletions(-) -- 2.52.0 ^ permalink raw reply [flat|nested] 278+ messages in thread
* Re: [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings 2026-08-31 2:41 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings liujie5 @ 2026-08-31 7:46 ` David Marchand 2026-08-31 16:18 ` Stephen Hemminger 1 sibling, 0 replies; 278+ messages in thread From: David Marchand @ 2026-08-31 7:46 UTC (permalink / raw) To: liujie5; +Cc: stephen, dev, Thomas Monjalon On Mon, 31 Aug 2026 at 04:41, <liujie5@linkdatatechnology.com> wrote: > > From: Jie Liu <liujie5@linkdatatechnology.com> > > This series updates the SXE2 poll mode driver (drivers/net/sxe2) and > its common library (drivers/common/sxe2), fixing issues found in the > previous version and re-aligning the driver with the reference > implementation. > > Changes since v6: > - drop the now-trivial sxe2_vsi_node_free() helper and inline > rte_free() at its call sites > - unify the duplicated FNAV/ACL COUNT action arms in the flow parser > - use a file-scope static const ops table for the vectorized Tx path > and fail sxe2_tx_queues_vec_prepare() on a NULL txq > - split "unify vectorized Tx buffer handling" into three commits: > the buffer_ring union fix, the NEON Tx 4-wide descriptor fill, and > the NEON Rx ptype/memory-ordering fixes > - use the primary VSI id directly for representors (the kernel > guarantees it is always valid) > - drop the packed/aligned attributes from the TM command message > structs to match the historical kernel layout > - fix VEC mode selection in the Tx/Rx mode set functions > - clean up commit messages (headline case/length, missing Fixes tags) > > Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> It looks like this series had issues during transmission. Patchwork created multiple series... -- David Marchand ^ permalink raw reply [flat|nested] 278+ messages in thread
* Re: [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings 2026-08-31 2:41 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings liujie5 2026-08-31 7:46 ` David Marchand @ 2026-08-31 16:18 ` Stephen Hemminger 1 sibling, 0 replies; 278+ messages in thread From: Stephen Hemminger @ 2026-08-31 16:18 UTC (permalink / raw) To: liujie5; +Cc: dev On Mon, 31 Aug 2026 10:41:03 +0800 liujie5@linkdatatechnology.com wrote: > From: Jie Liu <liujie5@linkdatatechnology.com> > > This series updates the SXE2 poll mode driver (drivers/net/sxe2) and > its common library (drivers/common/sxe2), fixing issues found in the > previous version and re-aligning the driver with the reference > implementation. > > Changes since v6: > - drop the now-trivial sxe2_vsi_node_free() helper and inline > rte_free() at its call sites > - unify the duplicated FNAV/ACL COUNT action arms in the flow parser > - use a file-scope static const ops table for the vectorized Tx path > and fail sxe2_tx_queues_vec_prepare() on a NULL txq > - split "unify vectorized Tx buffer handling" into three commits: > the buffer_ring union fix, the NEON Tx 4-wide descriptor fill, and > the NEON Rx ptype/memory-ordering fixes > - use the primary VSI id directly for representors (the kernel > guarantees it is always valid) > - drop the packed/aligned attributes from the TM command message > structs to match the historical kernel layout > - fix VEC mode selection in the Tx/Rx mode set functions > - clean up commit messages (headline case/length, missing Fixes tags) Getting much better. There are two items that AI flags that need a second look; either say "yes thats OK AI is wrong" or put out a new version. The two that are worth examining are: Patch 26: fnav_enable change. Ends up enabling FDIR on all Rx paths per queue Patch 31: fnav lane ordering. AI also gets worried that AVX512 fast-free change will change performance. But in the overall performance of any real code, that change will hardly be visible. I admit AI has dug far more into detail here than I have. Full report from AI (Claude Opus) The v6 items are fixed: 14/47 and 15/47 commit messages match the code now, 26/47 no longer duplicates the fnav command structs, the command struct patch (now 43/47) states the sxe2_tm_res 4 to 2 byte change, and the old 30/45 is split into 29, 30 and 31. I applied the series and read the tree. I did not build or bisect it. Patch 08/47: use base device name for representor --------------------------------------------------- Warning: the commit message says representor devices are allocated on the same NUMA node as the parent. The patch sets numa_node, but the allocation two lines later still uses rte_socket_id(): eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, rte_socket_id()); rte_socket_id() is the socket of the calling thread, not the socket of the device. Use the same numa_node for the allocation. Info: the literal "vf" is passed as a "%s" argument. Put it in the format string. Patch 26/47: add ACL engine event statistics support ------------------------------------------------------ Warning: this patch also changes Rx queue init in sxe2_queues_init(): if (adapter->flow_ctxt.fnav_inited) rxq->fnav_enable = true; sxe2_flow_init() sets fnav_inited to 1 always, so this sets fnav_enable on every Rx queue. Before this patch nothing assigned that field, so it was always false. The fnav blocks in all four vector Rx paths (sse, avx2, avx512, neon) were dead code and are now live on every queue. That is a data path change. It is not ACL statistics and it is not in the commit message. Please move it to its own patch and explain why every queue needs it. Patch 31/47: fix NEON Rx ptype mapping and memory ordering ------------------------------------------------------------ Warning: the fnav flags still use the old lane order. The patch builds desc_lo and desc_hi in natural order: uint32x4_t q1_01 = vzip2q_u32(d0, d1); uint32x4_t q1_23 = vzip2q_u32(d2, d3); so desc_lo is {d0[2], d1[2], d2[2], d3[2]}. The old code built {d1[2], d0[2], d3[2], d2[2]}. flags lane i is written to rx_pkts[i] through rearm0..rearm3, so this patch fixes the VLAN, checksum and RSS flags, which were swapped inside each packet pair. sxe2_rx_desc_fnav_flags_neon() is not touched and still builds descs_tmp1 = vzip1q_u32(d1, d0); descs_tmp2 = vzip1q_u32(d3, d2); which gives {d1[0], d0[0], d3[0], d2[0]}. That vector is OR'ed into flags in sxe2_rx_desc_offloads_para_fill_neon(), so RTE_MBUF_F_RX_FDIR and RTE_MBUF_F_RX_FDIR_ID are still set on the wrong mbuf of each pair. The bug is older than this patch, but this is the patch that fixes lane order, and 26/47 makes the path live. Warning: the patch is much wider than the commit message. Besides the ptype lanes and the fences it also changes: - staterr, from a 32 bit zip to a 16 bit zip. Lanes 0..3 are now the low half of the staterr word for pkt0..pkt3 and lanes 4..7 the high half. - the umbcast shuffle mask, the eop shuffle mask, rxe_mask and eop_mask. These follow from the new staterr layout and I read them as correct. - the DD count. The old code was rte_popcount64() of the DD bits, which counts DD bits anywhere in the group of four. It could return 2 when packets 0 and 2 are done and packet 1 is not, and hand up a descriptor the hardware has not written. The new code counts the leading run with rte_ctz64(). That is a real fix and it deserves its own patch, or at least a line in the message. Also, the ptype lane change is not a fix. With the old staterr layout, lanes 5/1/7/3 selected pkt0/1/2/3 correctly. With the new layout lanes 1/3/5/7 are correct. Both are right for their own layout. The message describes a bug that was not there. Patch 32/47: refine vectorized Tx/Rx mode setup ------------------------------------------------- Info: "Tx mode flags:0x%016x" and the Rx one print a uint32_t with a width of 16, so there are always eight leading zeros. %08x fits. Patch 35/47: restore link update call in status query ------------------------------------------------------- Warning: the commit message says the sxe2_link_update() call is moved back into sxe2_drv_mac_link_status_get(). The diff does not touch that function. It adds two (void)sxe2_link_update() calls in sxe2_event_irq_common_handler() and keeps the call in sxe2_link_update_init(). The effect is the same for the three call sites that exist today, so the code is fine. Please make the message describe what the patch does. Patch 17/47: move PCI register read macro to common ----------------------------------------------------- Info, pre-existing: the two macros are now next to each other and the byte order handling does not match. #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) #define SXE2_PCI_REG_READ(reg) rte_read32(reg) Other PMDs wrap the read in rte_le_to_cpu_32(). Not a change for this patch, but worth a follow up. Patch 37/47: use primary VSI ID for representor VSI ----------------------------------------------------- Info: I accept the kernel guarantee stated in the commit message. One loose end: sxe2_vsi_id_str() in sxe2_dump.c maps SXE2_INVALID_VSI_ID to "NA" and is used for this exact field. If the primary VSI id is always valid, that branch is dead and can go. ^ permalink raw reply [flat|nested] 278+ messages in thread
* [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu 2026-08-31 2:41 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset liujie5 ` (45 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_classes_driver_remove() calls cdrv->remove(cdev) without checking whether cdrv or cdrv->remove is NULL. If the class driver was never probed, cdev->cdrv remains NULL, and the unconditional call dereferences a NULL pointer, crashing during device removal. Add NULL checks for cdrv and cdrv->remove, returning 0 when either is NULL. Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_common.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/common/sxe2/sxe2_common.c b/drivers/common/sxe2/sxe2_common.c index 5c5db85f29..6e387a8a73 100644 --- a/drivers/common/sxe2/sxe2_common.c +++ b/drivers/common/sxe2/sxe2_common.c @@ -465,8 +465,12 @@ static int32_t sxe2_classes_driver_probe(struct sxe2_common_device *cdev, static int32_t sxe2_classes_driver_remove(struct sxe2_common_device *cdev) { struct sxe2_class_driver *cdrv = cdev->cdrv; + int32_t ret = 0; + + if (cdrv != NULL && cdrv->remove != NULL) + ret = cdrv->remove(cdev); - return cdrv->remove(cdev); + return ret; } static int32_t sxe2_kvargs_validate(struct sxe2_dev_kvargs_info *kv_info) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (2 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID liujie5 ` (44 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_dev_munmap() refuses to unmap the BAR region when cdev->config.kernel_reset is set, returning -EPERM. After a kernel reset the application still needs to release the previously mapped regions during cleanup; blocking munmap leaves stale mappings and prevents a clean teardown. Remove the kernel_reset check from sxe2_drv_dev_munmap() so the mapping is always released. The cdev parameter is no longer used, so mark it __rte_unused. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index a233a78136..3e2fbf572f 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -367,16 +367,10 @@ void RTE_EXPORT_INTERNAL_SYMBOL(sxe2_drv_dev_munmap) int32_t -sxe2_drv_dev_munmap(struct sxe2_common_device *cdev, void *virt, uint64_t len) +sxe2_drv_dev_munmap(struct sxe2_common_device *cdev __rte_unused, void *virt, uint64_t len) { int32_t ret = 0; - if (cdev->config.kernel_reset) { - ret = -EPERM; - PMD_LOG_WARN(COM, "kernel reset, need restart app."); - goto l_end; - } - PMD_LOG_DEBUG(COM, "Munmap virt=%p, len=0x%"PRIx64"", virt, len); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 03/47] net/sxe2: fix VF PCI device ID 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (3 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table liujie5 ` (43 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The VF PCI device ID is defined as 0x10b2 per the hardware specification, but the code incorrectly uses 0x10b. As a result, the VF driver never binds to the device, making VF functionality completely unusable. Fix this by changing SXE2_PCI_DEVICE_ID_VF_1 from 0x10b to 0x10b2. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 8bbfdc3a15..ec376b76dc 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -44,7 +44,7 @@ #define SXE2_PCI_VENDOR_ID_1 0x1ff2 #define SXE2_PCI_DEVICE_ID_PF_1 0x10b1 -#define SXE2_PCI_DEVICE_ID_VF_1 0x10b +#define SXE2_PCI_DEVICE_ID_VF_1 0x10b2 #define SXE2_PCI_VENDOR_ID_2 0x1d94 #define SXE2_PCI_DEVICE_ID_PF_2 0x1260 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (4 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment liujie5 ` (42 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The MSIX entry in sxe2_net_map_addr_info_pf sets a register width of 10 (decimal), but each PCIe MSIX table entry is 16 bytes (0x10). The VF map table already uses 0x10. Since reg_width is used as the stride between MSIX entries in sxe2_dev_pci_seg_map(), the wrong value makes the mapped region too short and places the entries at incorrect offsets. Change .reg_width from 10 to 0x10 for the SXE2_PCI_MAP_RES_IRQ_MSIX entry to match the VF table. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index ec376b76dc..5d8cfca6cf 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -94,7 +94,7 @@ static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_pf[SXE2_PCI_MAP_RES_ .reg_width = 4}, [SXE2_PCI_MAP_RES_IRQ_MSIX] = {.addr_base = SXE2_BAR4_MSIX_CTL(0), .bar_idx = 4, - .reg_width = 10}, + .reg_width = 0x10}, }; static struct sxe2_pci_map_addr_info sxe2_net_map_addr_info_vf[SXE2_PCI_MAP_RES_MAX_COUNT] = { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (5 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management liujie5 ` (41 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_func_caps_get() never assigns adapter->pf_idx from the device capabilities, leaving it at its zero-initialized value. Switchdev requests and representor setup that use pf_idx then report the wrong PF index on multi-PF configurations. Restore the pf_idx and port_idx assignments in sxe2_func_caps_get() and drop the now-redundant port_idx assignment from sxe2_drv_dev_caps_set(). Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d8cfca6cf..2e14c372f8 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1284,8 +1284,6 @@ void sxe2_eth_uinit(struct rte_eth_dev *dev __rte_unused) static void sxe2_drv_dev_caps_set(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { - adapter->port_idx = dev_caps->port_idx; - adapter->cap_flags = 0; if (dev_caps->cap_flags & SXE2_DEV_CAPS_OFFLOAD_L2) @@ -1344,6 +1342,8 @@ static int32_t sxe2_func_caps_get(struct sxe2_adapter *adapter) goto l_end; adapter->dev_type = dev_caps.dev_type; + adapter->port_idx = dev_caps.port_idx; + adapter->pf_idx = dev_caps.pf_idx; sxe2_drv_dev_caps_set(adapter, &dev_caps); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (6 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init liujie5 ` (40 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Fix several VSI create/destroy issues introduced by VF representor support: - Initialize other_vsi_list with TAILQ_INIT in sxe2_vsi_init before any VSI is inserted into it. - Treat -EPERM as a non-fatal error when destroying VSIs, since the kernel may have already removed the VSI. - Set main_vsi to NULL after destroy/free to avoid a dangling pointer if the VSI is destroyed again. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_vsi.c | 31 ++++++++++--------------------- 1 file changed, 10 insertions(+), 21 deletions(-) diff --git a/drivers/net/sxe2/sxe2_vsi.c b/drivers/net/sxe2/sxe2_vsi.c index d29480b931..e1a26fda6a 100644 --- a/drivers/net/sxe2/sxe2_vsi.c +++ b/drivers/net/sxe2/sxe2_vsi.c @@ -96,21 +96,6 @@ static struct sxe2_vsi *sxe2_vsi_node_create(struct sxe2_adapter *adapter, return vsi; } -static void sxe2_vsi_node_free(struct sxe2_vsi *vsi) -{ - struct sxe2_adapter *adapter; - - if (!vsi) - return; - - adapter = vsi->adapter; - if (vsi->vsi_type == SXE2_VSI_T_ESW) - TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); - - rte_free(vsi); - vsi = NULL; -} - static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) { int32_t ret = 0; @@ -131,6 +116,8 @@ static int32_t sxe2_vsi_destroy(struct sxe2_adapter *adapter, struct sxe2_vsi *v } l_free: + if (vsi->vsi_type == SXE2_VSI_T_DPDK_ESW) + TAILQ_REMOVE(&adapter->vsi_ctxt.other_vsi_list, vsi, next); rte_free(vsi); vsi = NULL; @@ -174,7 +161,7 @@ static int32_t sxe2_main_vsi_create(struct sxe2_adapter *adapter) goto l_end; l_free_vsi: - sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + rte_free(adapter->vsi_ctxt.main_vsi); adapter->vsi_ctxt.main_vsi = NULL; l_end: return ret; @@ -217,7 +204,7 @@ int32_t sxe2_other_vsi_create(struct sxe2_adapter *adapter, uint16_t cnt_vf) goto l_end; l_free_vsi: - sxe2_vsi_node_free(other_vsi); + rte_free(other_vsi); l_end: return ret; } @@ -230,7 +217,7 @@ int32_t sxe2_vsi_init(struct rte_eth_dev *dev) uint16_t srcvsi_cnt; PMD_INIT_FUNC_TRACE(); - + TAILQ_INIT(&adapter->vsi_ctxt.other_vsi_list); ret = sxe2_main_vsi_create(adapter); if (ret) { PMD_LOG_ERR(DRV, "Failed to create main VSI, ret=%d", ret); @@ -283,13 +270,14 @@ void sxe2_vsi_uninit(struct rte_eth_dev *dev) l_free: ret = sxe2_vsi_destroy(adapter, adapter->vsi_ctxt.main_vsi); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); goto l_end; } + adapter->vsi_ctxt.main_vsi = NULL; RTE_TAILQ_FOREACH_SAFE(var, &adapter->vsi_ctxt.other_vsi_list, next, tvar) { ret = sxe2_vsi_destroy(adapter, var); - if (ret) { + if (ret && ret != -EPERM) { PMD_LOG_ERR(DRV, "Failed to del vsi from fw, ret=%d", ret); break; } @@ -356,5 +344,6 @@ void sxe2_vsi_repr_main_vsi_destroy(struct rte_eth_dev *dev) { struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - sxe2_vsi_node_free(adapter->vsi_ctxt.main_vsi); + rte_free(adapter->vsi_ctxt.main_vsi); + adapter->vsi_ctxt.main_vsi = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 07/47] net/sxe2: initialize stats in representor device init 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (7 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming liujie5 ` (39 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_stats_init() call in sxe2_repr_dev_init to set up the statistics infrastructure for representor devices, and add the l_init_irq_ctxt_err error path to uninitialize the software irq context if stats initialization fails. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index f32318b731..c698baafe0 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -483,8 +483,16 @@ int32_t sxe2_repr_dev_init(struct rte_eth_dev *dev, goto l_init_sw_err; } + ret = sxe2_stats_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize stats, ret=[%d]", ret); + goto l_init_irq_ctxt_err; + } + goto l_end; +l_init_irq_ctxt_err: + sxe2_sw_irq_ctxt_uninit(dev); l_init_sw_err: sxe2_eth_uinit(dev); l_init_eth_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 08/47] net/sxe2: use base device name for representor naming 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (8 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:41 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors liujie5 ` (38 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Update the representor device naming to use the base device name prefix, and set the numa_node from the parent device data so that representor devices are allocated on the same NUMA node. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index c698baafe0..b7096f5927 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -552,8 +552,8 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, } for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - snprintf(name, sizeof(name), "sxe2_representor_c%dpf%d%s%u", - adapter->pf_idx, adapter->pf_idx, + snprintf(name, sizeof(name), "%s_representor_%s%u", + adapter->cdev->dev->name, "vf", req_eth_da->representor_ports[repr_idx]); @@ -562,6 +562,7 @@ int32_t sxe2_switchdev_repr_devs_init(struct sxe2_adapter *adapter, ret = -ENOMEM; goto l_release_port; } + eth_dev->data->numa_node = adapter->dev_info.dev_data->numa_node; eth_dev->data->dev_private = rte_zmalloc_socket(name, sizeof(struct sxe2_adapter), RTE_CACHE_LINE_SIZE, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (9 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming liujie5 @ 2026-08-31 2:41 ` liujie5 2026-08-31 2:42 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit liujie5 ` (37 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:41 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> When the PF link state changes in switchdev mode, refresh the link status of every VF representor and trigger the RTE_ETH_EVENT_INTR_LSC callback on each, so applications receive link events on representor ports. Also log OICR in hexadecimal for better readability. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index 3306504761..ba764dd5e4 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -77,14 +77,32 @@ static int32_t sxe2_fc_state_callback(struct rte_eth_dev *dev) static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t oicr) { struct rte_eth_dev *dev = &rte_eth_devices[adapter->dev_info.dev_data->port_id]; + struct rte_eth_dev *repr_eth_dev; + struct sxe2_adapter *repr_adapter; + uint16_t vf_id; if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { - PMD_DEV_LOG_INFO(adapter, DRV, "OICR=%" PRIu64, oicr); + PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); - if (rte_eal_process_type() == RTE_PROC_PRIMARY) + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL); + } + if (adapter->switchdev_info.is_switchdev) { + for (vf_id = 0; vf_id < adapter->repr_ctxt.nb_repr_vf; vf_id++) { + repr_eth_dev = adapter->repr_ctxt.vf_rep_eth_dev[vf_id]; + if (!repr_eth_dev) + continue; + repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); + (void)sxe2_drv_mac_link_status_get(repr_adapter); + if (rte_eal_process_type() == RTE_PROC_PRIMARY) { + rte_eth_dev_callback_process(repr_eth_dev, + RTE_ETH_EVENT_INTR_LSC, + NULL); + } + } + } } if (oicr & RTE_BIT32(SXE2_COM_SW_MODE_SWITCHDEV)) { PMD_DEV_LOG_INFO(adapter, DRV, "event notify switchdev"); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (10 preceding siblings ...) 2026-08-31 2:41 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields liujie5 ` (36 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_security_uinit() frees the security session but leaves dev->security_ctx pointing at the freed memory. Set dev->security_ctx to NULL after releasing the security context so a later access does not dereference a dangling pointer. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_security.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_security.c b/drivers/net/sxe2/sxe2_security.c index bc59d1b880..8f31067942 100644 --- a/drivers/net/sxe2/sxe2_security.c +++ b/drivers/net/sxe2/sxe2_security.c @@ -326,6 +326,7 @@ void sxe2_security_uinit(struct rte_eth_dev *dev) if (sctx != NULL) { rte_free(sctx); sctx = NULL; + dev->security_ctx = NULL; } sxe2_ipsec_uinit(adapter); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (11 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations liujie5 ` (35 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Rename repr_vf_k_vsi_id/repr_vf_u_vsi_id to repr_vf_primary_vsi_id/repr_vf_backup_vsi_id in sxe2_repr_private_data and update all references. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_dump.c | 8 ++++---- drivers/net/sxe2/sxe2_ethdev.h | 4 ++-- drivers/net/sxe2/sxe2_flow.c | 4 ++-- drivers/net/sxe2/sxe2_switchdev.c | 4 ++-- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index d43473e083..590219f502 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -211,16 +211,16 @@ sxe2_dump_switchdev_info(FILE *file, struct rte_eth_dev *dev) "\t -- repr_pf_id: %u\n" "\t -- repr_vf_id: %u\n" "\t -- repr_vf_vsi_id: %u\n" - "\t -- repr_vf_k_vsi_id: %s\n" - "\t -- repr_vf_u_vsi_id: %s\n", + "\t -- repr_vf_primary_vsi_id: %s\n" + "\t -- repr_vf_backup_vsi_id: %s\n", adapter->repr_priv_data->repr_id, adapter->repr_priv_data->repr_q_id, adapter->repr_priv_data->repr_pf_id, adapter->repr_priv_data->repr_vf_id, adapter->repr_priv_data->repr_vf_vsi_id, - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_k_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_primary_vsi_id, k_vsi_buf, sizeof(k_vsi_buf)), - sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_u_vsi_id, + sxe2_vsi_id_str(adapter->repr_priv_data->repr_vf_backup_vsi_id, u_vsi_buf, sizeof(u_vsi_buf))); goto l_end; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index c54e8a435e..158198d74b 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -263,8 +263,8 @@ struct sxe2_repr_private_data { uint16_t repr_pf_id; uint16_t repr_vf_id; uint16_t repr_vf_vsi_id; - uint16_t repr_vf_k_vsi_id; - uint16_t repr_vf_u_vsi_id; + uint16_t repr_vf_primary_vsi_id; + uint16_t repr_vf_backup_vsi_id; }; struct sxe2_sched_hw_cap { diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index 63cfc36968..cf54803301 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -380,9 +380,9 @@ static int32_t sxe2_flow_src_split_proc(struct rte_eth_dev *dev, if (adapter->switchdev_info.is_switchdev && adapter->is_dev_repr) { flow_bond_num = 1; flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = - adapter->repr_priv_data->repr_vf_u_vsi_id; + adapter->repr_priv_data->repr_vf_backup_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = - adapter->repr_priv_data->repr_vf_k_vsi_id; + adapter->repr_priv_data->repr_vf_primary_vsi_id; } for (idx = 0; idx < flow_bond_num; idx++) { diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index 44703cfb5c..efb1468b91 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,9 +312,9 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; - repr_priv_data->repr_vf_k_vsi_id = + repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; - repr_priv_data->repr_vf_u_vsi_id = + repr_priv_data->repr_vf_backup_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (12 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info liujie5 ` (34 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Remove duplicate function declarations from the sxe2 driver headers: - sxe2_drv_promisc_config, sxe2_drv_vsi_info_get and sxe2_drv_rxq_mapping_set in sxe2_cmd_chnl.h - sxe2_dev_pci_seg_unmap in sxe2_ethdev.h - sxe2_rx_pkts_scattered in sxe2_txrx_poll.h Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.h | 6 ------ drivers/net/sxe2/sxe2_ethdev.h | 2 -- drivers/net/sxe2/sxe2_txrx_poll.h | 2 -- 3 files changed, 10 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index d63caad526..294ac15db4 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -65,8 +65,6 @@ int32_t sxe2_drv_ipsec_rxsa_delete(struct sxe2_adapter *adapter, int32_t sxe2_drv_ipsec_txsa_delete(struct sxe2_adapter *adapter, uint16_t sa_id); -int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set); - int32_t sxe2_drv_udp_tunnel_add(struct sxe2_adapter *adapter, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); @@ -84,8 +82,6 @@ int32_t sxe2_drv_get_udp_tunnel_port(struct sxe2_adapter *adapter, int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); -int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi); - int32_t sxe2_drv_mac_link_status_get(struct sxe2_adapter *adapter); int32_t sxe2_drv_get_mac_stats(struct sxe2_adapter *adapter); @@ -110,8 +106,6 @@ int32_t sxe2_drv_mapping_reset(struct rte_eth_dev *eth_dev); int32_t sxe2_drv_mapping_stats_info_clear(struct rte_eth_dev *eth_dev); -int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, uint8_t pool_idx); - int32_t sxe2_drv_allmulti_config(struct sxe2_adapter *adapter, bool set); int32_t sxe2_drv_uc_config(struct sxe2_adapter *adapter, struct rte_ether_addr *addr, bool add); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 158198d74b..1409be74d3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -385,8 +385,6 @@ void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); int32_t sxe2_dev_pci_map_init(struct rte_eth_dev *dev); -void sxe2_dev_pci_seg_unmap(struct sxe2_adapter *adapter, uint32_t res_type); - int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, enum sxe2_udp_tunnel_protocol tunnel_proto, uint16_t udp_port); diff --git a/drivers/net/sxe2/sxe2_txrx_poll.h b/drivers/net/sxe2/sxe2_txrx_poll.h index 708e3839d7..bfa099c097 100644 --- a/drivers/net/sxe2/sxe2_txrx_poll.h +++ b/drivers/net/sxe2/sxe2_txrx_poll.h @@ -13,8 +13,6 @@ uint16_t sxe2_tx_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pkts, uint16_t uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); -uint16_t sxe2_rx_pkts_scattered(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); - uint16_t sxe2_rx_pkts_scattered_split(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); #endif /* SXE2_TXRX_POLL_H */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (13 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " liujie5 ` (33 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_infos_get() dereferences adapter->vsi_ctxt.main_vsi without checking for NULL, which can crash when the main VSI has not been created yet. Add an early NULL check on vsi and return -EINVAL. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 2e14c372f8..02f9ce3d32 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -781,6 +781,10 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct sxe2_vsi *vsi = adapter->vsi_ctxt.main_vsi; + if (unlikely(vsi == NULL)) { + PMD_LOG_ERR(INIT, "main vsi is NULL"); + return -EINVAL; + } dev_info->max_rx_queues = vsi->rxqs.q_cnt; dev_info->max_tx_queues = vsi->txqs.q_cnt; dev_info->min_rx_bufsize = SXE2_MIN_BUF_SIZE; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 14/47] net/sxe2: fill MAC addresses in device info 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (14 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report liujie5 ` (32 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Fill max_mac_addrs in sxe2_dev_infos_get() so applications can query the maximum number of MAC addresses supported by the device. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 02f9ce3d32..e85e34aa1a 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -792,6 +792,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, dev_info->max_lro_pkt_size = SXE2_FRAME_SIZE_MAX * SXE2_RX_LRO_DESC_MAX_NUM; dev_info->max_mtu = dev_info->max_rx_pktlen - SXE2_ETH_OVERHEAD; dev_info->min_mtu = RTE_ETHER_MIN_MTU; + dev_info->max_mac_addrs = SXE2_NUM_MACADDR_MAX; dev_info->rx_offload_capa = RTE_ETH_RX_OFFLOAD_VLAN_STRIP | -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (15 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers liujie5 ` (31 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Make the QINQ offload capabilities conditional on the port VLAN setting: only advertise RTE_ETH_TX_OFFLOAD_QINQ_INSERT, RTE_ETH_RX_OFFLOAD_QINQ_STRIP and RTE_ETH_RX_OFFLOAD_VLAN_FILTER when no port VLAN is configured. Report the buffer split supported header ptypes count in sxe2_buffer_split_supported_hdr_ptypes_get(). Fixes: a2b79a93515e ("net/sxe2: support L2 filtering and MAC config") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index e85e34aa1a..7a11a93dff 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -804,15 +804,11 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_RX_OFFLOAD_SCTP_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT | -#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC - RTE_ETH_RX_OFFLOAD_QINQ_STRIP | -#endif RTE_ETH_RX_OFFLOAD_VLAN_EXTEND | RTE_ETH_RX_OFFLOAD_TCP_LRO; dev_info->tx_offload_capa = RTE_ETH_TX_OFFLOAD_VLAN_INSERT | - RTE_ETH_TX_OFFLOAD_QINQ_INSERT | RTE_ETH_TX_OFFLOAD_MULTI_SEGS | RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE | RTE_ETH_TX_OFFLOAD_IPV4_CKSUM | @@ -855,14 +851,22 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO; - if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) - dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; - if (sxe2_ipsec_supported(adapter)) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_SECURITY; dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_SECURITY; } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_PTP) + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_TIMESTAMP; + + if (!sxe2_dev_port_vlan_check(dev)) { + dev_info->tx_offload_capa |= RTE_ETH_TX_OFFLOAD_QINQ_INSERT; +#ifndef RTE_LIBRTE_SXE2_16BYTE_RX_DESC + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP; +#endif + dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; + } + if (adapter->cap_flags & SXE2_DEV_CAPS_OFFLOAD_RSS) { dev_info->rx_offload_capa |= RTE_ETH_RX_OFFLOAD_RSS_HASH; dev_info->flow_type_rss_offloads |= SXE2_RSS_HF_SUPPORT_ALL; @@ -934,7 +938,7 @@ static int32_t sxe2_dev_infos_get(struct rte_eth_dev *dev, static const uint32_t * sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, - size_t *no_of_elements __rte_unused) + size_t *no_of_elements) { static const uint32_t ptypes[] = { RTE_PTYPE_L2_ETHER, @@ -972,6 +976,7 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, RTE_PTYPE_UNKNOWN }; + *no_of_elements = RTE_DIM(ptypes) - 1; return ptypes; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 16/47] net/sxe2: use regular write for mapped registers 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (16 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header liujie5 ` (30 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_pci_map_write_reg() uses the write-combined store (SXE2_PCI_REG_WRITE_WC) to write control registers, which is intended for doorbell/tail writes and can be lossy or delayed for ordering sensitive register updates. Add SXE2_PCI_REG_WRITE macro using a regular rte_write32() and use it in sxe2_pci_map_write_reg(). Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 2 +- drivers/net/sxe2/sxe2_ethdev.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 7a11a93dff..589f09c113 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1439,7 +1439,7 @@ void sxe2_pci_map_write_reg(struct sxe2_adapter *adapter, goto l_ret; } - SXE2_PCI_REG_WRITE_WC(reg_addr, value); + SXE2_PCI_REG_WRITE(reg_addr, value); l_ret: return; } diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index 1409be74d3..cf1104144c 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -355,6 +355,8 @@ struct sxe2_adapter { #define SXE2_DEV_PRIVATE_TO_ADAPTER(dev) \ ((struct sxe2_adapter *)(dev)->data->dev_private) +#define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) + void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, uint16_t idx_in_func); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (17 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type liujie5 ` (29 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Move SXE2_PCI_REG_READ to sxe2_ethdev.h so the PCI register access macros are kept together in the common header, matching SXE2_PCI_REG_WRITE. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_queue.h | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index cf1104144c..f2557b28c3 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -356,6 +356,7 @@ struct sxe2_adapter { ((struct sxe2_adapter *)(dev)->data->dev_private) #define SXE2_PCI_REG_WRITE(reg, value) rte_write32((rte_cpu_to_le_32(value)), (reg)) +#define SXE2_PCI_REG_READ(reg) rte_read32(reg) void *sxe2_pci_map_addr_get(struct sxe2_adapter *adapter, enum sxe2_pci_map_resource res_type, diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index a300b66771..10bdaf5b8d 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -12,8 +12,6 @@ #include "sxe2_drv_cmd.h" #include "sxe2_txrx_common.h" -#define SXE2_PCI_REG_READ(reg) \ - rte_read32(reg) #define SXE2_PCI_REG_WRITE_WC(reg, value) \ rte_write32_wc((rte_cpu_to_le_32(value)), reg) #define SXE2_PCI_REG_WRITE_WC_RELAXED(reg, value) \ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 18/47] net/sxe2: validate PCI map resource type 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (18 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized liujie5 ` (28 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_res_seg_map() indexes adapter->map_ctxt.addr_info[] with res_type without bounds checking, which can access out of bounds when an invalid resource type is passed. Add a bounds check on res_type and return -EINVAL. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 589f09c113..9ef93b8076 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1552,6 +1552,12 @@ int32_t sxe2_dev_pci_res_seg_map(struct sxe2_adapter *adapter, struct sxe2_pci_map_addr_info *addr_info = NULL; int32_t ret = 0; + if (unlikely(res_type >= SXE2_PCI_MAP_RES_MAX_COUNT)) { + PMD_DEV_LOG_ERR(adapter, INIT, "Invalid resource type %u", res_type); + ret = -EINVAL; + goto l_end; + } + addr_info = &adapter->map_ctxt.addr_info[res_type]; if (!addr_info || addr_info->bar_idx == SXE2_PCI_MAP_BAR_INVALID) { PMD_DEV_LOG_ERR(adapter, INIT, "Invalid bar index with resource type %d", res_type); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (19 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:42 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit liujie5 ` (27 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_pci_map_uinit() calls sxe2_dev_pci_seg_unmap() and walks bar_info unconditionally. Only perform the unmap and free when bar_info has been allocated, so an uninitialized map context is handled cleanly. Fixes: 66a10eb60ebe ("net/sxe2: add PCI BAR mapping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 9ef93b8076..fdff4ae10f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1773,14 +1773,13 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) uint8_t i = 0; PMD_INIT_FUNC_TRACE(); + if (map_ctxt->bar_info != NULL) { + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); + (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_RX_TAIL); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_DOORBELL_TX); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_DYN); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_ITR); - (void)sxe2_dev_pci_seg_unmap(adapter, SXE2_PCI_MAP_RES_IRQ_MSIX); - - if (map_ctxt != NULL && map_ctxt->bar_info != NULL) { for (i = 0; i < map_ctxt->bar_cnt; i++) { bar_info = &map_ctxt->bar_info[i]; if (bar_info != NULL && bar_info->seg_info != NULL) { @@ -1791,7 +1790,6 @@ void sxe2_dev_pci_map_uinit(struct rte_eth_dev *dev) rte_free(map_ctxt->bar_info); map_ctxt->bar_info = NULL; } - adapter->dev_info.dev_data = NULL; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (20 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized liujie5 @ 2026-08-31 2:42 ` liujie5 2026-08-31 2:43 ` [PATCH v7 21/47] net/sxe2: fix duplicated cleanup in dev close liujie5 ` (26 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:42 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_uninit() calls rep_dev->dev_ops->dev_close() for each VF representor without checking that dev_ops or dev_close is present, which can crash when the representor device is not fully initialized. Guard the call with NULL checks. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index fdff4ae10f..41ea67a607 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2074,9 +2074,11 @@ static int32_t sxe2_dev_uninit(struct rte_eth_dev *dev) for (i = 0; i < adapter->repr_ctxt.nb_repr_vf; i++) { rep_dev = adapter->repr_ctxt.vf_rep_eth_dev[i]; if (rep_dev) { - ret = rep_dev->dev_ops->dev_close(rep_dev); - if (ret) - goto l_end; + if (rep_dev->dev_ops && rep_dev->dev_ops->dev_close) { + ret = rep_dev->dev_ops->dev_close(rep_dev); + if (ret) + goto l_end; + } if (rep_dev->intr_handle) rte_intr_instance_free(rep_dev->intr_handle); ret = rte_eth_dev_release_port(rep_dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 21/47] net/sxe2: fix duplicated cleanup in dev close 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (21 preceding siblings ...) 2026-08-31 2:42 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 22/47] net/sxe2: align dev init and cleanup order liujie5 ` (25 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_dev_close() calls sxe2_switchdev_uninit() and sxe2_dev_pci_map_uinit() twice, and releases resources in an order that does not match the initialization sequence. Remove the duplicated calls and align the teardown order with the device init order. Fixes: 8cebf80f1eda ("net/sxe2: support Rx interrupt") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 41ea67a607..5d14e28d96 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2041,17 +2041,15 @@ static int32_t sxe2_dev_close(struct rte_eth_dev *dev) (void)sxe2_queues_release(dev); sxe2_mp_uninit(dev); (void)sxe2_sched_uinit(dev); - (void)sxe2_rss_disable(dev); (void)sxe2_flow_uninit(dev); + (void)sxe2_rss_disable(dev); (void)sxe2_udp_tunnel_port_clear(dev); - sxe2_vsi_uninit(dev); sxe2_security_uinit(dev); sxe2_intr_uninit(dev); (void)sxe2_switchdev_uninit(dev); sxe2_sw_uninit(dev); - (void)sxe2_switchdev_uninit(dev); - sxe2_dev_pci_map_uinit(dev); sxe2_eth_uinit(dev); + sxe2_vsi_uninit(dev); sxe2_dev_pci_map_uinit(dev); sxe2_free_repr_info(dev); sxe2_fc_state_uinit(dev); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 22/47] net/sxe2: align dev init and cleanup order 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (22 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 21/47] net/sxe2: fix duplicated cleanup in dev close liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 23/47] net/sxe2: simplify switchdev representor matching liujie5 ` (24 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_eth_init() to be called before sxe2_sw_init() and rearrange the error cleanup labels so that resources are torn down in the reverse order of initialization. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5d14e28d96..5bce710b29 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -1942,6 +1942,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_switchdev_err; } + ret = sxe2_eth_init(dev); + if (ret) { + PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); + goto init_eth_err; + } + ret = sxe2_sw_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize sw parameters, ret=[%d]", ret); @@ -1954,12 +1960,6 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, goto init_irq_err; } - ret = sxe2_eth_init(dev); - if (ret) { - PMD_LOG_ERR(INIT, "Failed to initialize eth parameters, ret=%d", ret); - goto init_eth_err; - } - ret = sxe2_security_init(dev); if (ret) { PMD_LOG_ERR(INIT, "Failed to initialize security, ret=%d", ret); @@ -2014,12 +2014,12 @@ static int32_t sxe2_dev_init(struct rte_eth_dev *dev, init_rss_err: sxe2_security_uinit(dev); init_security_err: - sxe2_eth_uinit(dev); -init_eth_err: sxe2_intr_uninit(dev); init_irq_err: sxe2_sw_uninit(dev); init_sw_err: + sxe2_eth_uinit(dev); +init_eth_err: (void)sxe2_switchdev_uninit(dev); init_switchdev_err: init_dev_info_err: -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 23/47] net/sxe2: simplify switchdev representor matching 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (23 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 22/47] net/sxe2: align dev init and cleanup order liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 24/47] net/sxe2: rename fnav cid manager symbols to flow liujie5 ` (23 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_match() encodes the kernel representor ID and compares it against each requested port, which is fragile. Match the PF number and VF ID directly against the switchdev representor info instead, and drop the sxe2_switchdev_repr_id_encode_get() helper. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 72 +++++++++++++++++----------------- drivers/net/sxe2/sxe2_ethdev.h | 3 -- 2 files changed, 37 insertions(+), 38 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 5bce710b29..08986e384f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -2149,42 +2149,25 @@ static int32_t sxe2_fw_version_string_get(struct rte_eth_dev *dev, char *fw_vers return ret; } -static uint16_t sxe2_switchdev_repr_id_encode_get(struct sxe2_switchdev_info *switchdev_info) -{ - enum rte_eth_representor_type type; - uint16_t repr = switchdev_info->vf_num; - uint32_t pf = switchdev_info->pf_num; - - switch (switchdev_info->port_name_type) { - case SXE2_PHYS_PORT_NAME_TYPE_UPLINK: - if (!switchdev_info->representor) - return UINT16_MAX; - type = RTE_ETH_REPRESENTOR_PF; - pf = switchdev_info->mpesw_owner; - break; - case SXE2_PHYS_PORT_NAME_TYPE_PFVF: - default: - type = RTE_ETH_REPRESENTOR_VF; - break; - } - - return SXE2_REPRESENTOR_ID(pf, type, repr); -} - static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, struct rte_eth_devargs *req_eth_da) { - uint32_t port_idx = 0; - uint32_t repr_idx; - uint16_t kernel_repr_id = sxe2_switchdev_repr_id_encode_get(&adapter->switchdev_info); - uint16_t repr_id; + uint16_t port_idx; + uint16_t repr_idx; + uint16_t vf_id; + uint16_t i; switch (req_eth_da->type) { case RTE_ETH_REPRESENTOR_PF: + if (adapter->switchdev_info.port_name_type != + SXE2_PHYS_PORT_NAME_TYPE_UPLINK) { + rte_errno = EBUSY; + return false; + } break; case RTE_ETH_REPRESENTOR_VF: if (adapter->switchdev_info.port_name_type != - SXE2_PHYS_PORT_NAME_TYPE_PFVF) { + SXE2_PHYS_PORT_NAME_TYPE_PFVF) { rte_errno = EBUSY; return false; } @@ -2197,15 +2180,34 @@ static bool sxe2_switchdev_repr_match(struct sxe2_adapter *adapter, return false; } + if (req_eth_da->nb_ports > 0) { + for (port_idx = 0; port_idx < req_eth_da->nb_ports; ++port_idx) { + if (adapter->switchdev_info.pf_num == req_eth_da->ports[port_idx]) + break; + } + if (port_idx == req_eth_da->nb_ports) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev pf %u not match req pf", + adapter->switchdev_info.pf_num); + rte_errno = EBUSY; + return false; + } + } + for (repr_idx = 0; repr_idx < req_eth_da->nb_representor_ports; ++repr_idx) { - repr_id = SXE2_REPRESENTOR_ID(req_eth_da->ports[port_idx], - req_eth_da->type, - req_eth_da->representor_ports[repr_idx]); - if (repr_id == kernel_repr_id) - return true; - } - rte_errno = EBUSY; - return false; + for (i = 0; i < adapter->repr_ctxt.nb_vf; ++i) { + vf_id = rte_le_to_cpu_16(adapter->repr_ctxt.repr_vf_id[i].func_id); + if (vf_id == req_eth_da->representor_ports[repr_idx]) + break; + } + if (i == adapter->repr_ctxt.nb_vf) { + PMD_DEV_LOG_DEBUG(adapter, DRV, "switchdev vf %u not match req vf(cnt:%u)", + req_eth_da->representor_ports[repr_idx], adapter->repr_ctxt.nb_vf); + rte_errno = EBUSY; + return false; + } + } + + return true; } static int32_t sxe2_eth_pmd_probe_pf(struct sxe2_common_device *cdev, diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index f2557b28c3..e818578319 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -65,9 +65,6 @@ enum sxe2_fnav_tunnel_flag_type { #define upper_32_bits(n) ((uint32_t)(((n) >> 16) >> 16)) #define lower_32_bits(n) ((uint32_t)((n) & 0xffffffff)) -#define SXE2_REPRESENTOR_ID(pf, type, repr) \ - (((pf) << 14) + ((type) << 12) + ((repr) & 0xfff)) - #define SXE2_I2C_EEPROM_DEV_ADDR 0xA0 #define SXE2_I2C_EEPROM_DEV_ADDR2 0xA2 #define SXE2_MODULE_TYPE_SFP 0x03 -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 24/47] net/sxe2: rename fnav cid manager symbols to flow 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (24 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 23/47] net/sxe2: simplify switchdev representor matching liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 25/47] net/sxe2: move tunnel port helpers into flow module liujie5 ` (22 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Rename the sxe2_fnav_cid_mgr, sxe2_fnav_cid_mgr_list_t, sxe2_fnav_count_resource and sxe2_fnav_get_filter_cid symbols to the sxe2_flow_* prefix for consistency with the flow module naming. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 2 +- drivers/net/sxe2/sxe2_cmd_chnl.h | 2 +- drivers/net/sxe2/sxe2_flow.c | 46 ++++++++++++++--------------- drivers/net/sxe2/sxe2_flow.h | 6 ++-- drivers/net/sxe2/sxe2_flow_define.h | 12 ++++---- 5 files changed, 34 insertions(+), 34 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index b09989fe50..3229c72597 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1800,7 +1800,7 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat } int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr) + struct sxe2_flow_cid_mgr *mgr) { struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index 294ac15db4..cfea1a1f0e 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -159,7 +159,7 @@ int32_t sxe2_drv_flow_fnav_get_stat_id(struct sxe2_adapter *adapter, uint32_t *s int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, - struct sxe2_fnav_cid_mgr *mgr); + struct sxe2_flow_cid_mgr *mgr); int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cf54803301..a33b8606df 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -857,7 +857,7 @@ static int32_t sxe2_flow_rte_list_free(struct sxe2_adapter *adapter, struct rte_flow *flow_temp = NULL; struct sxe2_flow *hw_flow = NULL; struct sxe2_flow *hw_flow_temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; rte_spinlock_lock(&adapter->flow_ctxt.flow_list_lock); TAILQ_FOREACH(flow_temp, &adapter->flow_ctxt.rte_flow_list, next) { if (flow_temp == flow) @@ -1028,7 +1028,7 @@ static struct rte_flow *sxe2_flow_create(struct rte_eth_dev *dev, goto l_free_flow; TAILQ_FOREACH(flow, &flow_list->sxe2_flow_list, next) { - ret = sxe2_fnav_get_filter_cid(adapter, flow); + ret = sxe2_flow_get_filter_cid(adapter, flow); if (ret != 0) { PMD_LOG_ERR(DRV, "fnav get stats id failed, ret:%d", ret); rte_flow_error_set(error, EIO, @@ -1088,16 +1088,16 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e return ret; } -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1112,7 +1112,7 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow } if (mgr == NULL) { mgr = rte_zmalloc("sxe2_fnav_cid_mgr", - sizeof(struct sxe2_fnav_cid_mgr), 0); + sizeof(struct sxe2_flow_cid_mgr), 0); if (!mgr) { PMD_LOG_ERR(DRV, "Failed to alloc sxe2vf_fnav_cid_mgr memory."); @@ -1143,13 +1143,13 @@ int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *mgr = *mgr_ptr; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; if (user_id == 0) { TAILQ_REMOVE(cid_mgr_list, mgr, next); @@ -1170,14 +1170,14 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; @@ -1218,7 +1218,7 @@ static int32_t sxe2_flow_query_count(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_fnav_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *mgr = NULL; switch (flow->action.count.stat_ctrl) { case SXE2_FNAV_STAT_ENA_NONE: count->hits_set = 0; @@ -1348,7 +1348,7 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.fnav_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) adapter->flow_ctxt.hw_res.count_type = adapter->devargs.fnav_stat_type; @@ -1370,10 +1370,10 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) int32_t ret = 0; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); struct rte_flow_error error; - struct sxe2_fnav_cid_mgr *mgr = NULL; - struct sxe2_fnav_cid_mgr *temp = NULL; - struct sxe2_fnav_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr *mgr = NULL; + struct sxe2_flow_cid_mgr *temp = NULL; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = + &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; ret = sxe2_flow_flush(dev, &error); if (ret) diff --git a/drivers/net/sxe2/sxe2_flow.h b/drivers/net/sxe2/sxe2_flow.h index daaeedd4dc..8d47b11ff4 100644 --- a/drivers/net/sxe2/sxe2_flow.h +++ b/drivers/net/sxe2/sxe2_flow.h @@ -14,16 +14,16 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev); int32_t sxe2_flow_uninit(struct rte_eth_dev *dev); -int32_t sxe2_fnav_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); +int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow); int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct sxe2_flow *flow, - struct sxe2_fnav_cid_mgr **mgr_ptr, + struct sxe2_flow_cid_mgr **mgr_ptr, struct rte_flow_error *error); int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev); diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 263a573f04..8a5d871978 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -98,8 +98,8 @@ struct rte_flow { }; TAILQ_HEAD(rte_flow_list_t, rte_flow); -struct sxe2_fnav_cid_mgr { - TAILQ_ENTRY(sxe2_fnav_cid_mgr) next; +struct sxe2_flow_cid_mgr { + TAILQ_ENTRY(sxe2_flow_cid_mgr) next; uint16_t stat_index; uint32_t user_id; uint32_t driver_id; @@ -107,18 +107,18 @@ struct sxe2_fnav_cid_mgr { uint64_t hits; uint64_t bytes; }; -TAILQ_HEAD(sxe2_fnav_cid_mgr_list_t, sxe2_fnav_cid_mgr); +TAILQ_HEAD(sxe2_flow_cid_mgr_list_t, sxe2_flow_cid_mgr); -struct sxe2_fnav_count_resource { +struct sxe2_flow_count_resource { uint32_t count_type; uint32_t global_index; - struct sxe2_fnav_cid_mgr_list_t fnav_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t flow_cid_mgr_list; }; struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_fnav_count_resource hw_res; + struct sxe2_flow_count_resource hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 25/47] net/sxe2: move tunnel port helpers into flow module 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (25 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 24/47] net/sxe2: rename fnav cid manager symbols to flow liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 26/47] net/sxe2: add ACL engine event statistics support liujie5 ` (21 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Move sxe2_flow_parse_pattern_ipip, sxe2_flow_add_udp_tunnel_port and sxe2_flow_add_tunnel_port from sxe2_flow_parse_pattern.c into sxe2_flow.c as static helpers, and drop the public declaration of sxe2_flow_add_tunnel_port from the header, keeping the tunnel port handling internal to the flow module. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow.c | 113 +++++++++++++++++++++ drivers/net/sxe2/sxe2_flow_parse_pattern.c | 113 --------------------- drivers/net/sxe2/sxe2_flow_parse_pattern.h | 6 -- 3 files changed, 113 insertions(+), 119 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index a33b8606df..cd39385340 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -550,6 +550,119 @@ int32_t sxe2_flow_init_udp_tunnel_port(struct rte_eth_dev *dev) return ret; } +static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, + enum sxe2_flow_udp_tunnel_protocol proto, + struct sxe2_flow *flow, + BITMAP_TYPE *flow_type) +{ + int32_t ret = 0; + uint16_t tun_port; + + tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; + if (tun_port == 0xffff || tun_port == 0) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); + goto l_end; + } + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + ret = -EINVAL; + PMD_LOG_ERR(DRV, "UDP must be over tunnel"); + goto l_end; + } + sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); + flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); +l_end: + return ret; +} + +static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) +{ + sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV4; + if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) + flow->pattern_outer.item_spec.ipv6.nexthdr = + SXE2_FLOW_IP_PROTOCOL_IPV6; + } + } + return 0; +} + +static int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, + struct rte_flow_error *error, + struct sxe2_flow *flow, BITMAP_TYPE *flow_type, + enum sxe2_flow_tunnel_type tunnel_type) +{ + int32_t ret = 0; + enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; + struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_pattern *pattern = &flow->pattern_outer; + switch (tunnel_type) { + case SXE2_FLOW_TUNNEL_TYPE_VXLAN: + if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; + } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || + sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; + } + break; + case SXE2_FLOW_TUNNEL_TYPE_GTPU: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; + break; + case SXE2_FLOW_TUNNEL_TYPE_GENEVE: + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; + break; + case SXE2_FLOW_TUNNEL_TYPE_GRE: + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { + proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; + } else { + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { + pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); + } + if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { + pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; + sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); + } + } + break; + case SXE2_FLOW_TUNNEL_TYPE_IPIP: + ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); + break; + default: + break; + } + if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { + ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); + if (ret != 0) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + NULL, "Failed to add udp port for tunnel."); + PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); + goto l_end; + } + } + if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { + if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) + sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); + } +l_end: + return ret; +} + static int32_t sxe2_flowlist_add_tunnel_port(struct rte_eth_dev *dev, struct rte_flow *flow_list, struct rte_flow_error *error) diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.c b/drivers/net/sxe2/sxe2_flow_parse_pattern.c index f5bf8922c6..189abb1a33 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.c +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.c @@ -1637,119 +1637,6 @@ static int32_t sxe2_flow_parse_pattern_vxlan_gpe(const struct rte_flow_item *ite return ret; } -static int32_t sxe2_flow_parse_pattern_ipip(struct sxe2_flow *flow, BITMAP_TYPE *flow_type) -{ - sxe2_set_bit(SXE2_EXPANSION_IPIP, flow_type); - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_IPV6; - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, flow->pattern_outer.map_spec); - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - flow->pattern_outer.item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_ETH; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV4; - if (sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) - flow->pattern_outer.item_spec.ipv6.nexthdr = - SXE2_FLOW_IP_PROTOCOL_IPV6; - } - } - return 0; -} - -static int32_t sxe2_flow_add_udp_tunnel_port(struct sxe2_adapter *adapter, - enum sxe2_flow_udp_tunnel_protocol proto, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type) -{ - int32_t ret = 0; - uint16_t tun_port; - - tun_port = adapter->flow_ctxt.tunnel_port_list[proto]; - if (tun_port == 0xffff || tun_port == 0) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP tunnel port not initialized, proto: %d", proto); - goto l_end; - } - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - ret = -EINVAL; - PMD_LOG_ERR(DRV, "UDP must be over tunnel"); - goto l_end; - } - sxe2_set_bit(SXE2_FLOW_FLD_ID_UDP_DST_PORT, flow->pattern_outer.map_spec); - flow->pattern_outer.item_spec.udp.dest = rte_cpu_to_be_16(tun_port); -l_end: - return ret; -} - -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type) -{ - int32_t ret = 0; - enum sxe2_flow_udp_tunnel_protocol proto = SXE2_FLOW_UDP_TUNNEL_MAX; - struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); - struct sxe2_flow_pattern *pattern = &flow->pattern_outer; - switch (tunnel_type) { - case SXE2_FLOW_TUNNEL_TYPE_VXLAN: - if (sxe2_test_bit(SXE2_EXPANSION_ETH, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN; - } else if (sxe2_test_bit(SXE2_EXPANSION_IPV4, flow_type) || - sxe2_test_bit(SXE2_EXPANSION_IPV6, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_VXLAN_GPE; - } - break; - case SXE2_FLOW_TUNNEL_TYPE_GTPU: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GTP_U; - break; - case SXE2_FLOW_TUNNEL_TYPE_GENEVE: - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_GENEVE; - break; - case SXE2_FLOW_TUNNEL_TYPE_GRE: - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) { - proto = SXE2_FLOW_UDP_TUNNEL_PROTOCOL_NVGRE; - } else { - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV4, flow_type)) { - pattern->item_spec.ipv4.protocol = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV4_PROT, pattern->map_spec); - } - if (sxe2_test_bit(SXE2_EXPANSION_OUTER_IPV6, flow_type)) { - pattern->item_spec.ipv6.nexthdr = SXE2_FLOW_IP_PROTOCOL_GRE; - sxe2_set_bit(SXE2_FLOW_FLD_ID_IPV6_PROT, pattern->map_spec); - } - } - break; - case SXE2_FLOW_TUNNEL_TYPE_IPIP: - ret = sxe2_flow_parse_pattern_ipip(flow, flow_type); - break; - default: - break; - } - if (proto != SXE2_FLOW_UDP_TUNNEL_MAX) { - ret = sxe2_flow_add_udp_tunnel_port(adapter, proto, flow, flow_type); - if (ret != 0) { - rte_flow_error_set(error, EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, "Failed to add udp port for tunnel."); - PMD_LOG_ERR(DRV, "Failed to add udp port for tunnel, ret %d.", ret); - goto l_end; - } - } - if (tunnel_type != SXE2_FLOW_TUNNEL_TYPE_NONE) { - if (!sxe2_test_bit(SXE2_EXPANSION_OUTER_UDP, flow_type)) - sxe2_set_bit(SXE2_FLOW_HDR_IPV_OTHER, pattern->hdrs); - } -l_end: - return ret; -} - struct sxe2_flow_parse_pattern_ops sxe2_flow_parse_pattern_list[] = { [SXE2_EXPANSION_OUTER_ETH] = { .is_inner = false, diff --git a/drivers/net/sxe2/sxe2_flow_parse_pattern.h b/drivers/net/sxe2/sxe2_flow_parse_pattern.h index 8442c35cae..69d83a6ea6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_pattern.h +++ b/drivers/net/sxe2/sxe2_flow_parse_pattern.h @@ -37,10 +37,4 @@ int32_t sxe2_flow_parse_pattern(struct rte_eth_dev *dev, struct rte_flow_error *error, struct sxe2_flow *flow); -int32_t sxe2_flow_add_tunnel_port(struct rte_eth_dev *dev, - struct rte_flow_error *error, - struct sxe2_flow *flow, - BITMAP_TYPE *flow_type, - enum sxe2_flow_tunnel_type tunnel_type); - #endif /* SXE2_FLOW_PARSE_PATTERN_H_ */ -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 26/47] net/sxe2: add ACL engine event statistics support 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (26 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 25/47] net/sxe2: move tunnel port helpers into flow module liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 27/47] net/sxe2: refactor primary process MP message handling liujie5 ` (20 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Add statistics support for the ACL flow engine to track packet hits and bytes, enabling flow aging and traffic monitoring for ACL rules. - Add acl-stat-type devarg to configure the statistics type - Implement sxe2_drv_flow_acl_get_stat_id/free_stat/query_stat - Handle the ACL engine in flow create/destroy/query paths - Add fnav_hw_res and acl_hw_res count resources Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 11 +++ drivers/net/sxe2/sxe2_cmd_chnl.c | 71 ++++++++++++++++++ drivers/net/sxe2/sxe2_cmd_chnl.h | 7 ++ drivers/net/sxe2/sxe2_drv_cmd.h | 7 ++ drivers/net/sxe2/sxe2_dump.c | 2 + drivers/net/sxe2/sxe2_ethdev.c | 23 ++++-- drivers/net/sxe2/sxe2_ethdev.h | 1 + drivers/net/sxe2/sxe2_flow.c | 90 ++++++++++++++++++----- drivers/net/sxe2/sxe2_flow_define.h | 5 +- drivers/net/sxe2/sxe2_flow_parse_action.c | 28 ++++--- drivers/net/sxe2/sxe2_queue.c | 2 + 11 files changed, 211 insertions(+), 36 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index 8278a5f108..c5b400a8ba 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -98,6 +98,17 @@ Runtime Configuration Default value is 3 (count both packets and bytes). +- ``acl-stat-type`` parameter [int] + + This parameter controls the ACL flow engine statistics type + used for flow rule hit counting (via ``rte_flow_query``). + + - 1: Only count the number of packets. + - 2: Only count the number of bytes. + - 3: Count both packets and bytes (default). + + Default value is 3 (count both packets and bytes). + - ``drv-sw-stats`` parameter [int] This parameter controls whether per-packet software statistics (SW stats) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3229c72597..3a55528c44 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1829,6 +1829,77 @@ int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, return ret; } +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id) +{ + struct sxe2_drv_flow_fnav_get_stat_id_req req = { 0 }; + struct sxe2_drv_flow_fnav_get_stat_id_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, + &req, sizeof(req), + &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get acl stat id, ret: %d.", ret); + goto l_end; + } + *stat_id = resp.stat_id; + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id) +{ + struct sxe2_drv_flow_fnav_free_stat_id_req req = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = stat_id; + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, + &req, sizeof(req), + NULL, 0); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to free acl stat id, ret: %d.", ret); + goto l_end; + } + +l_end: + return ret; +} + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr) +{ + struct sxe2_drv_flow_fnav_query_stat_req req = { 0 }; + struct sxe2_drv_flow_fnav_query_stat_resp resp = { 0 }; + struct sxe2_drv_cmd_params cmd = { 0 }; + struct sxe2_common_device *cdev = adapter->cdev; + int32_t ret = -1; + + req.stat_id = mgr->stat_index; + req.stat_ctrl = mgr->count_type; + req.is_clear = 1; + + sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY, + &req, sizeof(req), &resp, sizeof(resp)); + ret = sxe2_drv_cmd_exec(cdev, &cmd); + if (ret) { + PMD_DEV_LOG_ERR(adapter, DRV, "Failed to query ACL stat, stat id: %u, ret: %d.", + req.stat_id, ret); + goto l_end; + } + mgr->hits += resp.stat_hits; + mgr->bytes += resp.stat_bytes; + +l_end: + return ret; +} + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set) { diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.h b/drivers/net/sxe2/sxe2_cmd_chnl.h index cfea1a1f0e..7d07068bfc 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.h +++ b/drivers/net/sxe2/sxe2_cmd_chnl.h @@ -161,6 +161,13 @@ int32_t sxe2_drv_flow_fnav_free_stat(struct sxe2_adapter *adapter, uint32_t stat int32_t sxe2_drv_flow_fnav_query_stat(struct sxe2_adapter *adapter, struct sxe2_flow_cid_mgr *mgr); +int32_t sxe2_drv_flow_acl_get_stat_id(struct sxe2_adapter *adapter, uint32_t *stat_id); + +int32_t sxe2_drv_flow_acl_free_stat(struct sxe2_adapter *adapter, uint32_t stat_id); + +int32_t sxe2_drv_flow_acl_query_stat(struct sxe2_adapter *adapter, + struct sxe2_flow_cid_mgr *mgr); + int32_t sxe2_drv_srcvsi_prune_config(struct sxe2_adapter *adapter, uint16_t *vsi_list, uint16_t vsi_cnt, bool set); diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 03ef3b315d..01fd813ed1 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -824,6 +824,13 @@ enum sxe2_drv_cmd_code { SXE2_DRV_CMD_OPT_EEP_GET = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_OPT, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), + SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2), + SXE2_DRV_CMD_FLOW_ACL_STAT_FREE = + SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 3), + }; #endif /* SXE2_DRV_CMD_H */ diff --git a/drivers/net/sxe2/sxe2_dump.c b/drivers/net/sxe2/sxe2_dump.c index 590219f502..31f7d6ba61 100644 --- a/drivers/net/sxe2/sxe2_dump.c +++ b/drivers/net/sxe2/sxe2_dump.c @@ -80,12 +80,14 @@ sxe2_dump_dev_args_info(FILE *file, struct rte_eth_dev *dev) "\t -- no_sched_mode: %s\n" "\t -- flow-duplicate-pattern: %u\n" "\t -- fnav-stat-type: %u\n" + "\t -- acl-stat-type: %u\n" "\t -- sched_layer_mode: %u\n" "\t -- rx_low_latency: %s\n" "\t -- function-flow-direct: %s\n", adapter->devargs.no_sched_mode ? "On" : "Off", adapter->devargs.flow_dup_pattern_mode, adapter->devargs.fnav_stat_type, + adapter->devargs.acl_stat_type, adapter->devargs.sched_layer_mode, adapter->devargs.rx_low_latency ? "On" : "Off", adapter->devargs.func_flow_direct_en ? "On" : "Off"); diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 08986e384f..77a31eb8a1 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -72,6 +72,7 @@ static const struct rte_pci_id pci_id_sxe2_tbl[] = { #define SXE2_DEVARG_FLOW_DUP_PATTERN_MODE "flow-duplicate-pattern" #define SXE2_DEVARG_FUNC_FLOW_DIRCT "function-flow-direct" #define SXE2_DEVARG_FNAV_STAT_TYPE "fnav-stat-type" +#define SXE2_DEVARG_ACL_STAT_TYPE "acl-stat-type" #define SXE2_DEVARG_NO_SCHED_MODE "no-sched-mode" #define SXE2_DEVARG_SCHED_LAYER_MODE "sched-layer-mode" #define SXE2_DEVARG_RX_LOW_LATENCY "rx-low-latency" @@ -981,11 +982,11 @@ sxe2_buffer_split_supported_hdr_ptypes_get(struct rte_eth_dev *dev __rte_unused, return ptypes; } -static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, void *args) +static int32_t sxe2_parse_stat_type(const char *key, const char *value, void *args) { int32_t ret = -EINVAL; uint8_t *num = (uint8_t *)args; - unsigned long fnav_stat_type; + unsigned long stat_type; char *endptr = NULL; if (value == NULL || args == NULL) { @@ -993,19 +994,19 @@ static int32_t sxe2_parse_fnav_stat_type(const char *key, const char *value, voi goto l_end; } errno = 0; - fnav_stat_type = strtoul(value, &endptr, 10); + stat_type = strtoul(value, &endptr, 10); if (errno != 0 || endptr == value || *endptr != '\0') { PMD_LOG_WARN(INIT, "%s: \"%s\" is not a valid int value.", key, value); goto l_end; } - if (fnav_stat_type > SXE2_FNAV_STAT_ENA_ALL || - fnav_stat_type == SXE2_FNAV_STAT_ENA_NONE) { + if (stat_type > SXE2_FNAV_STAT_ENA_ALL || + stat_type == SXE2_FNAV_STAT_ENA_NONE) { PMD_LOG_ERR(INIT, "%s: \"%s\" out of range [1-3].", key, value); goto l_end; } - *num = (uint8_t)fnav_stat_type; + *num = (uint8_t)stat_type; ret = 0; l_end: return ret; @@ -1187,13 +1188,20 @@ static int32_t sxe2_args_parse(struct rte_eth_dev *dev, struct sxe2_dev_kvargs_i if (kvargs == NULL) goto l_end; ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_FNAV_STAT_TYPE, - &sxe2_parse_fnav_stat_type, + &sxe2_parse_stat_type, &adapter->devargs.fnav_stat_type); if (ret) { PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse fnav stat type, ret:%d", ret); goto l_end; } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_ACL_STAT_TYPE, + &sxe2_parse_stat_type, &adapter->devargs.acl_stat_type); + if (ret) { + PMD_DEV_LOG_ERR(adapter, INIT, "Failed to parse acl stat type, ret:%d", ret); + goto l_end; + } + ret = sxe2_kvargs_process(kvargs, SXE2_DEVARG_NO_SCHED_MODE, &sxe2_parse_bool, &adapter->devargs.no_sched_mode); @@ -2366,6 +2374,7 @@ RTE_PMD_REGISTER_PARAM_STRING(net_sxe2, "flow-duplicate-pattern=<0|1|2> " "function-flow-direct=<0|1> " "fnav-stat-type=<1|2|3> " + "acl-stat-type=<1|2|3> " "no-sched-mode=<0|1> " "sched-layer-mode=<0-3> " "rx-low-latency=<0|1>"); diff --git a/drivers/net/sxe2/sxe2_ethdev.h b/drivers/net/sxe2/sxe2_ethdev.h index e818578319..e9f78fe57f 100644 --- a/drivers/net/sxe2/sxe2_ethdev.h +++ b/drivers/net/sxe2/sxe2_ethdev.h @@ -135,6 +135,7 @@ struct sxe2_devargs { uint8_t flow_dup_pattern_mode; uint8_t func_flow_direct_en; uint8_t fnav_stat_type; + uint8_t acl_stat_type; uint8_t no_sched_mode; uint8_t sched_layer_mode; uint8_t rx_low_latency; diff --git a/drivers/net/sxe2/sxe2_flow.c b/drivers/net/sxe2/sxe2_flow.c index cd39385340..52e332cb10 100644 --- a/drivers/net/sxe2/sxe2_flow.c +++ b/drivers/net/sxe2/sxe2_flow.c @@ -1204,13 +1204,24 @@ static int32_t sxe2_flow_flush(struct rte_eth_dev *dev, struct rte_flow_error *e int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow *flow) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; uint32_t stat_index; uint32_t user_id; uint32_t driver_id; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; + uint32_t count_type; + + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.fnav_hw_res.count_type; + } else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + count_type = adapter->flow_ctxt.acl_hw_res.count_type; + } else { + ret = -ENOTSUP; + goto l_end; + } if (sxe2_test_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types)) { user_id = flow->action.count.user_id; @@ -1233,7 +1244,10 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow goto l_end; } - ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + ret = sxe2_drv_flow_fnav_get_stat_id(adapter, &stat_index); + else if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + ret = sxe2_drv_flow_acl_get_stat_id(adapter, &stat_index); if (ret) { PMD_LOG_ERR(DRV, "Failed to alloc fw count id."); rte_free(mgr); @@ -1244,7 +1258,7 @@ int32_t sxe2_flow_get_filter_cid(struct sxe2_adapter *adapter, struct sxe2_flow mgr->user_id = user_id; mgr->driver_id = driver_id; mgr->stat_index = stat_index; - mgr->count_type = adapter->flow_ctxt.hw_res.count_type; + mgr->count_type = count_type; } flow->action.count.stat_index = mgr->stat_index; flow->action.count.stat_ctrl = mgr->count_type; @@ -1260,13 +1274,26 @@ int32_t sxe2_flow_free_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *mgr = *mgr_ptr; uint32_t user_id = flow->action.count.user_id; - if (user_id == 0) { - TAILQ_REMOVE(cid_mgr_list, mgr, next); - ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + + if (user_id == 0 && mgr) { + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); + } else { + PMD_LOG_ERR(DRV, + "Failed to free flow count, unknown engine type: %d.", + flow->engine_type); + ret = -ENOTSUP; + return ret; + } if (ret) { rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_ACTION, NULL, @@ -1287,13 +1314,19 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, struct rte_flow_error *error) { int32_t ret = 0; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; struct sxe2_flow_cid_mgr *temp = NULL; struct sxe2_flow_cid_mgr *mgr = NULL; uint32_t user_id = flow->action.count.user_id; uint32_t driver_id = flow->action.count.driver_id; + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; + else + goto l_end; + TAILQ_FOREACH(temp, cid_mgr_list, next) { if (temp->user_id == user_id && temp->driver_id == driver_id) { @@ -1310,7 +1343,15 @@ int32_t sxe2_flow_query_mgr(struct sxe2_adapter *adapter, ret = -EINVAL; goto l_end; } - ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + + if (flow->engine_type == SXE2_FLOW_ENGINE_ACL) { + ret = sxe2_drv_flow_acl_query_stat(adapter, mgr); + } else if (flow->engine_type == SXE2_FLOW_ENGINE_FNAV) { + ret = sxe2_drv_flow_fnav_query_stat(adapter, mgr); + } else { + PMD_LOG_ERR(DRV, "query flow engine neither FNAV nor ACL"); + ret = -ENOTSUP; + } if (ret) { rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, NULL, @@ -1461,12 +1502,18 @@ int32_t sxe2_flow_init(struct rte_eth_dev *dev) struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); int32_t ret = 0; TAILQ_INIT(&adapter->flow_ctxt.rte_flow_list); - TAILQ_INIT(&adapter->flow_ctxt.hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list); + TAILQ_INIT(&adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list); if (adapter->devargs.fnav_stat_type) - adapter->flow_ctxt.hw_res.count_type = + adapter->flow_ctxt.fnav_hw_res.count_type = adapter->devargs.fnav_stat_type; else - adapter->flow_ctxt.hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + adapter->flow_ctxt.fnav_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; + + if (adapter->devargs.acl_stat_type) + adapter->flow_ctxt.acl_hw_res.count_type = adapter->devargs.acl_stat_type; + else + adapter->flow_ctxt.acl_hw_res.count_type = SXE2_FNAV_STAT_ENA_ALL; adapter->flow_ctxt.fnav_inited = 1; rte_spinlock_init(&adapter->flow_ctxt.flow_list_lock); @@ -1485,13 +1532,13 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) struct rte_flow_error error; struct sxe2_flow_cid_mgr *mgr = NULL; struct sxe2_flow_cid_mgr *temp = NULL; - struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = - &adapter->flow_ctxt.hw_res.flow_cid_mgr_list; + struct sxe2_flow_cid_mgr_list_t *cid_mgr_list = NULL; ret = sxe2_flow_flush(dev, &error); if (ret) PMD_LOG_ERR(DRV, "Failed to flush flow, ret: %d.", ret); + cid_mgr_list = &adapter->flow_ctxt.fnav_hw_res.flow_cid_mgr_list; TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { TAILQ_REMOVE(cid_mgr_list, mgr, next); ret = sxe2_drv_flow_fnav_free_stat(adapter, mgr->stat_index); @@ -1500,5 +1547,14 @@ int32_t sxe2_flow_uninit(struct rte_eth_dev *dev) "Failed to free fnav stat id, ret: %d.", ret); rte_free(mgr); } + + cid_mgr_list = &adapter->flow_ctxt.acl_hw_res.flow_cid_mgr_list; + TAILQ_FOREACH_SAFE(mgr, cid_mgr_list, next, temp) { + TAILQ_REMOVE(cid_mgr_list, mgr, next); + ret = sxe2_drv_flow_acl_free_stat(adapter, mgr->stat_index); + if (ret) + PMD_LOG_ERR(DRV, "Failed to free acl stat id, ret: %d.", ret); + rte_free(mgr); + } return ret; } diff --git a/drivers/net/sxe2/sxe2_flow_define.h b/drivers/net/sxe2/sxe2_flow_define.h index 8a5d871978..d04499f5cb 100644 --- a/drivers/net/sxe2/sxe2_flow_define.h +++ b/drivers/net/sxe2/sxe2_flow_define.h @@ -100,7 +100,7 @@ TAILQ_HEAD(rte_flow_list_t, rte_flow); struct sxe2_flow_cid_mgr { TAILQ_ENTRY(sxe2_flow_cid_mgr) next; - uint16_t stat_index; + uint32_t stat_index; uint32_t user_id; uint32_t driver_id; uint32_t count_type; @@ -118,7 +118,8 @@ struct sxe2_flow_count_resource { struct sxe2_flow_context { struct rte_flow_list_t rte_flow_list; rte_spinlock_t flow_list_lock; - struct sxe2_flow_count_resource hw_res; + struct sxe2_flow_count_resource fnav_hw_res; + struct sxe2_flow_count_resource acl_hw_res; uint16_t tunnel_port_list[SXE2_FLOW_UDP_TUNNEL_MAX]; uint32_t fnav_inited; }; diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index a9559e2d7e..03ada4e8a6 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -953,7 +953,8 @@ static int32_t sxe2_flow_check_actions(struct rte_eth_dev *dev __rte_unused, str } } - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { if (vsi_num) { flow->action.q_region.q_index = 0; flow->action.q_region.region = 7; @@ -980,6 +981,7 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, uint8_t action_num[SXE2_FLOW_ACTION_MAX] = {0}; enum sxe2_flow_engine_type engine_type = flow->engine_type; struct sxe2_adapter *adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(dev); + struct sxe2_flow_count_resource *hw_res = NULL; sxe2_flow_action_pre(flow); @@ -988,7 +990,8 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, case RTE_FLOW_ACTION_TYPE_VOID: break; case RTE_FLOW_ACTION_TYPE_PASSTHRU: - if (engine_type == SXE2_FLOW_ENGINE_FNAV) { + if (engine_type == SXE2_FLOW_ENGINE_FNAV || + engine_type == SXE2_FLOW_ENGINE_ACL) { sxe2_set_bit(SXE2_FLOW_ACTION_PASSTHRU, flow->action.act_types); action_num[SXE2_FLOW_ACTION_PASSTHRU]++; } else { @@ -1035,14 +1038,9 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, break; case RTE_FLOW_ACTION_TYPE_COUNT: if (engine_type == SXE2_FLOW_ENGINE_FNAV) { - sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); - act_count = action->conf; - flow->action.count.user_id = act_count->id; - flow->action.count.driver_id = 0; - if (flow->action.count.user_id == 0) - flow->action.count.driver_id = - ++adapter->flow_ctxt.hw_res.global_index; - action_num[SXE2_FLOW_ACTION_COUNT]++; + hw_res = &adapter->flow_ctxt.fnav_hw_res; + } else if (engine_type == SXE2_FLOW_ENGINE_ACL) { + hw_res = &adapter->flow_ctxt.acl_hw_res; } else { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, action, @@ -1052,6 +1050,16 @@ int32_t sxe2_flow_parse_action(struct rte_eth_dev *dev, ret = -EINVAL; goto l_end; } + sxe2_set_bit(SXE2_FLOW_ACTION_COUNT, flow->action.act_types); + act_count = action->conf; + flow->action.count.user_id = + (act_count == NULL) ? 0 : act_count->id; + flow->action.count.driver_id = 0; + if (flow->action.count.user_id == 0) { + flow->action.count.driver_id = + ++hw_res->global_index; + } + action_num[SXE2_FLOW_ACTION_COUNT]++; break; case RTE_FLOW_ACTION_TYPE_RSS: if (engine_type == SXE2_FLOW_ENGINE_RSS) { diff --git a/drivers/net/sxe2/sxe2_queue.c b/drivers/net/sxe2/sxe2_queue.c index afb2681b72..3aaa14c685 100644 --- a/drivers/net/sxe2/sxe2_queue.c +++ b/drivers/net/sxe2/sxe2_queue.c @@ -39,6 +39,8 @@ int32_t sxe2_queues_init(struct rte_eth_dev *dev) rxq->rx_buf_len = RTE_MIN(rxq->rx_buf_len, SXE2_RX_MAX_DATA_BUF_SIZE); if (frame_size > rxq->rx_buf_len) dev->data->scattered_rx = 1; + if (adapter->flow_ctxt.fnav_inited) + rxq->fnav_enable = true; } adapter->ptp_ctxt.mbuf_rx_ts_offset = -1; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 27/47] net/sxe2: refactor primary process MP message handling 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (27 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 26/47] net/sxe2: add ACL engine event statistics support liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 28/47] net/sxe2: refactor Tx queue reset operations liujie5 ` (19 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Extract the multi-process work logic into the sxe2_mp_do_primary_work helper and operate on a copy of the request in the primary handler so the original message is not modified. Simplify the reply construction and return -ENOENT instead of -EINVAL when no response is received from the primary process. Fixes: 5db446ba97b0 ("net/sxe2: support statistics and multi-process") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_mp.c | 59 ++++++++++++++++++++++---------------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/drivers/net/sxe2/sxe2_mp.c b/drivers/net/sxe2/sxe2_mp.c index a4a5c76495..93a11150a9 100644 --- a/drivers/net/sxe2/sxe2_mp.c +++ b/drivers/net/sxe2/sxe2_mp.c @@ -29,16 +29,11 @@ static int32_t sxe2_mp_secondary_handle(const struct rte_mp_msg *mp_msg, const void *peer); static int32_t -sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +sxe2_mp_do_primary_work(struct sxe2_mp_param *param) { - struct rte_mp_msg reply; - const struct sxe2_mp_param *param = - (const struct sxe2_mp_param *)mp_msg->param; - struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; struct rte_eth_dev *dev; - int32_t ret = 0; struct sxe2_mp_shared_data *mz_data; - int32_t send_reply = 0; + int32_t ret = 0; int32_t cnt = 0; if (!rte_eth_dev_is_valid_port(param->port_id)) { @@ -49,24 +44,21 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) } dev = &rte_eth_devices[param->port_id]; - sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { - PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", SXE2_MP_MZ_NAME); - ret = -ENOENT; - goto out; + sxe2_mp_mz = rte_memzone_lookup(SXE2_MP_MZ_NAME); + if (sxe2_mp_mz == NULL) { + PMD_LOG_ERR(DRV, "Failed to lookup memzone %s", + SXE2_MP_MZ_NAME); + ret = -ENOENT; + goto out; + } } mz_data = (struct sxe2_mp_shared_data *)sxe2_mp_mz->addr; - send_reply = 1; - - memset(&reply, 0, sizeof(reply)); - (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); - reply.len_param = sizeof(*reply_param); - switch (param->type) { case SXE2_MP_REQ_GET_STATS: - ret = sxe2_stats_info_get(dev, - &mz_data->payload.stats_blk.stats, + ret = sxe2_stats_info_get(dev, &mz_data->payload.stats_blk.stats, &mz_data->payload.stats_blk.qstats); break; case SXE2_MP_REQ_GET_XSTATS: @@ -88,15 +80,32 @@ sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) default: PMD_LOG_ERR(DRV, "primary process: unrecognized msg type: %d", param->type); - send_reply = false; ret = -EINVAL; - goto out; + break; } + out: - if (!send_reply) - return ret; + param->result = ret; + return ret; +} - reply_param->result = ret; +static int32_t +sxe2_mp_primary_handle(const struct rte_mp_msg *mp_msg, const void *peer) +{ + struct rte_mp_msg reply; + struct sxe2_mp_param *reply_param = (struct sxe2_mp_param *)reply.param; + const struct sxe2_mp_param *param = + (const struct sxe2_mp_param *)mp_msg->param; + struct sxe2_mp_param param_copy; + + memset(&reply, 0, sizeof(reply)); + (void)strlcpy(reply.name, SXE2_MP_NAME, sizeof(reply.name)); + reply.len_param = sizeof(*reply_param); + + param_copy = *param; + (void)sxe2_mp_do_primary_work(¶m_copy); + + reply_param->result = param_copy.result; reply_param->type = param->type; reply_param->port_id = param->port_id; @@ -275,7 +284,7 @@ int32_t sxe2_mp_request_simple(struct rte_eth_dev *dev, if (reply.nb_received == 0) { PMD_LOG_ERR(DRV, "No response received from primary for type=%d, port %u", type, dev->data->port_id); - ret = -EINVAL; + ret = -ENOENT; goto out; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 28/47] net/sxe2: refactor Tx queue reset operations 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (28 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 27/47] net/sxe2: refactor primary process MP message handling liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 29/47] net/sxe2: unify vectorized Tx buffer handling liujie5 ` (18 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Extract the descriptor ring reset loop into a sxe2_tx_queue_desc_ring_reset helper and reuse it from both the scalar and vectorized queue reset paths. Add a sxe2_tx_queue_reset_vec entry point for vectorized queues, export sxe2_tx_buffer_ring_free for reuse outside the module (clearing the buffer ring pointer after freeing it), and add sxe2_tx_vec_ops_get to build the vectorized Tx queue operations table used by the vector path setup. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_tx.c | 42 +++++++++++++++++++++++--------- drivers/net/sxe2/sxe2_tx.h | 4 +++ drivers/net/sxe2/sxe2_txrx_vec.c | 17 ++++++++++--- 3 files changed, 49 insertions(+), 14 deletions(-) diff --git a/drivers/net/sxe2/sxe2_tx.c b/drivers/net/sxe2/sxe2_tx.c index f49238ceef..94a6e9afc7 100644 --- a/drivers/net/sxe2/sxe2_tx.c +++ b/drivers/net/sxe2/sxe2_tx.c @@ -19,6 +19,17 @@ static void *sxe2_tx_doorbell_addr_get(struct sxe2_adapter *adapter, uint16_t qu queue_id); } +static void sxe2_tx_queue_desc_ring_reset(struct sxe2_tx_queue *txq) +{ + uint16_t i; + static const union sxe2_tx_data_desc zeroed_desc = {{0}}; + + for (i = 0; i < txq->ring_depth; i++) { + txq->desc_ring[i] = zeroed_desc; + txq->desc_ring[i].wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); + } +} + static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue *txq) { txq->tdt_reg_addr = sxe2_tx_doorbell_addr_get(adapter, txq->queue_id); @@ -28,20 +39,12 @@ static void sxe2_tx_tail_init(struct sxe2_adapter *adapter, struct sxe2_tx_queue void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) { uint16_t prev, i; - volatile union sxe2_tx_data_desc *txd; - static const union sxe2_tx_data_desc zeroed_desc = {{0}}; struct sxe2_tx_buffer *tx_buffer = txq->buffer_ring; - for (i = 0; i < txq->ring_depth; i++) - txq->desc_ring[i] = zeroed_desc; + sxe2_tx_queue_desc_ring_reset(txq); prev = txq->ring_depth - 1; for (i = 0; i < txq->ring_depth; i++) { - txd = &txq->desc_ring[i]; - if (txd == NULL) - continue; - - txd->wb.dd = rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE); tx_buffer[i].mbuf = NULL; tx_buffer[i].last_id = i; tx_buffer[prev].next_id = i; @@ -56,6 +59,21 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq) txq->next_rs = txq->rs_thresh - 1; } +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq) +{ + sxe2_tx_queue_desc_ring_reset(txq); + + memset(txq->buffer_ring, 0, + sizeof(struct sxe2_tx_buffer) * txq->ring_depth); + + txq->desc_used_num = 0; + txq->desc_free_num = txq->ring_depth - 1; + txq->next_use = 0; + txq->next_clean = txq->ring_depth - 1; + txq->next_dd = txq->rs_thresh - 1; + txq->next_rs = txq->rs_thresh - 1; +} + void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) { uint32_t i; @@ -70,10 +88,12 @@ void __rte_cold sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq) } } -static void sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq) { - if (txq != NULL && txq->buffer_ring != NULL) + if (txq != NULL && txq->buffer_ring != NULL) { rte_free(txq->buffer_ring); + txq->buffer_ring = NULL; + } } const struct sxe2_txq_ops sxe2_default_txq_ops = { diff --git a/drivers/net/sxe2/sxe2_tx.h b/drivers/net/sxe2/sxe2_tx.h index f4823126b3..bc5ff1c2bc 100644 --- a/drivers/net/sxe2/sxe2_tx.h +++ b/drivers/net/sxe2/sxe2_tx.h @@ -9,6 +9,10 @@ void __rte_cold sxe2_tx_queue_reset(struct sxe2_tx_queue *txq); +void __rte_cold sxe2_tx_queue_reset_vec(struct sxe2_tx_queue *txq); + +void __rte_cold sxe2_tx_buffer_ring_free(struct sxe2_tx_queue *txq); + int32_t __rte_cold sxe2_tx_queue_start(struct rte_eth_dev *dev, uint16_t queue_id); void sxe2_tx_queue_mbufs_release(struct sxe2_tx_queue *txq); diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index cf004f5eb2..1442d5d119 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -8,6 +8,14 @@ #include "sxe2_ethdev.h" #include "sxe2_common_log.h" +static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq); + +static const struct sxe2_txq_ops sxe2_tx_vec_ops = { + .queue_reset = sxe2_tx_queue_reset_vec, + .mbufs_release = sxe2_tx_queue_mbufs_release_vec, + .buffer_ring_free = sxe2_tx_buffer_ring_free, +}; + int32_t __rte_cold sxe2_rx_vec_support_check(struct rte_eth_dev *dev, uint32_t *vec_flags) { struct sxe2_rx_queue *rxq; @@ -230,10 +238,13 @@ int32_t __rte_cold sxe2_tx_queues_vec_prepare(struct rte_eth_dev *dev) for (i = 0; i < dev->data->nb_tx_queues; ++i) { txq = dev->data->tx_queues[i]; if (txq == NULL) { - PMD_LOG_INFO(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); - continue; + PMD_LOG_ERR(TX, "Failed to prepare tx queue, txq[%d] is NULL", i); + ret = -EINVAL; + goto l_end; } - txq->ops.mbufs_release = sxe2_tx_queue_mbufs_release_vec; + txq->ops = sxe2_tx_vec_ops; + txq->ops.queue_reset(txq); } +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 29/47] net/sxe2: unify vectorized Tx buffer handling 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (29 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 28/47] net/sxe2: refactor Tx queue reset operations liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:43 ` [PATCH v7 30/47] net/sxe2: optimize NEON Tx descriptor fill liujie5 ` (17 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Add a union of the scalar and vectorized buffer ring pointers to the Tx queue structure so the vectorized path can use sxe2_tx_buffer_vec directly. Rename the mbuf fill helper to sxe2_tx_pkts_mbuf_fill_vec, switch the vectorized Tx burst and mbuf release paths to the buffer_ring_vec member, and drop the AVX512-specific fill handling and conditional branching. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_queue.h | 5 +- drivers/net/sxe2/sxe2_txrx_vec.c | 57 ++-------- drivers/net/sxe2/sxe2_txrx_vec_avx2.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_avx512.c | 133 +----------------------- drivers/net/sxe2/sxe2_txrx_vec_common.h | 9 +- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 10 +- drivers/net/sxe2/sxe2_txrx_vec_sse.c | 10 +- 7 files changed, 40 insertions(+), 194 deletions(-) diff --git a/drivers/net/sxe2/sxe2_queue.h b/drivers/net/sxe2/sxe2_queue.h index 10bdaf5b8d..e53a1ce852 100644 --- a/drivers/net/sxe2/sxe2_queue.h +++ b/drivers/net/sxe2/sxe2_queue.h @@ -62,7 +62,10 @@ struct sxe2_txq_ops { }; struct sxe2_tx_queue { volatile union sxe2_tx_data_desc *desc_ring; - struct sxe2_tx_buffer *buffer_ring; + union { + struct sxe2_tx_buffer *buffer_ring; + struct sxe2_tx_buffer_vec *buffer_ring_vec; + }; volatile uint32_t *tdt_reg_addr; uint64_t offloads; diff --git a/drivers/net/sxe2/sxe2_txrx_vec.c b/drivers/net/sxe2/sxe2_txrx_vec.c index 1442d5d119..c9363444df 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec.c +++ b/drivers/net/sxe2/sxe2_txrx_vec.c @@ -165,66 +165,31 @@ int32_t __rte_cold sxe2_tx_vec_support_check(struct rte_eth_dev *dev, uint32_t * static void sxe2_tx_queue_mbufs_release_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer_vec; uint16_t i; - if (unlikely(txq == NULL || txq->buffer_ring == NULL)) { + if (unlikely(txq == NULL || txq->buffer_ring_vec == NULL)) { PMD_LOG_ERR(TX, "Tx release mbufs vec, invalid params."); return; } - i = txq->next_dd - (txq->rs_thresh - 1); -#ifdef CC_AVX512_SUPPORT - struct rte_eth_dev *dev; - struct sxe2_tx_buffer_vec *buffer_vec; - dev = &rte_eth_devices[txq->port_id]; - - if (dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512 || - dev->tx_pkt_burst == sxe2_tx_pkts_vec_avx512_simple) { - buffer_vec = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + i = txq->next_dd - (txq->rs_thresh - 1); + buffer_vec = txq->buffer_ring_vec; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer_vec[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer_vec[i].mbuf); - buffer_vec[i].mbuf = NULL; - } - } - i = 0; - } - for ( ; i < txq->next_use; ++i) { + if (txq->next_use < i) { + for ( ; i < txq->ring_depth; ++i) { if (buffer_vec[i].mbuf != NULL) { rte_pktmbuf_free_seg(buffer_vec[i].mbuf); buffer_vec[i].mbuf = NULL; } } - } else { -#endif - buffer = txq->buffer_ring; - buffer = txq->buffer_ring; - if (txq->next_use < i) { - for ( ; i < txq->ring_depth; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } - i = 0; - } - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; - } - } -#ifdef CC_AVX512_SUPPORT + i = 0; } -#endif - for (; i < txq->next_use; ++i) { - if (buffer[i].mbuf != NULL) { - rte_pktmbuf_free_seg(buffer[i].mbuf); - buffer[i].mbuf = NULL; + for ( ; i < txq->next_use; ++i) { + if (buffer_vec[i].mbuf != NULL) { + rte_pktmbuf_free_seg(buffer_vec[i].mbuf); + buffer_vec[i].mbuf = NULL; } } } diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c index 0618e6d988..da96ca3064 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx2.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx2.c @@ -115,7 +115,7 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -134,14 +134,14 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -157,10 +157,10 @@ sxe2_tx_pkts_vec_avx2_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx2(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); diff --git a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c index a830c7a33b..6c8415ee5a 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_avx512.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_avx512.c @@ -1,8 +1,6 @@ /* SPDX-License-Identifier: BSD-3-Clause * Copyright (C), 2025, Wuxi Stars Micro System Technologies Co., Ltd. */ - -#ifndef SXE2_TEST #include <rte_vect.h> #include "sxe2_ethdev.h" @@ -12,114 +10,6 @@ #include "sxe2_txrx_vec_common.h" #include "sxe2_vsi.h" -static __rte_always_inline int32_t sxe2_tx_bufs_free_vec_avx512(struct sxe2_tx_queue *txq) -{ - struct sxe2_tx_buffer_vec *buffer; - struct rte_mbuf *mbuf; - struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; - struct rte_mempool *mp; - struct rte_mempool_cache *cache; - void **cache_objs; - uint32_t copied; - uint32_t i; - int32_t ret; - uint16_t rs_thresh; - uint16_t free_num; - - if (rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_DESC_DONE) != - (txq->desc_ring[txq->next_dd].wb.dd & - rte_cpu_to_le_64(SXE2_TX_DESC_DTYPE_MASK))) { - ret = 0; - goto l_end; - } - - rs_thresh = txq->rs_thresh; - - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += txq->next_dd - (rs_thresh - 1); - - if ((txq->offloads & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) && - (rs_thresh & 31) == 0) { - mp = buffer[0].mbuf->pool; - cache = rte_mempool_default_cache(mp, rte_lcore_id()); - - if (cache == NULL || cache->len) - goto normal; - - if (rs_thresh > RTE_MEMPOOL_CACHE_MAX_SIZE) { - (void)rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh); - goto done; - } - cache_objs = &cache->objs[cache->len]; - - copied = 0; - while (copied < rs_thresh) { - const __m512i objs0 = _mm512_loadu_si512(&buffer[copied]); - const __m512i objs1 = _mm512_loadu_si512(&buffer[copied + 8]); - const __m512i objs2 = _mm512_loadu_si512(&buffer[copied + 16]); - const __m512i objs3 = _mm512_loadu_si512(&buffer[copied + 24]); - - _mm512_storeu_si512(&cache_objs[copied], objs0); - _mm512_storeu_si512(&cache_objs[copied + 8], objs1); - _mm512_storeu_si512(&cache_objs[copied + 16], objs2); - _mm512_storeu_si512(&cache_objs[copied + 24], objs3); - copied += 32; - } - cache->len += rs_thresh; - - if (cache->len >= cache->flushthresh) { - (void)rte_mempool_ops_enqueue_bulk(mp, - &cache->objs[cache->size], cache->len - cache->size); - cache->len = cache->size; - } - goto done; - } - -normal: - mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); - - if (likely(mbuf)) { - mbuf_free_arr[0] = mbuf; - free_num = 1; - - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - - if (likely(mbuf)) { - if (likely(mbuf->pool == mbuf_free_arr[0]->pool)) { - mbuf_free_arr[free_num] = mbuf; - free_num++; - } else { - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - - mbuf_free_arr[0] = mbuf; - free_num = 1; - } - } - } - - rte_mempool_put_bulk(mbuf_free_arr[0]->pool, - (void *)mbuf_free_arr, free_num); - } else { - for (i = 1; i < rs_thresh; ++i) { - mbuf = rte_pktmbuf_prefree_seg(buffer[i].mbuf); - if (mbuf != NULL) - rte_mempool_put(mbuf->pool, mbuf); - } - } - -done: - txq->desc_free_num += txq->rs_thresh; - txq->next_dd += txq->rs_thresh; - if (txq->next_dd >= txq->ring_depth) - txq->next_dd = txq->rs_thresh - 1; - ret = rs_thresh; - -l_end: - return ret; -} - static __rte_always_inline void sxe2_tx_desc_fill_one_avx512(volatile union sxe2_tx_data_desc *desc, struct rte_mbuf *pkt, uint64_t desc_cmd, bool with_offloads) @@ -207,16 +97,6 @@ void sxe2_tx_desc_fill_avx512(volatile union sxe2_tx_data_desc *desc, struct rte } } -static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill_avx512(struct sxe2_tx_buffer_vec *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) -{ - uint16_t i; - - for (i = 0; i < nb_pkts; ++i) - buffer[i].mbuf = tx_pkts[i]; -} - static __rte_always_inline uint16_t sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -228,7 +108,7 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk uint16_t tx_num; if (txq->desc_free_num < txq->free_thresh) - (void)sxe2_tx_bufs_free_vec_avx512(txq); + (void)sxe2_tx_bufs_free_vec(txq); nb_pkts = RTE_MIN(txq->desc_free_num, nb_pkts); if (unlikely(nb_pkts == 0)) { @@ -241,15 +121,14 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; - buffer += next_use; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, res_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -265,10 +144,10 @@ sxe2_tx_pkts_vec_avx512_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pk next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = txq->desc_ring; - buffer = (struct sxe2_tx_buffer_vec *)txq->buffer_ring; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill_avx512(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); sxe2_tx_desc_fill_avx512(desc, tx_pkts, tx_num, SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); @@ -863,5 +742,3 @@ uint16_t sxe2_rx_pkts_scattered_vec_avx512_offload(void *rx_queue, return sxe2_rx_pkts_scattered_common_vec_avx512(rx_queue, rx_pkts, nb_pkts, true); } - -#endif diff --git a/drivers/net/sxe2/sxe2_txrx_vec_common.h b/drivers/net/sxe2/sxe2_txrx_vec_common.h index 9ac99cf0fa..ede4c236b1 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_common.h +++ b/drivers/net/sxe2/sxe2_txrx_vec_common.h @@ -25,10 +25,11 @@ #define SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC 64 static __rte_always_inline void -sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, - struct rte_mbuf **tx_pkts, uint16_t nb_pkts) +sxe2_tx_pkts_mbuf_fill_vec(struct sxe2_tx_buffer_vec *buffer, + struct rte_mbuf **tx_pkts, uint16_t nb_pkts) { uint16_t i; + for (i = 0; i < nb_pkts; ++i) buffer[i].mbuf = tx_pkts[i]; } @@ -36,7 +37,7 @@ sxe2_tx_pkts_mbuf_fill(struct sxe2_tx_buffer *buffer, static __rte_always_inline int32_t sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) { - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; struct rte_mbuf *mbuf; struct rte_mbuf *mbuf_free_arr[SXE2_TX_FREE_BUFFER_SIZE_MAX_VEC]; int32_t ret; @@ -50,7 +51,7 @@ sxe2_tx_bufs_free_vec(struct sxe2_tx_queue *txq) goto l_end; } rs_thresh = txq->rs_thresh; - buffer = &txq->buffer_ring[txq->next_dd - (rs_thresh - 1)]; + buffer = &txq->buffer_ring_vec[txq->next_dd - (rs_thresh - 1)]; mbuf = rte_pktmbuf_prefree_seg(buffer[0].mbuf); if (likely(mbuf)) { mbuf_free_arr[0] = mbuf; diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 4e5cb87cd5..b51cc55368 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -39,7 +39,7 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -59,14 +59,14 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, @@ -82,10 +82,10 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, diff --git a/drivers/net/sxe2/sxe2_txrx_vec_sse.c b/drivers/net/sxe2/sxe2_txrx_vec_sse.c index c3e8a2983b..181bb40041 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_sse.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_sse.c @@ -40,7 +40,7 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, uint16_t nb_pkts, bool with_offloads) { volatile union sxe2_tx_data_desc *desc; - struct sxe2_tx_buffer *buffer; + struct sxe2_tx_buffer_vec *buffer; uint16_t next_use; uint16_t res_num; uint16_t tx_num; @@ -57,11 +57,11 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, tx_num = nb_pkts; next_use = txq->next_use; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; txq->desc_free_num -= nb_pkts; res_num = txq->ring_depth - txq->next_use; if (tx_num >= res_num) { - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, res_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, @@ -74,9 +74,9 @@ sxe2_tx_pkts_vec_sse_batch(struct sxe2_tx_queue *txq, next_use = 0; txq->next_rs = txq->rs_thresh - 1; desc = &txq->desc_ring[next_use]; - buffer = &txq->buffer_ring[next_use]; + buffer = &txq->buffer_ring_vec[next_use]; } - sxe2_tx_pkts_mbuf_fill(buffer, tx_pkts, tx_num); + sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { sxe2_tx_desc_fill_one_sse(desc, *tx_pkts, SXE2_TX_DATA_DESC_CMD_EOP, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 30/47] net/sxe2: optimize NEON Tx descriptor fill 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (30 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 29/47] net/sxe2: unify vectorized Tx buffer handling liujie5 @ 2026-08-31 2:43 ` liujie5 2026-08-31 2:44 ` [PATCH v7 31/47] net/sxe2: fix NEON Rx ptype mapping and memory ordering liujie5 ` (16 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:43 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Add sxe2_tx_desc_fill_4_neon_simple() to write four data descriptors with a single vst1q_u64_x4 store, and use it in sxe2_tx_pkts_vec_neon_batch() for the non-offload path to reduce the number of per-packet descriptor stores. Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 77 ++++++++++++++++++++++++--- 1 file changed, 70 insertions(+), 7 deletions(-) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index b51cc55368..6b4c70c7ac 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -34,6 +34,52 @@ sxe2_tx_desc_fill_one_neon(volatile union sxe2_tx_data_desc *desc, vst1q_u64(RTE_CAST_PTR(uint64_t *, desc), data_desc); } +static __rte_always_inline void +sxe2_tx_desc_fill_4_neon_simple(volatile union sxe2_tx_data_desc *desc, + struct rte_mbuf **pkts) +{ + uint64x2_t d0, d1, d2, d3; + uint64x2x4_t v; + const uint64_t cmd_base = ((uint64_t)SXE2_TX_DESC_DTYPE_DATA) | + ((uint64_t)SXE2_TX_DATA_DESC_CMD_EOP) << + SXE2_TX_DATA_DESC_CMD_SHIFT; + + d0 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[0]), + cmd_base | + ((uint64_t)pkts[0]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[0]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d1 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[1]), + cmd_base | + ((uint64_t)pkts[1]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[1]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d2 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[2]), + cmd_base | + ((uint64_t)pkts[2]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[2]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + d3 = (uint64x2_t){ + rte_pktmbuf_iova(pkts[3]), + cmd_base | + ((uint64_t)pkts[3]->data_len) << SXE2_TX_DATA_DESC_BUF_SZ_SHIFT | + ((uint64_t)SXE2_TX_DATA_DESC_MACLEN_VAL(pkts[3]->l2_len)) + << SXE2_TX_DATA_DESC_OFFSET_SHIFT + }; + + v.val[0] = d0; + v.val[1] = d1; + v.val[2] = d2; + v.val[3] = d3; + vst1q_u64_x4(RTE_CAST_PTR(uint64_t *, desc), v); +} + static __rte_always_inline uint16_t sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts, uint16_t nb_pkts, bool with_offloads) @@ -67,10 +113,18 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts if (tx_num >= res_num) { sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, res_num); - - for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + } + } else { + for (i = 0; i + 3 < res_num - 1; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < res_num - 1; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } sxe2_tx_desc_fill_one_neon(desc, *tx_pkts++, @@ -87,9 +141,18 @@ sxe2_tx_pkts_vec_neon_batch(struct sxe2_tx_queue *txq, struct rte_mbuf **tx_pkts sxe2_tx_pkts_mbuf_fill_vec(buffer, tx_pkts, tx_num); - for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { - sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, - SXE2_TX_DATA_DESC_CMD_EOP, with_offloads); + if (with_offloads) { + for (i = 0; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, true); + } + } else { + for (i = 0; i + 3 < tx_num; i += 4, tx_pkts += 4, desc += 4) + sxe2_tx_desc_fill_4_neon_simple(desc, tx_pkts); + for (; i < tx_num; ++i, ++tx_pkts, ++desc) { + sxe2_tx_desc_fill_one_neon(desc, *tx_pkts, + SXE2_TX_DATA_DESC_CMD_EOP, false); + } } next_use += tx_num; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 31/47] net/sxe2: fix NEON Rx ptype mapping and memory ordering 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (31 preceding siblings ...) 2026-08-31 2:43 ` [PATCH v7 30/47] net/sxe2: optimize NEON Tx descriptor fill liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 32/47] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 ` (15 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Compute the descriptor lower/upper dwords (desc_lo/desc_hi) once per loop iteration and pass them to sxe2_rx_desc_ptype_fill_neon() and sxe2_rx_desc_offloads_para_fill_neon(). Map the packet_type lanes from desc_lo lanes 1/3/5/7, fixing the previous lane ordering that mapped pkt0/1/2/3 from lanes 5/1/7/3. Drop three of the four rte_atomic_thread_fence(acquire) barriers between the descriptor loads in sxe2_rx_pkts_common_vec_neon(); the single acquire fence after the descriptor set is loaded is sufficient for the Rx producer/consumer ordering. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_txrx_vec_neon.c | 132 +++++++++++++------------- 1 file changed, 68 insertions(+), 64 deletions(-) diff --git a/drivers/net/sxe2/sxe2_txrx_vec_neon.c b/drivers/net/sxe2/sxe2_txrx_vec_neon.c index 6b4c70c7ac..0b139b8269 100644 --- a/drivers/net/sxe2/sxe2_txrx_vec_neon.c +++ b/drivers/net/sxe2/sxe2_txrx_vec_neon.c @@ -213,22 +213,24 @@ uint16_t sxe2_tx_pkts_vec_neon(void *tx_queue, } static __rte_always_inline void -sxe2_rx_desc_ptype_fill_neon(uint16x8_t staterr, struct rte_mbuf **__rte_restrict rx_pkts) +sxe2_rx_desc_ptype_fill_neon(uint32x4_t desc_lo, + struct rte_mbuf **__rte_restrict rx_pkts, + const uint32_t *__rte_restrict ptype_tbl) { - uint16x8_t ptype_mask = { - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, - 0, 0x3FFULL, + const uint32x4_t ptype_mask = { + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, + SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16, }; uint16x8_t ptype_all; - ptype_all = vandq_u16(staterr, ptype_mask); + ptype_all = vreinterpretq_u16_u32(vandq_u32(desc_lo, ptype_mask)); - rx_pkts[3]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; - rx_pkts[2]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; - rx_pkts[1]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; - rx_pkts[0]->packet_type = sxe2_ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[0]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 1)]; + rx_pkts[1]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 3)]; + rx_pkts[2]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 5)]; + rx_pkts[3]->packet_type = ptype_tbl[vgetq_lane_u16(ptype_all, 7)]; } static __rte_always_inline uint32x4_t @@ -271,9 +273,10 @@ sxe2_rx_desc_fnav_flags_neon(uint64x2_t descs_arr[4]) static __rte_always_inline void sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, volatile union sxe2_rx_desc *desc, - uint64x2_t descs[4], struct rte_mbuf **rx_pkts) + uint64x2_t descs[4], uint32x4_t desc_lo, uint32x4_t desc_hi, + struct rte_mbuf **rx_pkts) { - uint32x4_t desc_lo, desc_hi, flags, tmp_flags; + uint32x4_t flags, tmp_flags; const uint64x2_t mbuf_init = {rxq->mbuf_init_value, 0}; uint64x2_t rearm0, rearm1, rearm2, rearm3; @@ -330,23 +333,6 @@ sxe2_rx_desc_offloads_para_fill_neon(struct sxe2_rx_queue *rxq, 0, 0, 0, 0, 0, 0, 0, 0 }; - { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint64x2_t f64, t64; - - flags = vzip2q_u32(d1, d0); - tmp_flags = vzip2q_u32(d3, d2); - f64 = vreinterpretq_u64_u32(flags); - t64 = vreinterpretq_u64_u32(tmp_flags); - desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(f64), - vget_low_u64(t64))); - desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(f64), - vget_high_u64(t64))); - } - desc_lo = vandq_u32(desc_lo, desc_msk); desc_hi = vandq_u32(desc_hi, rss_msk); @@ -505,25 +491,39 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt uint64x2_t descs[SXE2_RX_NUM_PER_LOOP_NEON]; uint8x16_t pkt_mb1, pkt_mb2, pkt_mb3, pkt_mb4; uint64x2_t mbp1, mbp2; + uint32x4_t desc_lo, desc_hi; uint16x8_t staterr; uint16x8_t tmp; uint16_t bit_num; descs[3] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 3)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[2] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 2)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[1] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc + 1)); - rte_atomic_thread_fence(rte_memory_order_acquire); descs[0] = vld1q_u64(RTE_CAST_PTR(uint64_t *, desc)); rte_atomic_thread_fence(rte_memory_order_acquire); - descs[3] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 3), descs[3], 0); descs[2] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 2), descs[2], 0); descs[1] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc + 1), descs[1], 0); descs[0] = vld1q_lane_u64(RTE_CAST_PTR(uint64_t *, desc), descs[0], 0); + { + uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); + uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); + uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); + uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); + + uint32x4_t q1_01 = vzip2q_u32(d0, d1); + uint32x4_t q1_23 = vzip2q_u32(d2, d3); + uint64x2_t q1_01_64 = vreinterpretq_u64_u32(q1_01); + uint64x2_t q1_23_64 = vreinterpretq_u64_u32(q1_23); + + desc_lo = vreinterpretq_u32_u64(vcombine_u64(vget_low_u64(q1_01_64), + vget_low_u64(q1_23_64))); + desc_hi = vreinterpretq_u32_u64(vcombine_u64(vget_high_u64(q1_01_64), + vget_high_u64(q1_23_64))); + } + mbp1 = vld1q_u64((uint64_t *)&buffer[i]); mbp2 = vld1q_u64((uint64_t *)&buffer[i + 2]); @@ -543,7 +543,8 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt pkt_mb1 = vqtbl1q_u8(vreinterpretq_u8_u64(descs[0]), rvp_shuf_mask); if (do_offload) { - sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, &rx_pkts[i]); + sxe2_rx_desc_offloads_para_fill_neon(rxq, desc, descs, desc_lo, + desc_hi, &rx_pkts[i]); } else { const uint64x2_t mbuf_init = { rxq->mbuf_init_value, @@ -578,55 +579,48 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt rte_prefetch_non_temporal(desc + SXE2_RX_NUM_PER_LOOP_NEON); { - uint32x4_t d0 = vreinterpretq_u32_u64(descs[0]); - uint32x4_t d1 = vreinterpretq_u32_u64(descs[1]); - uint32x4_t d2 = vreinterpretq_u32_u64(descs[2]); - uint32x4_t d3 = vreinterpretq_u32_u64(descs[3]); - uint32x4_t sterr_tmp1 = vzip2q_u32(d1, d0); - uint32x4_t sterr_tmp2 = vzip2q_u32(d3, d2); - uint32x4_t sterr_u32 = vzip1q_u32(sterr_tmp1, sterr_tmp2); - - staterr = vreinterpretq_u16_u32(sterr_u32); + uint16x8_t sterr_tmp1 = vzip2q_u16(vreinterpretq_u16_u64(descs[0]), + vreinterpretq_u16_u64(descs[2])); + uint16x8_t sterr_tmp2 = vzip2q_u16(vreinterpretq_u16_u64(descs[1]), + vreinterpretq_u16_u64(descs[3])); + staterr = vzip1q_u16(sterr_tmp1, sterr_tmp2); } - sxe2_rx_desc_ptype_fill_neon(staterr, &rx_pkts[i]); + sxe2_rx_desc_ptype_fill_neon(desc_lo, &rx_pkts[i], sxe2_ptype_tbl); if (umbcast_flags != NULL) { - uint32x4_t umbcast_mask = { - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - SXE2_RX_DESC_STATUS_UMBCAST_MASK, SXE2_RX_DESC_STATUS_UMBCAST_MASK, - }; - + const uint32x4_t umbcast_mask = + vdupq_n_u32(SXE2_RX_DESC_STATUS_UMBCAST_MASK); uint8x16_t umbcast_shuf_mask = { - 0x0B, 0x03, 0x0F, 0x07, + 3, 7, 11, 15, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }; uint8x16_t umbcast_bits = - vreinterpretq_u8_u32(vandq_u32(vreinterpretq_u32_u16(staterr), - umbcast_mask)); + vreinterpretq_u8_u32(vandq_u32(desc_lo, umbcast_mask)); umbcast_bits = vqtbl1q_u8(umbcast_bits, umbcast_shuf_mask); - vst1q_lane_u32((uint32_t *)umbcast_flags, - vreinterpretq_u32_u8(umbcast_bits), 0); + *(uint32_t *)umbcast_flags = + vgetq_lane_u32(vreinterpretq_u32_u8(umbcast_bits), 0); umbcast_flags += SXE2_RX_NUM_PER_LOOP_NEON; } if (split_rxe_flags) { uint8x16_t eop_shuf_mask = { - 0x08, 0x00, 0x0C, 0x04, + 0, 2, 4, 6, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; uint8x16_t eop_bits; uint32x4_t rxe_mask = { - 0x2080, 0x2080, 0x2080, 0x2080 + 0x20802080, 0x20802080, 0x20802080, 0x20802080 }; uint32x4_t rxe_bits; uint32x4_t eop_mask; - eop_mask = vshlq_n_u32(vdupq_n_u32(1), SXE2_RX_DESC_STATUS_EOP_SHIFT); + eop_mask = vdupq_n_u32((1U << SXE2_RX_DESC_STATUS_EOP_SHIFT) | + (1U << (SXE2_RX_DESC_STATUS_EOP_SHIFT + 16))); eop_bits = vandq_u8(vmvnq_u8(vreinterpretq_u8_u16(staterr)), vreinterpretq_u8_u32(eop_mask)); @@ -650,12 +644,22 @@ sxe2_rx_pkts_common_vec_neon(struct sxe2_rx_queue *rxq, struct rte_mbuf **rx_pkt } { - uint32x4_t dd_mask = vdupq_n_u32(1); - uint32x4_t sterr_dd = vandq_u32(vreinterpretq_u32_u16(staterr), dd_mask); - uint16x4_t packed_lo = vmovn_u32(sterr_dd); - uint64_t dd64 = vget_lane_u64(vreinterpret_u64_u16(packed_lo), 0); - - bit_num = (uint16_t)rte_popcount64(dd64); + const uint16x8_t dd_check = { + 0x0001, 0x0001, 0x0001, 0x0001, + 0, 0, 0, 0 + }; + uint16x8_t sterr_dd; + uint64_t stat; + sterr_dd = vandq_u16(staterr, dd_check); + sterr_dd = vshlq_n_u16(sterr_dd, 15); + sterr_dd = + vreinterpretq_u16_s16(vshrq_n_s16(vreinterpretq_s16_u16(sterr_dd), + 15)); + stat = ~vgetq_lane_u64(vreinterpretq_u64_u16(sterr_dd), 0); + if (likely(stat == 0)) + bit_num = SXE2_RX_NUM_PER_LOOP_NEON; + else + bit_num = (uint16_t)(rte_ctz64(stat) / 16); } done_num += bit_num; if (likely(bit_num != SXE2_RX_NUM_PER_LOOP_NEON)) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 32/47] net/sxe2: refine vectorized Tx/Rx mode setup 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (32 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 31/47] net/sxe2: fix NEON Rx ptype mapping and memory ordering liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 33/47] net/sxe2: fix RSS action attribute validation liujie5 ` (14 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Set rte_eth_tx_pkt_prepare_dummy for the simple and vectorized Tx paths instead of leaving the prepare callback unset, and split the NEON simple/offload mode selection based on the offload flag. Log the selected Tx/Rx mode flags and apply the default Rx free threshold when the configured value is zero. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_rx.c | 3 ++- drivers/net/sxe2/sxe2_txrx.c | 20 +++++++++++++++----- 2 files changed, 17 insertions(+), 6 deletions(-) diff --git a/drivers/net/sxe2/sxe2_rx.c b/drivers/net/sxe2/sxe2_rx.c index d700c60083..3830c676d7 100644 --- a/drivers/net/sxe2/sxe2_rx.c +++ b/drivers/net/sxe2/sxe2_rx.c @@ -319,7 +319,8 @@ int32_t __rte_cold sxe2_rx_queue_setup(struct rte_eth_dev *dev, rxq->mb_pool = mp; } - rxq->rx_free_thresh = rx_conf->rx_free_thresh; + rxq->rx_free_thresh = (rx_conf->rx_free_thresh == 0) ? + SXE2_DEFAULT_RX_FREE_THRESH : rx_conf->rx_free_thresh; rxq->port_id = dev->data->port_id; rxq->offloads = offloads; if (offloads & RTE_ETH_RX_OFFLOAD_KEEP_CRC) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index 79870866d1..f7276f6a19 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -358,7 +358,7 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } if (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; #ifdef RTE_ARCH_X86 if (tx_mode_flags & SXE2_TX_MODE_VEC_AVX512) { #ifdef CC_AVX512_SUPPORT @@ -386,21 +386,28 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) } #elif defined(RTE_ARCH_ARM64) if (tx_mode_flags & SXE2_TX_MODE_VEC_NEON) { - dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + if (tx_mode_flags & SXE2_TX_MODE_VEC_OFFLOAD) { + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon; + } else { + dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + } } else { - dev->tx_pkt_burst = sxe2_tx_pkts_vec_neon_simple; + dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; + dev->tx_pkt_burst = sxe2_tx_pkts; } #endif } else { if (tx_mode_flags & SXE2_TX_MODE_SIMPLE_BATCH) { - dev->tx_pkt_prepare = NULL; + dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy; dev->tx_pkt_burst = sxe2_tx_pkts_simple; } else { dev->tx_pkt_prepare = sxe2_tx_pkts_prepare; dev->tx_pkt_burst = sxe2_tx_pkts; } } + PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x port_id:%u.", + tx_mode_flags, dev->data->port_id); } static const struct { @@ -582,6 +589,9 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) dev->rx_pkt_burst = sxe2_rx_pkts_scattered_split; else dev->rx_pkt_burst = sxe2_rx_pkts_scattered; + + PMD_LOG_DEBUG(RX, "Rx mode flags:0x%016x port_id:%u.", + rx_mode_flags, dev->data->port_id); } static const struct { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 33/47] net/sxe2: fix RSS action attribute validation 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (33 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 32/47] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 34/47] net/sxe2: restore PF-only guard in UDP tunnel port add liujie5 ` (13 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The rss->level/key_len/queue_num checks only set the rte_flow_error but still return 0 (success), so invalid RSS configurations are accepted instead of being rejected with ENOTSUP. Return the error code from the validation checks, matching the behavior in the V3 implementation. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_flow_parse_action.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_flow_parse_action.c b/drivers/net/sxe2/sxe2_flow_parse_action.c index 03ada4e8a6..65ddfeb47f 100644 --- a/drivers/net/sxe2/sxe2_flow_parse_action.c +++ b/drivers/net/sxe2/sxe2_flow_parse_action.c @@ -12,7 +12,7 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss *rss, struct rte_flow_error *error) { - int32_t ret = ENOTSUP; + int32_t ret = -ENOTSUP; switch (rss->func) { case RTE_ETH_HASH_FUNCTION_DEFAULT: case RTE_ETH_HASH_FUNCTION_TOEPLITZ: @@ -25,15 +25,21 @@ static int32_t sxe2_flow_check_rss_action_attr(const struct rte_flow_action_rss goto l_end; } - if (rss->level > 2) + if (rss->level > 2) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "RSS level is could not be greater than 2"); - if (rss->key_len) + goto l_end; + } + if (rss->key_len) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a nonzero RSS key_len is not supported"); - if (rss->queue_num) + goto l_end; + } + if (rss->queue_num) { rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_ACTION, NULL, "a non-NULL RSS queue is not supported"); + goto l_end; + } ret = 0; l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 34/47] net/sxe2: restore PF-only guard in UDP tunnel port add 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (34 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 33/47] net/sxe2: fix RSS action attribute validation liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 35/47] net/sxe2: restore link update call in status query liujie5 ` (12 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_udp_tunnel_port_add_common() lost the check that restricts UDP tunnel port configuration to PF devices (not VF or representor), so VF/representor devices can now attempt to add UDP tunnel ports, which the hardware does not support. Restore the PF-only guard returning -ENOTSUP, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/net/sxe2/sxe2_ethdev.c b/drivers/net/sxe2/sxe2_ethdev.c index 77a31eb8a1..8c60c9cfde 100644 --- a/drivers/net/sxe2/sxe2_ethdev.c +++ b/drivers/net/sxe2/sxe2_ethdev.c @@ -630,6 +630,10 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) { + ret = -ENOTSUP; + goto l_end; + } rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -659,6 +663,7 @@ int32_t sxe2_udp_tunnel_port_add_common(struct sxe2_adapter *ad, l_unlock_end: rte_spinlock_unlock(&ad->udp_tunnel_ctx.lock); +l_end: return ret; } @@ -669,6 +674,9 @@ int32_t sxe2_udp_tunnel_port_del_common(struct sxe2_adapter *ad, struct sxe2_udp_tunnel_cfg *tunnel_config; int32_t ret = -1; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); tunnel_config = &ad->udp_tunnel_ctx.tunnel_conf[tunnel_proto]; @@ -703,6 +711,9 @@ static int32_t sxe2_udp_tunnel_port_clear(struct rte_eth_dev *dev) int32_t ret = 0; uint16_t tunnel_proto = 0; + if (ad->dev_type != SXE2_DEV_T_PF || ad->is_dev_repr) + return -ENOTSUP; + rte_spinlock_lock(&ad->udp_tunnel_ctx.lock); for (tunnel_proto = 0; tunnel_proto < SXE2_UDP_TUNNEL_MAX; tunnel_proto++) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 35/47] net/sxe2: restore link update call in status query 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (35 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 34/47] net/sxe2: restore PF-only guard in UDP tunnel port add liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 36/47] net/sxe2: validate representor ID against VF count liujie5 ` (11 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_mac_link_status_get() no longer calls sxe2_link_update() after refreshing the link context, so the ethdev link state is only refreshed during device init (sxe2_link_update_init) and never updated when link status is queried at runtime, including on LSC interrupt events. Move the sxe2_link_update() call back into sxe2_drv_mac_link_status_get() and simplify sxe2_link_update_init() accordingly, matching the V3 implementation. Fixes: 1d7fd921beef ("net/sxe2: support link update") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_irq.c | 2 ++ drivers/net/sxe2/sxe2_mac.c | 11 +++-------- 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_irq.c b/drivers/net/sxe2/sxe2_irq.c index ba764dd5e4..4c3a29900d 100644 --- a/drivers/net/sxe2/sxe2_irq.c +++ b/drivers/net/sxe2/sxe2_irq.c @@ -84,6 +84,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t if (oicr & RTE_BIT32(SXE2_COM_EC_LINK_CHG)) { PMD_DEV_LOG_INFO(adapter, DRV, "OICR=0x%" PRIx64, oicr); (void)sxe2_drv_mac_link_status_get(adapter); + (void)sxe2_link_update(dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, @@ -96,6 +97,7 @@ static void sxe2_event_irq_common_handler(struct sxe2_adapter *adapter, uint64_t continue; repr_adapter = SXE2_DEV_PRIVATE_TO_ADAPTER(repr_eth_dev); (void)sxe2_drv_mac_link_status_get(repr_adapter); + (void)sxe2_link_update(repr_eth_dev, 0); if (rte_eal_process_type() == RTE_PROC_PRIMARY) { rte_eth_dev_callback_process(repr_eth_dev, RTE_ETH_EVENT_INTR_LSC, diff --git a/drivers/net/sxe2/sxe2_mac.c b/drivers/net/sxe2/sxe2_mac.c index 729c804ac3..ab9bd5355b 100644 --- a/drivers/net/sxe2/sxe2_mac.c +++ b/drivers/net/sxe2/sxe2_mac.c @@ -448,18 +448,13 @@ int32_t sxe2_link_update_init(struct rte_eth_dev *dev) int32_t ret; PMD_INIT_FUNC_TRACE(); - rte_spinlock_init(&adapter->link_ctxt.link_lock); - ret = sxe2_drv_mac_link_status_get(adapter); - if (ret) { + if (ret) PMD_DEV_LOG_ERR(adapter, DRV, "Failed to get link status, ret=%d", ret); - goto l_end; - } - - (void)sxe2_link_update(dev, 0); + else + (void)sxe2_link_update(dev, 0); -l_end: return ret; } int32_t sxe2_link_update(struct rte_eth_dev *dev, __rte_unused int32_t wait_to_complete) -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 36/47] net/sxe2: validate representor ID against VF count 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (36 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 35/47] net/sxe2: restore link update call in status query liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 37/47] net/sxe2: use primary VSI ID for representor VSI liujie5 ` (10 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_switchdev_repr_private_data_init() indexes parent_adapter->repr_ctxt.repr_vf_id[repr_id] without checking that repr_id is within the number of configured VFs, which can access out of bounds when an invalid representor ID is passed. Add a bounds check on repr_id against repr_ctxt.nb_vf and return -EINVAL on the error path. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index efb1468b91..d0304ccc94 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -312,6 +312,12 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, repr_priv_data->repr_q_id = repr_id; repr_priv_data->repr_pf_id = parent_adapter->pf_idx; repr_priv_data->repr_vf_id = repr_id; + if (repr_id >= parent_adapter->repr_ctxt.nb_vf) { + PMD_LOG_ERR(INIT, "repr_id %u exceed max vf %u", + repr_id, parent_adapter->repr_ctxt.nb_vf); + ret = -EINVAL; + goto l_free; + } repr_priv_data->repr_vf_primary_vsi_id = parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id; repr_priv_data->repr_vf_backup_vsi_id = -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 37/47] net/sxe2: use primary VSI ID for representor VSI 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (37 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 36/47] net/sxe2: validate representor ID against VF count liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 38/47] net/sxe2: wrap command params fill debug log in macro liujie5 ` (9 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> For repr_vf_vsi_id, use the primary VSI id directly instead of falling back to the DPDK VSI id when the kernel VSI id is invalid. The kernel side guarantees the primary VSI id it provides is always valid in any scenario, so the fallback ternary is unnecessary. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_switchdev.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_switchdev.c b/drivers/net/sxe2/sxe2_switchdev.c index d0304ccc94..466182c55c 100644 --- a/drivers/net/sxe2/sxe2_switchdev.c +++ b/drivers/net/sxe2/sxe2_switchdev.c @@ -324,10 +324,7 @@ int32_t sxe2_switchdev_repr_private_data_init(struct rte_eth_dev *dev, parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; repr_priv_data->repr_vf_vsi_id = - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id != - SXE2_INVALID_VSI_ID ? - parent_adapter->repr_ctxt.repr_vf_id[repr_id].kernel_vsi_id : - parent_adapter->repr_ctxt.repr_vf_id[repr_id].dpdk_vsi_id; + repr_priv_data->repr_vf_primary_vsi_id; adapter->repr_priv_data = repr_priv_data; goto l_end; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 38/47] net/sxe2: wrap command params fill debug log in macro 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (38 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 37/47] net/sxe2: use primary VSI ID for representor VSI liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 39/47] net/sxe2: restore Rx queue buffer split fill support liujie5 ` (8 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_cmd_params_fill() passes the opcode string as a parameter to __sxe2_drv_cmd_params_fill() just to emit a debug log. The debug log is level-gated by PMD_DEV_LOG_DEBUG either way; moving it into the macro body only consolidates the call sites. Wrap the log and the fill helper in a do/while block, dropping the opc_str parameter so the opcode stringization happens at the call site. Evaluate the adapter argument exactly once through a local variable. Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 3a55528c44..85098ac664 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -26,10 +26,9 @@ static void sxe2_drv_trace_id_alloc(uint64_t *trace_id) } static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, - struct sxe2_drv_cmd_params *cmd, uint32_t opc, const char *opc_str, + struct sxe2_drv_cmd_params *cmd, uint32_t opc, void *in_data, uint32_t in_len, void *out_data, uint32_t out_len) { - PMD_DEV_LOG_DEBUG(adapter, DRV, "cmd opcode:%s", opc_str); cmd->timeout = SXE2_DRV_CMD_DFLT_TIMEOUT; cmd->opcode = opc; cmd->vsi_id = adapter->vsi_ctxt.dpdk_vsi_id; @@ -44,8 +43,11 @@ static void __sxe2_drv_cmd_params_fill(struct sxe2_adapter *adapter, } #define sxe2_drv_cmd_params_fill(adapter, cmd, opc, in_data, in_len, out_data, out_len) \ - __sxe2_drv_cmd_params_fill(adapter, cmd, opc, #opc, in_data, in_len, out_data, out_len) - + do { \ + struct sxe2_adapter *_ad = (adapter); \ + PMD_DEV_LOG_DEBUG(_ad, DRV, "cmd opcode:%s", #opc); \ + __sxe2_drv_cmd_params_fill(_ad, cmd, opc, in_data, in_len, out_data, out_len); \ + } while (0) int32_t sxe2_drv_dev_caps_get(struct sxe2_adapter *adapter, struct sxe2_drv_dev_caps_resp *dev_caps) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 39/47] net/sxe2: restore Rx queue buffer split fill support 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (39 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 38/47] net/sxe2: wrap command params fill debug log in macro liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:44 ` [PATCH v7 40/47] net/sxe2: skip tunnel config fill on get failure liujie5 ` (7 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The V4 branch dropped sxe2_rxq_buf_split_fill() and the buffer split handling in sxe2_rxq_ctxt_cfg_fill(), so the Rx buffer split offload (RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) is advertised in device info but the per-queue context never configures split_en/split_type_mask/ hdr_len, and buffer split packets are not handled correctly. Restore the sxe2_rxq_buf_split_fill() helper and the buffer split branch in sxe2_rxq_ctxt_cfg_fill(), matching the V3 implementation. Fixes: d8e4e075acb4 ("net/sxe2: add probing skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 88 ++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 85098ac664..7b27cf2e8d 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -195,6 +195,84 @@ int32_t sxe2_drv_vsi_del(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi) #define SXE2_RXQ_CTXT_CFG_BUF_LEN_ALIGN (1 << 7) #define SXE2_RX_HDR_SIZE 256 +static int32_t sxe2_rxq_buf_split_fill(struct sxe2_rx_queue *rxq, + struct sxe2_drv_rxq_ctxt *ctxt) +{ + uint32_t proto_hdr; + + proto_hdr = rxq->rx_seg[0].proto_hdr; + if (proto_hdr == RTE_PTYPE_UNKNOWN) { + PMD_LOG_ERR(RX, "Buffer split protocol must be configured"); + return -EINVAL; + } + + switch (proto_hdr & RTE_PTYPE_L4_MASK) { + case RTE_PTYPE_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_L4_TCP; + goto l_end; + case RTE_PTYPE_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_L4_UDP; + goto l_end; + case RTE_PTYPE_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L3_MASK) { + case RTE_PTYPE_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV4; + goto l_end; + case RTE_PTYPE_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_L2_MASK) { + case RTE_PTYPE_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L4_MASK) { + case RTE_PTYPE_INNER_L4_TCP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_TCP; + goto l_end; + case RTE_PTYPE_INNER_L4_UDP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_UDP; + goto l_end; + case RTE_PTYPE_INNER_L4_SCTP: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L4_SCTP; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L3_MASK) { + case RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV4; + goto l_end; + case RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L3_IPV6; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_INNER_L2_MASK) { + case RTE_PTYPE_INNER_L2_ETHER: + ctxt->split_type_mask = SXE2_PTYPE_INNER_L2_ETHER; + goto l_end; + } + + switch (proto_hdr & RTE_PTYPE_TUNNEL_MASK) { + case RTE_PTYPE_TUNNEL_GRENAT: + ctxt->split_type_mask = SXE2_PTYPE_TUNNEL_GRENAT; + goto l_end; + } + + PMD_LOG_ERR(RX, "Buffer split protocol is not supported"); + return -ENOTSUP; +l_end: + ctxt->hdr_len = SXE2_RX_HDR_SIZE; + return 0; +} + static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, struct sxe2_drv_rxq_cfg_req *req, uint16_t rxq_cnt) { @@ -228,7 +306,17 @@ static int32_t sxe2_rxq_ctxt_cfg_fill(struct sxe2_rx_queue *rxq, else ctxt->keep_crc_en = 0; + if (rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT) { + ret = sxe2_rxq_buf_split_fill(rxq, ctxt); + if (ret) + goto l_end; + ctxt->split_en = 1; + } else { + ctxt->split_en = 0; + } + ctxt->desc_size = sizeof(union sxe2_rx_desc); +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 40/47] net/sxe2: skip tunnel config fill on get failure 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (40 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 39/47] net/sxe2: restore Rx queue buffer split fill support liujie5 @ 2026-08-31 2:44 ` liujie5 2026-08-31 2:45 ` [PATCH v7 41/47] net/sxe2: skip flow ID assignment on filter add failure liujie5 ` (6 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:44 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_udp_tunnel_get() fills tunnel_config fields even when the firmware command fails, so a failed get overwrites the config with the (zero-initialized) response data instead of leaving it intact. Return early with the error code when sxe2_drv_cmd_exec() fails, matching the V3 implementation. Fixes: fff24885f70a ("net/sxe2: support custom UDP tunnel ports") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 7b27cf2e8d..5ab287a77b 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1650,15 +1650,17 @@ int32_t sxe2_drv_udp_tunnel_get(struct sxe2_adapter *adapter, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_LOG_ERR(DRV, "Failed to get udp proto %d port, ret=%d", req.type, ret); + goto l_end; + } tunnel_config->fw_port = resp.port; tunnel_config->fw_status = resp.enable; tunnel_config->fw_dst_en = resp.dst; tunnel_config->fw_src_en = resp.src; tunnel_config->fw_used = resp.fw_used; - +l_end: return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 41/47] net/sxe2: skip flow ID assignment on filter add failure 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (41 preceding siblings ...) 2026-08-31 2:44 ` [PATCH v7 40/47] net/sxe2: skip tunnel config fill on get failure liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 42/47] net/sxe2: correct command channel log messages liujie5 ` (5 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> sxe2_drv_flow_filter_add() assigns flow->flow_id from the response even when the firmware command fails, overwriting any previously set flow id with the zero-initialized response value. Return early on command failure so flow->flow_id is preserved, and set flow->create_err on both the success and error paths. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 5ab287a77b..6a5c1907c2 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -1818,9 +1818,13 @@ int32_t sxe2_drv_flow_filter_add(struct sxe2_adapter *adapter, struct sxe2_flow sxe2_drv_cmd_params_fill(adapter, &cmd, SXE2_DRV_CMD_FLOW_FILTER_ADD, &req, sizeof(req), &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, &cmd); - if (ret) + if (ret) { PMD_DEV_LOG_ERR(adapter, DRV, "Failed to add flow filter, ret: %d.", ret); + goto l_end; + } flow->flow_id = resp.flow_id; + +l_end: flow->create_err = ret; return ret; } -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 42/47] net/sxe2: correct command channel log messages 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (42 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 41/47] net/sxe2: skip flow ID assignment on filter add failure liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 43/47] net/sxe2: align command structs with kernel layout liujie5 ` (4 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu From: Jie Liu <liujie5@linkdatatechnology.com> Several error/warning messages in sxe2_cmd_chnl.c are inaccurate or lost context: - vsi_info_get: message lost the vsi id; restore it - rxq_bind_irq/rxq_unbind_irq: message lost the rxq index; restore it - promisc_config: fix "promic" typo in the message - queue_info_get_update: use "tx/rx queue map get failed" wording - rxq_mapping_set: incorrect "get dev caps" wording; use "rx queue mapping failed" - txq_mapping_set: "Rx queue" should read "Tx queue"; incorrect "get dev caps" wording should read "tx queue mapping failed" Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_cmd_chnl.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_cmd_chnl.c b/drivers/net/sxe2/sxe2_cmd_chnl.c index 6a5c1907c2..65e3a4ca21 100644 --- a/drivers/net/sxe2/sxe2_cmd_chnl.c +++ b/drivers/net/sxe2/sxe2_cmd_chnl.c @@ -481,7 +481,7 @@ int32_t sxe2_drv_vsi_info_get(struct sxe2_adapter *adapter, struct sxe2_vsi *vsi &vsi_info_get_resp, sizeof(vsi_info_get_resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_DEV_LOG_ERR(adapter, DRV, "switchdev cpvsi info get failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "vsi %u info get failed, ret=%d", vsi->vsi_id, ret); goto l_end; } @@ -537,7 +537,7 @@ int32_t sxe2_drv_rxq_bind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx, ui NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq bind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u bind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -557,7 +557,7 @@ int32_t sxe2_drv_rxq_unbind_irq(struct sxe2_adapter *adapter, uint16_t rxq_idx) NULL, 0); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_ERR(adapter, DRV, "rxq unbind irq failed, ret=%d", ret); + PMD_DEV_LOG_ERR(adapter, DRV, "rxq %u unbind irq failed, ret=%d", rxq_idx, ret); return ret; } @@ -758,7 +758,7 @@ int32_t sxe2_drv_promisc_config(struct sxe2_adapter *adapter, bool set) ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_DEV_LOG_WARN(adapter, DRV, "promic config failed, ret=%d", ret); + PMD_DEV_LOG_WARN(adapter, DRV, "promisc config failed, ret=%d", ret); return ret; } @@ -1683,7 +1683,7 @@ int32_t sxe2_drv_queue_info_get_update(struct sxe2_adapter *adapter, struct eth_ &resp, sizeof(resp)); ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) { - PMD_LOG_ERR(DRV, "get queue info map failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx/rx queue map get failed, ret=%d", ret); goto l_end; } @@ -1727,7 +1727,7 @@ int32_t sxe2_drv_rxq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "rx queue mapping failed, ret=%d", ret); l_end: return ret; @@ -1744,7 +1744,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, txq = eth_dev->data->tx_queues[queue_id]; if (txq == NULL) { - PMD_LOG_ERR(DRV, "Rx queue %u is not available or setup", queue_id); + PMD_LOG_ERR(DRV, "Tx queue %u is not available or setup", queue_id); ret = -EINVAL; goto l_end; } @@ -1758,7 +1758,7 @@ int32_t sxe2_drv_txq_mapping_set(struct rte_eth_dev *eth_dev, uint16_t queue_id, ret = sxe2_drv_cmd_exec(cdev, ¶m); if (ret) - PMD_LOG_ERR(DRV, "get dev caps failed, ret=%d", ret); + PMD_LOG_ERR(DRV, "tx queue mapping failed, ret=%d", ret); l_end: return ret; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 43/47] net/sxe2: align command structs with kernel layout 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (43 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 42/47] net/sxe2: correct command channel log messages liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 44/47] common/sxe2: fix ioctl channel log and close handling liujie5 ` (3 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The sxe2_drv_cmd.h command structures must match the layout used by historical SXE2 kernel versions so the same firmware command ABI is shared. Several structures were declared with __rte_packed_begin/ __rte_packed_end and extra rsv padding that the kernel layout does not have: - sxe2_drv_link_info_resp: drop rsv[3] padding (size unchanged) - sxe2_tm_res: drop rsv[2] padding and packed attribute, reducing the TM command payload length from 4 to 2 bytes to match the historical kernel layout - sxe2_tm_info: drop packed attribute, removing -Wpacked-not-aligned warnings - sxe2_tm_add_mid_msg/sxe2_tm_add_queue_msg: drop packed attribute; the message sizes (16 and 20 bytes) are unchanged, but the tm info member moves to its naturally aligned offset (4 and 8) - sxe2_drv_sfp_req/sxe2_drv_sfp_resp: drop packed attribute Fixes: 9c894f75113f ("net/sxe2: support TM hierarchy and shaping") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_drv_cmd.h | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/drivers/net/sxe2/sxe2_drv_cmd.h b/drivers/net/sxe2/sxe2_drv_cmd.h index 01fd813ed1..ee9d86dd4c 100644 --- a/drivers/net/sxe2/sxe2_drv_cmd.h +++ b/drivers/net/sxe2/sxe2_drv_cmd.h @@ -230,7 +230,6 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_vsi_info_get_resp { struct __rte_aligned(4) __rte_packed_begin sxe2_drv_link_info_resp { uint32_t speed; uint8_t status; - uint8_t rsv[3]; } __rte_packed_end; struct __rte_aligned(4) __rte_packed_begin sxe2_switchdev_info { @@ -348,31 +347,30 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_rss_hf_req { uint8_t rsv1[3]; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_res { +struct sxe2_tm_res { uint16_t teid; - uint8_t rsv[2]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_info { +struct sxe2_tm_info { uint32_t committed; uint32_t peak; uint8_t priority; uint8_t reserve; uint16_t weight; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_mid_msg { +struct sxe2_tm_add_mid_msg { uint16_t parent_teid; uint8_t adj_lvl; struct sxe2_tm_info info; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_tm_add_queue_msg { +struct sxe2_tm_add_queue_msg { uint16_t parent_teid; uint16_t queue_id; uint8_t adj_lvl; struct sxe2_tm_info info; -} __rte_packed_end; +}; struct __rte_aligned(4) __rte_packed_begin sxe2_drv_ipsec_capa_resq { uint16_t tx_sa_cnt; @@ -633,7 +631,7 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_udp_tunnel_resp { uint8_t rsv; } __rte_packed_end; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { +struct sxe2_drv_sfp_req { uint8_t is_wr; uint8_t is_qsfp; uint16_t bus_addr; @@ -642,14 +640,14 @@ struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_req { uint16_t data_len; uint16_t rvd; uint8_t data[]; -} __rte_packed_end; +}; -struct __rte_aligned(4) __rte_packed_begin sxe2_drv_sfp_resp { +struct sxe2_drv_sfp_resp { uint8_t is_wr; uint8_t is_qsfp; uint16_t data_len; uint8_t data[]; -} __rte_packed_end; +}; enum sxe2_fc_type { SXE2_FC_T_DIS = 0, -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 44/47] common/sxe2: fix ioctl channel log and close handling 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (44 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 43/47] net/sxe2: align command structs with kernel layout liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 45/47] doc/sxe2: remove drv-SW-stats parameter documentation liujie5 ` (2 subsequent siblings) 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> Compare sxe2_ioctl_chnl.c against the reference implementation and correct the following discrepancies: - sxe2_drv_dev_close: only log the closed fd when it is valid, move PMD_LOG_INFO inside the fd >= 0 check - sxe2_drv_dev_mmap: fix swapped format arguments in the debug log (cmd_fd and bar_idx were passed in the wrong order) - sxe2_drv_dev_dma_unmap: use PMD_LOG_ERR instead of PMD_LOG_INFO for the ioctl failure message Fixes: 83866f8d7638 ("common/sxe2: add base driver skeleton") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/common/sxe2/sxe2_ioctl_chnl.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/drivers/common/sxe2/sxe2_ioctl_chnl.c b/drivers/common/sxe2/sxe2_ioctl_chnl.c index 3e2fbf572f..9f455bd8d5 100644 --- a/drivers/common/sxe2/sxe2_ioctl_chnl.c +++ b/drivers/common/sxe2/sxe2_ioctl_chnl.c @@ -107,9 +107,11 @@ sxe2_drv_dev_close(struct sxe2_common_device *cdev) { int32_t fd = SXE2_CDEV_TO_CMD_FD(cdev); - if (fd >= 0) + if (fd >= 0) { close(fd); - PMD_LOG_INFO(COM, "closed device fd=%d", fd); + PMD_LOG_INFO(COM, "closed device fd=%d", fd); + } + SXE2_CDEV_TO_CMD_FD(cdev) = SXE2_CMD_FD_INVALID; } @@ -349,8 +351,9 @@ void goto l_err; } - PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", src=0x%"PRIx64", offset=0x%"PRIx64"", - bar_idx, cmd_fd, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); + PMD_LOG_DEBUG(COM, "fd=%d, bar idx=%d, len=%"PRIu64", " + "offset=0x%"PRIx64", pci_offset=0x%"PRIx64"", + cmd_fd, bar_idx, len, offset, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); virt = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, cmd_fd, SXE2_COM_PCI_OFFSET_GEN(bar_idx, offset)); @@ -477,7 +480,7 @@ sxe2_drv_dev_dma_unmap(struct sxe2_common_device *cdev, uint64_t iova) pthread_mutex_lock(&cdev->config.lock); ret = ioctl(cmd_fd, SXE2_COM_CMD_DMA_UNMAP, &cmd_params); if (ret < 0) { - PMD_LOG_INFO(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", + PMD_LOG_ERR(COM, "Failed to dma unmap, fd=%d, ret=%d, err:%s", cmd_fd, ret, strerror(errno)); ret = -EIO; pthread_mutex_unlock(&cdev->config.lock); -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 45/47] doc/sxe2: remove drv-SW-stats parameter documentation 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (45 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 44/47] common/sxe2: fix ioctl channel log and close handling liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 46/47] net/sxe2: remove ineffective representor queue counts liujie5 2026-08-31 2:45 ` [PATCH v7 47/47] net/sxe2: fix VEC mode selection in mode set functions liujie5 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The drv-sw-stats devarg is no longer supported. Remove its parameter description from the Runtime Configuration section. The "Receive Software Statistics" xstats section is kept because the rx_sw_* counters are still accumulated in the Rx data path and reported through rte_eth_xstats_get(). Fixes: 9e95b2b3859c ("doc: update sxe2 guide and features") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- doc/guides/nics/sxe2.rst | 31 ++----------------------------- 1 file changed, 2 insertions(+), 29 deletions(-) diff --git a/doc/guides/nics/sxe2.rst b/doc/guides/nics/sxe2.rst index c5b400a8ba..fe4f9f916b 100644 --- a/doc/guides/nics/sxe2.rst +++ b/doc/guides/nics/sxe2.rst @@ -109,30 +109,6 @@ Runtime Configuration Default value is 3 (count both packets and bytes). -- ``drv-sw-stats`` parameter [int] - - This parameter controls whether per-packet software statistics (SW stats) - are collected in the Rx data path. - - Hardware packet statistic counters may be inaccurate for certain packet types - due to hardware design limitations. - When accuracy of Rx packet classification statistics is critical, - enabling this parameter allows the driver to accumulate statistics in software - as packets are received, providing an alternative statistical path - that bypasses hardware counter inaccuracies. - - - 0: Disable software statistics collection (default). - The basic port statistics (``ipackets``, ``ibytes``) are reported - from the hardware counters. - - 1: Enable software statistics collection. - Per-packet software statistics are accumulated for unicast, - multicast, broadcast, and dropped packets in the Rx data path. - - When enabled, the following extended statistics (xstats) are available: - ``rx_sw_unicast_packets``, ``rx_sw_multicast_packets``, - ``rx_sw_broadcast_packets``, ``rx_sw_drop_packets``, - and ``rx_sw_drop_bytes``. - - ``no-sched-mode`` parameter [int] This parameter enables non-scheduling mode (no-sched mode). @@ -208,8 +184,7 @@ reflect the actual packets processed by the driver. Receive Software Statistics These counters are collected in the Rx data path - when ``drv-sw-stats=1`` is configured (see the ``drv-sw-stats`` devarg above). - When ``drv-sw-stats`` is disabled (default), these xstats report zero. + on every received packet. - ``rx_sw_unicast_packets``: Number of unicast packets received. - ``rx_sw_multicast_packets``: Number of multicast packets received. @@ -217,10 +192,8 @@ Receive Software Statistics - ``rx_sw_drop_packets``: Number of packets dropped in the Rx data path. - ``rx_sw_drop_bytes``: Number of bytes dropped in the Rx data path. - When ``drv-sw-stats`` is enabled, the basic counters - ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) + The basic counters ``ipackets`` and ``ibytes`` (from ``rte_eth_stats``) also reflect the software-accumulated packet and byte counts. - Otherwise, they are reported from hardware counters. Fnav Flow Engine Statistics The Fnav flow engine statistics type is controlled by -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 46/47] net/sxe2: remove ineffective representor queue counts 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (46 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 45/47] doc/sxe2: remove drv-SW-stats parameter documentation liujie5 @ 2026-08-31 2:45 ` liujie5 2026-08-31 2:45 ` [PATCH v7 47/47] net/sxe2: fix VEC mode selection in mode set functions liujie5 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> rte_eth_dev_info_get() overwrites dev_info->nb_rx_queues and dev_info->nb_tx_queues from dev->data after the PMD dev_infos_get callback returns, so assigning them in sxe2_repr_dev_infos_get() has no effect. Remove the ineffective assignments. Fixes: 635084db5d57 ("net/sxe2: support VF representors") Cc: stable@dpdk.org Cc: stephen@networkplumber.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_ethdev_repr.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/drivers/net/sxe2/sxe2_ethdev_repr.c b/drivers/net/sxe2/sxe2_ethdev_repr.c index b7096f5927..ec45187dc9 100644 --- a/drivers/net/sxe2/sxe2_ethdev_repr.c +++ b/drivers/net/sxe2/sxe2_ethdev_repr.c @@ -127,7 +127,7 @@ static int32_t sxe2_repr_dev_close(struct rte_eth_dev *dev) return 0; } -static int32_t sxe2_repr_dev_infos_get(struct rte_eth_dev *dev, +static int32_t sxe2_repr_dev_infos_get(__rte_unused struct rte_eth_dev *dev, struct rte_eth_dev_info *dev_info) { dev_info->max_rx_queues = 1; @@ -195,8 +195,6 @@ static int32_t sxe2_repr_dev_infos_get(struct rte_eth_dev *dev, dev_info->speed_capa = RTE_ETH_LINK_SPEED_10G | RTE_ETH_LINK_SPEED_25G | RTE_ETH_LINK_SPEED_50G | RTE_ETH_LINK_SPEED_100G; - dev_info->nb_rx_queues = dev->data->nb_rx_queues; - dev_info->nb_tx_queues = dev->data->nb_tx_queues; dev_info->default_rxportconf.burst_size = SXE2_RX_MAX_BURST; dev_info->default_txportconf.burst_size = SXE2_TX_MAX_BURST; -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* [PATCH v7 47/47] net/sxe2: fix VEC mode selection in mode set functions 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 ` (47 preceding siblings ...) 2026-08-31 2:45 ` [PATCH v7 46/47] net/sxe2: remove ineffective representor queue counts liujie5 @ 2026-08-31 2:45 ` liujie5 48 siblings, 0 replies; 278+ messages in thread From: liujie5 @ 2026-08-31 2:45 UTC (permalink / raw) To: stephen; +Cc: dev, Jie Liu, stable From: Jie Liu <liujie5@linkdatatechnology.com> The Tx/Rx mode set functions pre-assigned tx_mode_flags/rx_mode_flags from vec_flags (SXE2_{TX,RX}_MODE_VEC_SIMPLE or _VEC_OFFLOAD) before the per-ISA capability checks. As SXE2_{TX,RX}_MODE_VEC_SET_MASK includes the SIMPLE and OFFLOAD bits, the subsequent "(flags & SET_MASK) == 0" guards never matched, so the AVX2 and SSE VEC mode bits were never set and the vectorized path fell back to SSE even when AVX2 was available. Remove the pre-assignment and OR in "vec_flags | MODE" at each ISA selection branch so the correct VEC mode bit is selected on every architecture. Fixes: ac60f302cbef ("net/sxe2: add vectorized Rx and Tx") Cc: stable@dpdk.org Signed-off-by: Jie Liu <liujie5@linkdatatechnology.com> --- drivers/net/sxe2/sxe2_txrx.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/net/sxe2/sxe2_txrx.c b/drivers/net/sxe2/sxe2_txrx.c index f7276f6a19..824ac1a3f2 100644 --- a/drivers/net/sxe2/sxe2_txrx.c +++ b/drivers/net/sxe2/sxe2_txrx.c @@ -319,13 +319,12 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) ret = sxe2_tx_vec_support_check(dev, &vec_flags); if (ret == 0 && rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_128) { - tx_mode_flags = vec_flags; #ifdef RTE_ARCH_X86 if ((rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_512) && (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512F) == 1) && (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512BW) == 1)) { #ifdef CC_AVX512_SUPPORT - tx_mode_flags |= SXE2_TX_MODE_VEC_AVX512; + tx_mode_flags |= (vec_flags | SXE2_TX_MODE_VEC_AVX512); #else PMD_LOG_INFO(TX, "AVX512 is not supported in build env."); #endif @@ -334,10 +333,10 @@ void sxe2_tx_mode_func_set(struct rte_eth_dev *dev) ((rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX2) == 1) || (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512F) == 1)) && (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_256)) - tx_mode_flags |= SXE2_TX_MODE_VEC_AVX2; + tx_mode_flags |= (vec_flags | SXE2_TX_MODE_VEC_AVX2); if ((0 == (tx_mode_flags & SXE2_TX_MODE_VEC_SET_MASK))) - tx_mode_flags |= SXE2_TX_MODE_VEC_SSE; + tx_mode_flags |= (vec_flags | SXE2_TX_MODE_VEC_SSE); #elif defined(RTE_ARCH_ARM64) if (rte_cpu_get_flag_enabled(RTE_CPUFLAG_NEON) == 1) tx_mode_flags |= (vec_flags | SXE2_TX_MODE_VEC_NEON); @@ -520,13 +519,12 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) ret = sxe2_rx_vec_support_check(dev, &vec_flags); if (ret == 0 && rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_128) { - rx_mode_flags = vec_flags; #ifdef RTE_ARCH_X86 if ((rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_512) && (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512F) == 1) && (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512BW) == 1)) { #ifdef CC_AVX512_SUPPORT - rx_mode_flags |= SXE2_RX_MODE_VEC_AVX512; + rx_mode_flags |= (vec_flags | SXE2_RX_MODE_VEC_AVX512); #else PMD_LOG_INFO(RX, "AVX512 support detected but not enabled"); #endif @@ -535,11 +533,11 @@ void sxe2_rx_mode_func_set(struct rte_eth_dev *dev) ((rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX2) == 1) || (rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX512F) == 1)) && (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_256)) - rx_mode_flags |= SXE2_RX_MODE_VEC_AVX2; + rx_mode_flags |= (vec_flags | SXE2_RX_MODE_VEC_AVX2); if (((rx_mode_flags & SXE2_RX_MODE_VEC_SET_MASK) == 0) && rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_128) - rx_mode_flags |= SXE2_RX_MODE_VEC_SSE; + rx_mode_flags |= (vec_flags | SXE2_RX_MODE_VEC_SSE); #elif defined(RTE_ARCH_ARM64) if (rte_cpu_get_flag_enabled(RTE_CPUFLAG_NEON) == 1) { -- 2.52.0 ^ permalink raw reply related [flat|nested] 278+ messages in thread
* Re: [PATCH v1 00/13] net/sxe2: fix bugs 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 ` (12 preceding siblings ...) 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 @ 2026-08-18 14:22 ` Stephen Hemminger 13 siblings, 0 replies; 278+ messages in thread From: Stephen Hemminger @ 2026-08-18 14:22 UTC (permalink / raw) To: liujie5; +Cc: dev On Tue, 18 Aug 2026 10:15:05 +0800 liujie5@linkdatatechnology.com wrote: > From: Jie Liu <liujie5@linkdatatechnology.com> > > Jie Liu (13): > net/sxe2: add Rx queue buffer split fill support > net/sxe2: update switchdev repr VSI ID display format > net/sxe2: add ACL engine event statistics support > net/sxe2: enhance device cap and res management > net/sxe2: improve representor device initialization > net/sxe2: refactor flow tunnel port handling > net/sxe2: validate IPsec key length against maximum limit > net/sxe2: enhance repr event handling and MP code > net/sxe2: optimize vectorized Tx/Rx path > common/sxe2: allow munmap during kernel reset > net/sxe2: clean up duplicate function declarations > net/sxe2: clean up structure definitions > doc/sxe2: add acl-stat-type parameter documentation Still see lots of errors in AI review. Please fix and resubmit. In this case, since sxe2 is not in a previous stable release it is correct to not put stable@dpdk.org in. But it would help future developers if you added Fixes: tag if you know which commit introduced the problem. You should be sending each submission with a different version. (i.e next should be v3). # net/sxe2 v1 (13 patches) review notes ## Series-level 1. **Bug fixes buried in feature patches.** There are at least eight of them (list below). Each should be its own patch. A `Fixes:` tag would help even though sxe2 is not in 25.11, so nothing here is stable material. Fixes hiding in feature patches: - 03: `SXE2_PCI_DEVICE_ID_VF_1` 0x10b -> 0x10b2 (VF never binds today) - 04: `reg_width` 10 -> 0x10 for `SXE2_PCI_MAP_RES_IRQ_MSIX` - 04: duplicate `sxe2_switchdev_uninit()` / `sxe2_dev_pci_map_uinit()` in `dev_close` - 06: `sxe2_flow_check_rss_action_attr()` fell through and returned 0 after setting an error, so unsupported RSS attrs were silently accepted - 07: `dev->security_ctx` left dangling after free - 09: `rx_free_thresh == 0` not defaulted - 09: `other_vsi_list` not TAILQ_INIT'd before `sxe2_main_vsi_create()` - 09: NEON Rx DD count used `popcount` instead of "count up to first hole" 2. **Commit messages.** Patches 03, 04, 05, 06, 08, 09, 10 have a bulleted list of unrelated changes as the message. That is the signal the patch should be several patches. One logical change per patch, and the message says what the symptom was and what the fix is, not a changelog of every hunk. 3. **Message/diff mismatches:** - 08 says "Change error return from EINVAL to ENODATA"; the code returns `-ENOENT`. - 08 describes removing the `qstats` parameter from `sxe2_mp_req_get_stats`; no such change is in the diff. - 11 lists `sxe2_drv_mac_link_status_get` as removed; the diff keeps it. - 13 says it adds `acl-stat-type` docs; it also deletes the entire `drv-sw-stats` section (see below). 4. No cover letter in the bundle. Please send a 00/13 describing the series intent, since it mixes new features (ACL stats, buffer split), refactors and fixes. --- ## 01/13 net/sxe2: add Rx queue buffer split fill support The subject covers roughly 20 lines of the diff. The rest is log message typo fixes, an unrelated `sxe2_link_update()` call, `{}` -> `{0}`, error path changes in `sxe2_drv_udp_tunnel_get()` and `sxe2_drv_flow_filter_add()`. Split. - Removing the `opc_str` argument drops the only debug print of the command opcode. If that log is unwanted, say so; do not delete it as a side effect of adding buffer split. - `sxe2_rxq_buf_split_fill()` re-tests `rxq->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT`, which the caller already tested. The `else` branch is dead. Drop the test in the helper and keep the zeroing in the caller. - `ret = -1` on failure. Use a negative errno (`-ENOTSUP` for the unsupported protocol case, `-EINVAL` for unconfigured). - L3 matching only accepts `RTE_PTYPE_L3_IPV4_EXT_UNKNOWN` / `RTE_PTYPE_L3_IPV6_EXT_UNKNOWN`. An application that sets plain `RTE_PTYPE_L3_IPV4` falls through to the L2 test and then errors out. Is that intended? `sxe2_buffer_split_supported_hdr_ptypes_get()` should agree with what this function accepts. - `ctxt->hdr_len = SXE2_RX_HDR_SIZE;` is repeated in every case. Set it once after the switch chain. Also, why is the header length fixed at 256 bytes regardless of which layer the split is at? - Only `rx_seg[0].proto_hdr` is examined. What happens with `nseg > 1`? - `goto l_end` is being used as a `break` out of a switch. Restructure so the helper computes `split_type_mask` and returns. - `(void)sxe2_link_update(dev, 0)` inside `sxe2_drv_mac_link_status_get()`: this puts an ethdev-layer call inside the command channel layer, gives every caller (including the interrupt handler) the side effect of publishing link state, and reaches into `rte_eth_devices[]` directly. It is also only correct in combination with 08/13, which removes the now duplicate call in `sxe2_link_update_init()`. Those two hunks belong in one patch, and the layering should be the other way round: the caller calls `sxe2_link_update()`. ## 02/13 net/sxe2: update switchdev repr VSI ID display This is a struct field rename across four files, not a display change. Subject should say so. The new names lose information. `repr_vf_k_vsi_id` is fed from `kernel_vsi_id` and `repr_vf_u_vsi_id` from `dpdk_vsi_id`; calling them "primary" and "backup" hides that, and `sxe2_flow_src_split_proc()` still indexes them by `SXE2_MAX_DRV_TYPE_KERNEL` / `_DPDK`. Either keep kernel/dpdk in the names or explain what primary/backup means at the hardware level. The local buffers in `sxe2_dump_switchdev_info()` are still `k_vsi_buf` / `u_vsi_buf`. ## 03/13 net/sxe2: add ACL engine event statistics support Split at minimum into: (a) the `sxe2_fnav_cid_mgr` -> `sxe2_flow_cid_mgr` rename, (b) ACL stat support, (c) the VF device ID fix, (d) the sxe2_queue.c change. - **`SXE2_PCI_DEVICE_ID_VF_1` 0x10b -> 0x10b2** has nothing to do with ACL stats and is a user visible bug. Own patch, ideally with a `Fixes:` tag. - **`sxe2_flow_free_mgr()` can free a list member without removing it.** When `engine_type` is neither ACL nor FNAV, both branches are skipped, so `TAILQ_REMOVE()` never runs, but the code below still does `rte_free(mgr)`. That leaves a freed pointer on whichever list the mgr came from. Add an `else` that errors out, or derive `cid_mgr_list` once and remove unconditionally. - Same shape in `sxe2_flow_get_filter_cid()` and `sxe2_flow_query_mgr()`: the unknown engine case in `get_filter_cid` does `goto l_end` with `ret == 0`, so the caller sees success and no counter was allocated. `query_mgr` at least returns `-ENOTSUP`. Be consistent. - ``` SXE2_DRV_CMD_FLOW_ACL_STAT_QUERY = SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 1), SXE2_DRV_CMD_FLOW_ACL_STAT_ALLOC, SXE2_DRV_CMD_FLOW_ACL_STAT_FREE, ``` Every other entry in this enum is written with an explicit `SXE2_MK_DRV_CMD()`. Relying on implicit `+1` over an encoded value is fragile. Write `SXE2_MK_DRV_CMD(SXE2_DRV_CMD_MODULE_ACL, 2)` and `(..., 3)`. - `sxe2_drv_flow_acl_get_stat_id()` and `_free_stat()` send `sxe2_drv_flow_fnav_*` request structures. If the ACL and FNAV messages are the same on the wire, add a comment; otherwise define ACL types. - `req.is_clear = 1` is hardcoded, so every `rte_flow_query()` clears the hardware counter. `struct rte_flow_query_count` has a `reset` field. What happens with two readers, or with `reset == 0`? `mgr->hits`/`mgr->bytes` accumulate but nothing ever resets them. - `struct sxe2_drv_acl_query_stat_resp.stat_index` is never read. - `mgr->stat_index` is `uint16_t` but the firmware returns and consumes `uint32_t`. Silent truncation. - `int32_t ret = -1;` in all three new functions is immediately overwritten. - The ACL counter default uses `SXE2_FNAV_STAT_ENA_ALL` and `sxe2_parse_stat_type()` still range-checks against the FNAV enum. If the values are shared, rename the enum; if not, this is a bug. - `adapter->flow_ctxt.fnav_inited` now gates ACL too, and the sxe2_queue.c hunk (`rxq->fnav_enable = true`) is unrelated to ACL statistics. It also introduces an ordering dependency on `sxe2_flow_init()` running before `sxe2_queues_init()`. Please justify or drop. - `rte_zmalloc("sxe2_fnav_cid_mgr", ...)`, the "sxe2vf_fnav_cid_mgr" error string and "fnav get stats id failed" in `sxe2_flow_create()` are now on the shared path. ## 04/13 net/sxe2: enhance device cap and res management Seven unrelated changes in one patch. This one has to be split before it can be reviewed properly. Specific problems: - **`init_rss_err` label moved past `sxe2_security_uinit()`.** After the reorder, a failure in RSS init unwinds to `sxe2_intr_uninit()` and never calls `sxe2_security_uinit()`, so the security context leaks. The label has to stay above the `security_uinit` call. - **`*no_of_elements = RTE_DIM(ptypes)`** counts the trailing `RTE_PTYPE_UNKNOWN` terminator, so callers see one bogus element. Either report `RTE_DIM(ptypes) - 1` or drop the terminator from the array. - **`sxe2_switchdev_repr_match()` PF loop is inverted.** It returns false if *any* requested port differs from `pf_num`. With `nb_ports > 1` it can never succeed, which contradicts the new multi-port loop in `sxe2_eth_pmd_probe()` in this same patch. It should match if the adapter's `pf_num` is among the requested ports. - `port_idx = UINT16_MAX` is dead; the loop overwrites it immediately. - **`SXE2_PCI_REG_WRITE_WC` -> `SXE2_PCI_REG_WRITE`** in `sxe2_pci_map_write_reg()` changes MMIO write semantics with no explanation. Why is write combining no longer wanted, and does anything depend on the ordering difference? - `dev_info->nb_rx_queues` / `nb_tx_queues`: `rte_eth_dev_info_get()` already fills these from `dev->data` after calling the PMD op. Drop. - `RTE_ETH_RX_OFFLOAD_RSS_HASH` is added unconditionally while the rest of the RSS capability is gated on `SXE2_DEV_CAPS_OFFLOAD_RSS` a few lines below. - QINQ_STRIP / QINQ_INSERT / VLAN_FILTER are now advertised conditionally on `sxe2_dev_port_vlan_check()`. `dev_infos_get()` is supposed to report static hardware capability. Making it vary with runtime port VLAN state means an application that configured an offload can later see it as unsupported. What is the actual constraint here? - `sxe2_dev_infos_get()` returning `-EINVAL` when `main_vsi == NULL`: how can that happen? This looks like it is papering over an init ordering bug. - `sxe2_dev_pci_map_uinit()` silently drops the `map_ctxt != NULL` test. If that test was never needed, remove it in a separate cleanup and say so. - `sxe2_eth_pmd_probe()` calls `sxe2_eth_pmd_remove(cdev)` on failure. The bus layer also calls remove when probe fails. Confirm that is not a double teardown. - `SXE2_PCI_REG_WRITE` / `SXE2_PCI_REG_READ` moved to sxe2_ethdev.h while `SXE2_PCI_REG_WRITE_WC*` stays in sxe2_queue.h. Keep the family together. - `reg_width` 10 -> 0x10: separate fix, `Fixes:`. - The duplicate `sxe2_switchdev_uninit()` and `sxe2_dev_pci_map_uinit()` calls removed from `sxe2_dev_close()` are a double free fix. Separate patch, a `Fixes:` tag, and describe the crash. - `sxe2_dev_close()` and the `sxe2_dev_init()` unwind path are still not mirror images of each other (switchdev/eth ordering differs). Worth making them match. ## 05/13 net/sxe2: improve representor device initialization - `sxe2_stats_init()` is added with no matching uninit anywhere in the representor teardown path. If it allocates, that is a leak on port close. - The struct member realignment is unrelated churn. Drop it or make it its own patch. - `l_init_irq_ctxt_err` is entered when `sxe2_stats_init()` fails, but `l_init_sw_err` / `l_init_eth_err` are named after the step that failed. Rename to `l_init_stats_err` for consistency. - `snprintf(name, sizeof(name), "%s_representor_%s%u", ..., "vf", ...)`: put `vf` in the format string. Also, `cdev->dev->name` is variable length and truncation is not detected; check the return against `sizeof(name)`. ## 06/13 net/sxe2: refactor flow tunnel port handling - **The new PF_BOND block is dead code.** The two pre-existing lines immediately after it unconditionally overwrite index 0: ``` flow_src_vsi[SXE2_MAX_DRV_TYPE_DPDK][0] = adapter->vsi_ctxt.dpdk_vsi_id; flow_src_vsi[SXE2_MAX_DRV_TYPE_KERNEL][0] = adapter->vsi_ctxt.kernel_vsi_id; ``` so bond member 0 is clobbered and the new `else` branch is redundant with them. Delete those two lines. - **`bond_member_cnt` is never assigned anywhere in the series.** It is zero, so `flow_bond_num = 0` and the loop body never executes. Either the assignment is missing from the series or the whole PF_BOND block should be dropped until it is complete. - No bound check on `flow_bond_num` against the `flow_src_vsi` array dimensions. That value comes from the device. - **`sxe2_flow_check_rss_action_attr()`**: adding the `goto l_end` after each `rte_flow_error_set()` is a real bug fix. Today the function sets an error and then returns 0, so an unsupported `level`, `key_len` or `queue_num` is accepted. Separate patch, ideally with a `Fixes:` tag. Also fix the doubled space and grammar in "RSS level is could not be greater than 2". - The `sxe2_flow_meta_proc()` restructure (`else if` -> nested `if/else`) is identical in behaviour and adds a level of indentation. Drop it. - The function moves from sxe2_flow_parse_pattern.c to sxe2_flow.c are a pure code move. Put them in their own patch so the diff can be verified as a move. ## 07/13 net/sxe2: validate IPsec key length against maximum - The sxe2_security.c hunk (`dev->security_ctx = NULL`) is a separate use after free fix and is not mentioned in the commit message. Own patch, `Fixes:`. While there, the `sctx = NULL;` on the local is dead. - `sxe2_security_valid_key()` already takes `max_key`. What is the relationship between `max_key` and `SXE2_IPSEC_MAX_KEY_LEN`, and can `max_key` exceed it? If yes, the bug is in the caller and that is where it should be fixed. - The message claims this "prevents potential buffer overflows". If the overflow is reachable, this needs a `Fixes:` tag and a note to security@dpdk.org before posting. If it is defensive hardening, do not describe it as an overflow fix. - `>` vs `>=`: which is correct depends on whether the destination is `key[SXE2_IPSEC_MAX_KEY_LEN]`. Please confirm. ## 08/13 net/sxe2: enhance repr event handling and MP code Double space in the subject line. - **Caching `sxe2_mp_mz`.** The lookup is now done once and the result kept forever. If the memzone is freed and recreated across a device close/open, the cached pointer is stale. What guarantees its lifetime? - `uint8_t vf_id` against `nb_repr_vf`: if `nb_repr_vf` is wider and can exceed 255 this loops forever. Use the same type as the counter. - The new representor LSC loop calls `sxe2_drv_mac_link_status_get()` per representor from interrupt context, and with 01/13 applied each of those also runs `sxe2_link_update()`. That is N command channel round trips inside the interrupt handler on every link change. Consider reading the PF link state once and pushing it to the representors. - `sxe2_rxq_intr_unregister()`: moving `rte_free(irq_ctxt->rxq_event_fd)` inside the enclosing `if` leaks the allocation whenever that condition is false, unless the condition is exactly `rxq_event_fd != NULL`. Not mentioned in the commit message at all. - `sxe2_mp_do_primary_work()` takes a copy of the message parameter to "avoid side effects", but the original was already `const`. Just return `ret` and drop `param_copy`. - 08 removing `(void)sxe2_link_update(dev, 0)` from `sxe2_link_update_init()` is only correct with 01/13 applied. Squash the two hunks. ## 09/13 net/sxe2: optimize vectorized Tx/Rx path This patch is doing at least six things, several of which are correctness changes to the vector data path that are not mentioned in the commit message. It needs to be broken up, and the correctness changes need to say what was broken. Blocking issues: - **`sxe2_tx_queue_mbufs_release_vec()` now calls `rte_pktmbuf_free_seg()` without a NULL check.** `rte_pktmbuf_free_seg()` dereferences its argument; it does not tolerate NULL. The only "validation" added is a check on the ring pointer, not on individual entries, and `sxe2_tx_queue_reset_vec()` memsets the whole ring to zero. Any stop/start cycle, or any hole in [next_dd - (rs_thresh-1), next_use), is a NULL dereference. Restore the checks. - **`SXE2_RX_DESC_STATUS_DD_MASK` -> `SXE2_RX_DESC_STATUS_DD_SHIFT`** in `sxe2_monitor_callback()`. A shift count is not a mask. This looks like a regression, it is unrelated to the vector path, and it is unexplained. - **Acquire fences removed from the NEON Rx descriptor loads.** The three `rte_atomic_thread_fence(rte_memory_order_acquire)` calls between the `descs[3]`..`descs[0]` loads are gone. Those barriers are what stops arm64 from observing a partially DMA written descriptor. If they really are redundant given the single remaining fence before the lane reloads, spell out the argument in the commit message. Otherwise this is descriptor tearing under load. - **`repr_vf_vsi_id` fallback dropped.** In sxe2_switchdev.c the `kernel_vsi_id != SXE2_INVALID_VSI_ID ? kernel : dpdk` selection is replaced by an unconditional assignment from the primary (kernel) VSI, so `repr_vf_vsi_id` can now be `SXE2_INVALID_VSI_ID`. Functional regression, in a patch about vector Tx/Rx, with no mention in the message. - **NEON Rx ptype lane mapping changed.** Old: pkt0<-lane5, pkt1<-lane1, pkt2<-lane7, pkt3<-lane3. New: pkt0<-lane1, pkt1<-lane3, pkt2<-lane5, pkt3<-lane7. One of the two is wrong. Same for the ptype mask (`0x3FF` -> `SXE2_RX_DESC_PTYPE_MASK_NO_SHIFT << 16`), the `umbcast`/`eop` shuffle masks, `rxe_mask` `0x2080` -> `0x20802080`, and `eop_mask` gaining the +16 bit. These are correctness fixes to Rx flag and ptype parsing. They belong in their own patch with `Fixes:` and a description of the wrong behaviour they produce. - **The DD count rewrite is a real bug fix.** The old `popcount` counted every set DD bit in the group, so a pattern like DD,not-DD,DD,DD reported 4 and the driver consumed descriptors the hardware had not written. The new `rte_ctz64(stat) / 16` stops at the first hole, which is correct. Own patch, ideally with a `Fixes:` tag. - **`vst1q_lane_u32(...)` -> `*(uint32_t *)umbcast_flags = vgetq_lane_u32(...)`.** The intrinsic does not require 4 byte alignment; the direct store does. If `umbcast_flags` can be unaligned this is undefined behaviour. - **`sxe2_tx_desc_fill_4_neon_simple()` disagrees with the tail loop.** The 4-wide body always encodes `MACLEN` from `pkt->l2_len`, but the scalar tail calls `sxe2_tx_desc_fill_one_neon(..., false)`. Within one burst, packets get different descriptor contents depending on their position in the ring. Also, in simple mode the application is not required to set `l2_len`. - `vst1q_u64_x4()` is not available on all arm64 toolchains DPDK supports. Check the minimum GCC/clang requirement. - **`sxe2_tx_queue_reset_vec()`** memsets `sizeof(struct sxe2_tx_buffer) * ring_depth` while every other line in the vec path now uses `struct sxe2_tx_buffer_vec`. Which type owns the allocation? State it, and use that type consistently, otherwise the next person who shrinks the vec allocation gets a heap overflow here. - `sxe2_tx_queues_vec_prepare()` used to override only `mbufs_release`; it now replaces the whole ops table and calls `queue_reset()`. Resetting the descriptor ring here is a behaviour change that is not described. - `sxe2_tx_vec_ops_get()` returns a `struct` by value. Return `const struct sxe2_txq_ops *` like `sxe2_default_txq_ops`. - Deleting `sxe2_tx_bufs_free_vec_avx512()` removes the mempool cache bulk free fast path. That is a performance regression in a patch titled "optimize". If it was removed because it was wrong (the `rte_mempool_ops_enqueue_bulk(mp, (void *)buffer, rs_thresh)` call assumes `struct sxe2_tx_buffer_vec` is exactly one pointer, and the `goto normal` jumps into scope), say that. - `dev->tx_pkt_prepare = rte_eth_tx_pkt_prepare_dummy` instead of `NULL`: is that symbol available to out of tree and in tree PMDs, and what does it buy over the NULL fast path in `rte_eth_tx_prepare()`? - Removing `#ifndef SXE2_TEST` from sxe2_txrx_vec_avx512.c is unexplained. - `PMD_LOG_DEBUG(TX, "Tx mode flags:0x%016x ...")`: `%016x` on a 32 bit value pads to 16 digits. Use `%#010x`. - Unrelated but welcome fixes to pull out of here: `rx_free_thresh` defaulting, `TAILQ_INIT(&other_vsi_list)` before `sxe2_main_vsi_create()`, `main_vsi = NULL` after destroy, `sxe2_tx_buffer_ring_free()` NULLing the pointer, and the duplicate `sxe2_rx_pkts_scattered` declaration (that last one belongs in 11/13). - `if (ret && ret != -EPERM)` in `sxe2_vsi_uninit()`: why is `-EPERM` expected? Add a comment. Note the code then proceeds to drop the VSI list even though the firmware side destroy failed. ## 10/13 common/sxe2: allow munmap during kernel reset Two unrelated changes; the subject only covers one. - Removing the `kernel_reset` guard from `sxe2_drv_dev_munmap()`: what was the guard protecting against, and why is it safe now? "Enable cleanup operations" is not an explanation of why unmapping after a kernel reset is safe. - `cdev` becomes unused. Check whether the `l_end:` label still has a `goto` reaching it; if not, that is `-Wunused-label`. - `sxe2_classes_driver_remove()` returning 0 when `cdrv == NULL` hides a probe/remove asymmetry. A NULL `cdrv->remove` is legitimately optional; a NULL `cdrv` on a device that was probed is a bug worth logging. ## 11/13 net/sxe2: clean up duplicate function declarations Fine, with two notes: the commit message lists `sxe2_drv_mac_link_status_get` but the diff keeps it, and the duplicate `sxe2_rx_pkts_scattered` declaration removed in 09/13 belongs in this patch. ## 12/13 net/sxe2: clean up structure definitions These are firmware message structures. Removing `__rte_packed_begin` / `__rte_packed_end` and `__rte_aligned(4)` changes their size and alignment, and therefore the wire format: - `sxe2_tm_res`: dropping `rsv[2]` takes `sizeof()` from 4 to 2. - `sxe2_rxq_map_info`: alignment goes from 4 to 8, which changes the offset of the embedded arrays in `sxe2_queue_map_info` and possibly the size of any parent message. - `sxe2_drv_sfp_req` / `_resp` have flexible array members and are presumably sized as `sizeof(req) + data_len` at the call site. Tail padding changes the length sent to firmware. I am not going to take this without either a firmware ABI document confirming the new layouts, or `static_assert(sizeof(...) == N)` on every message structure so a future change cannot silently break it. Note that someone deliberately converted these to the `__rte_packed_begin/_end` form recently; please explain what is wrong with them now. ## 13/13 doc/sxe2: add acl-stat-type parameter documentation **This deletes the entire `drv-sw-stats` section** (23 lines removed, 10 added) while the commit message only describes adding `acl-stat-type`. Nothing in this series removes the `drv-sw-stats` devarg from the driver, so this looks like a rebase accident that drops documentation for a supported parameter. Please restore it. Minor: the new block says both "- 3: Count both packets and bytes (default)." and "Default value is 3 (count both packets and bytes)." Pick one. Also, the documentation should land in the same patch as the devarg it documents (03/13), not eleven patches later. ^ permalink raw reply [flat|nested] 278+ messages in thread
end of thread, other threads:[~2026-08-31 16:19 UTC | newest] Thread overview: 278+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2026-08-18 2:15 [PATCH v1 00/13] net/sxe2: fix bugs liujie5 2026-08-18 2:15 ` [PATCH v1 01/13] net/sxe2: add Rx queue buffer split fill support liujie5 2026-08-18 2:15 ` [PATCH v1 02/13] net/sxe2: update switchdev repr VSI ID display format liujie5 2026-08-18 2:15 ` [PATCH v1 03/13] net/sxe2: add ACL engine event statistics support liujie5 2026-08-18 2:15 ` [PATCH v1 04/13] net/sxe2: enhance device cap and res management liujie5 2026-08-18 2:15 ` [PATCH v1 05/13] net/sxe2: improve representor device initialization liujie5 2026-08-18 2:15 ` [PATCH v1 06/13] net/sxe2: refactor flow tunnel port handling liujie5 2026-08-18 2:15 ` [PATCH v1 07/13] net/sxe2: validate IPsec key length against maximum limit liujie5 2026-08-18 2:15 ` [PATCH v1 08/13] net/sxe2: enhance repr event handling and MP code liujie5 2026-08-18 2:15 ` [PATCH v1 09/13] net/sxe2: optimize vectorized Tx/Rx path liujie5 2026-08-18 2:15 ` [PATCH v1 10/13] common/sxe2: allow munmap during kernel reset liujie5 2026-08-18 2:15 ` [PATCH v1 11/13] net/sxe2: clean up duplicate function declarations liujie5 2026-08-18 2:15 ` [PATCH v1 12/13] net/sxe2: clean up structure definitions liujie5 2026-08-18 2:15 ` [PATCH v1 13/13] doc/sxe2: add acl-stat-type parameter documentation liujie5 2026-08-26 8:53 ` [PATCH v3 00/51] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-26 17:07 ` Stephen Hemminger 2026-08-26 8:53 ` [PATCH v3 01/51] common/sxe2: fix null pointer in class driver remove liujie5 2026-08-26 8:53 ` [PATCH v3 02/51] common/sxe2: allow munmap during kernel reset liujie5 2026-08-26 8:53 ` [PATCH v3 03/51] net/sxe2: fix VF PCI device ID liujie5 2026-08-26 8:54 ` [PATCH v3 04/51] net/sxe2: fix MSIX register width in PF map table liujie5 2026-08-26 8:54 ` [PATCH v3 05/51] net/sxe2: restore pf and port index caps assignment liujie5 2026-08-26 8:54 ` [PATCH v3 06/51] net/sxe2: fix VSI lifecycle management liujie5 2026-08-26 8:54 ` [PATCH v3 07/51] net/sxe2: initialize stats in representor device init liujie5 2026-08-26 8:54 ` [PATCH v3 08/51] net/sxe2: use base device name for representor naming liujie5 2026-08-26 8:54 ` [PATCH v3 09/51] net/sxe2: propagate LSC event to VF representors liujie5 2026-08-26 8:54 ` [PATCH v3 10/51] net/sxe2: validate IPsec key length against maximum limit liujie5 2026-08-26 8:54 ` [PATCH v3 11/51] net/sxe2: rename representor VSI ID fields liujie5 2026-08-26 8:54 ` [PATCH v3 12/51] net/sxe2: clean up duplicate function declarations liujie5 2026-08-26 8:54 ` [PATCH v3 13/51] net/sxe2: fix null VSI dereference in device info liujie5 2026-08-26 8:55 ` [PATCH v3 14/51] net/sxe2: fill MAC and queue counts " liujie5 2026-08-26 8:55 ` [PATCH v3 15/51] net/sxe2: fix QinQ and RSS offload capability report liujie5 2026-08-26 8:55 ` [PATCH v3 16/51] net/sxe2: use regular write for mapped registers liujie5 2026-08-26 8:55 ` [PATCH v3 17/51] net/sxe2: move PCI register read macro to common header liujie5 2026-08-26 8:55 ` [PATCH v3 18/51] net/sxe2: validate PCI map resource type liujie5 2026-08-26 8:55 ` [PATCH v3 19/51] net/sxe2: guard PCI BAR unmap when not initialized liujie5 2026-08-26 8:55 ` [PATCH v3 20/51] net/sxe2: fix null dereference in dev uninit liujie5 2026-08-26 8:55 ` [PATCH v3 21/51] net/sxe2: fix duplicated cleanup in dev close liujie5 2026-08-26 8:55 ` [PATCH v3 22/51] net/sxe2: align dev init and cleanup order liujie5 2026-08-26 8:55 ` [PATCH v3 23/51] net/sxe2: simplify switchdev representor matching liujie5 2026-08-26 8:55 ` [PATCH v3 24/51] net/sxe2: probe all requested PF ports liujie5 2026-08-26 8:56 ` [PATCH v3 25/51] net/sxe2: rename fnav cid manager symbols to flow liujie5 2026-08-26 8:56 ` [PATCH v3 26/51] net/sxe2: move tunnel port helpers into flow module liujie5 2026-08-26 8:56 ` [PATCH v3 27/51] net/sxe2: add ACL engine event statistics support liujie5 2026-08-26 8:56 ` [PATCH v3 28/51] net/sxe2: guard Rx queue event FD free in unregister liujie5 2026-08-26 8:56 ` [PATCH v3 29/51] net/sxe2: refactor primary process MP message handling liujie5 2026-08-26 8:56 ` [PATCH v3 30/51] net/sxe2: refactor Tx queue reset operations liujie5 2026-08-26 8:56 ` [PATCH v3 31/51] net/sxe2: unify vectorized Tx buffer handling liujie5 2026-08-26 8:56 ` [PATCH v3 32/51] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 2026-08-26 8:56 ` [PATCH v3 33/51] net/sxe2: fix RSS action attribute validation liujie5 2026-08-26 8:56 ` [PATCH v3 34/51] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 2026-08-26 8:57 ` [PATCH v3 35/51] net/sxe2: align flow meta proc priority handling with V3 liujie5 2026-08-26 8:57 ` [PATCH v3 36/51] net/sxe2: restore link update call in status query liujie5 2026-08-26 8:57 ` [PATCH v3 37/51] net/sxe2: validate representor ID against VF count liujie5 2026-08-26 8:57 ` [PATCH v3 38/51] net/sxe2: use primary VSI ID for representor VSI liujie5 2026-08-26 8:57 ` [PATCH v3 39/51] net/sxe2: wrap command params fill debug log in macro liujie5 2026-08-26 8:57 ` [PATCH v3 40/51] net/sxe2: restore Rx queue buffer split fill support liujie5 2026-08-26 8:57 ` [PATCH v3 41/51] net/sxe2: skip tunnel config fill on get failure liujie5 2026-08-26 8:57 ` [PATCH v3 42/51] net/sxe2: skip flow id assignment on filter add failure liujie5 2026-08-26 8:57 ` [PATCH v3 43/51] net/sxe2: fix command channel log messages liujie5 2026-08-26 8:57 ` [PATCH v3 44/51] net/sxe2: align command structs with historical kernel layout liujie5 2026-08-26 8:58 ` [PATCH v3 45/51] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-26 8:58 ` [PATCH v3 46/51] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-26 8:58 ` [PATCH v3 47/51] net/sxe2: harden ACL flow count resource handling liujie5 2026-08-26 8:58 ` [PATCH v3 48/51] net/sxe2: fix device init and representor matching issues liujie5 2026-08-26 8:58 ` [PATCH v3 49/51] net/sxe2: use correct loop counter type for representor LSC liujie5 2026-08-26 8:58 ` [PATCH v3 50/51] net/sxe2: restore NULL check in vectorized Tx mbuf release liujie5 2026-08-26 8:58 ` [PATCH v3 51/51] net/sxe2: simplify Rx queue buffer split fill helper liujie5 2026-08-27 2:36 ` [PATCH v4 00/44] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-27 15:14 ` Stephen Hemminger 2026-08-27 2:36 ` [PATCH v4 01/44] common/sxe2: fix null pointer in class driver remove liujie5 2026-08-27 2:36 ` [PATCH v4 02/44] common/sxe2: allow munmap during kernel reset liujie5 2026-08-27 2:36 ` [PATCH v4 03/44] net/sxe2: fix VF PCI device ID liujie5 2026-08-27 2:36 ` [PATCH v4 04/44] net/sxe2: fix MSIX register width in PF map table liujie5 2026-08-27 2:36 ` [PATCH v4 05/44] net/sxe2: restore pf and port index caps assignment liujie5 2026-08-27 2:36 ` [PATCH v4 06/44] net/sxe2: fix VSI lifecycle management liujie5 2026-08-27 2:37 ` [PATCH v4 07/44] net/sxe2: initialize stats in representor device init liujie5 2026-08-27 2:37 ` [PATCH v4 08/44] net/sxe2: use base device name for representor naming liujie5 2026-08-27 2:37 ` [PATCH v4 09/44] net/sxe2: propagate LSC event to VF representors liujie5 2026-08-27 2:37 ` [PATCH v4 10/44] net/sxe2: validate IPsec key length against maximum limit liujie5 2026-08-27 2:37 ` [PATCH v4 11/44] net/sxe2: rename representor VSI ID fields liujie5 2026-08-27 2:37 ` [PATCH v4 12/44] net/sxe2: clean up duplicate function declarations liujie5 2026-08-27 2:37 ` [PATCH v4 13/44] net/sxe2: fix null VSI dereference in device info liujie5 2026-08-27 2:37 ` [PATCH v4 14/44] net/sxe2: fill MAC and queue counts " liujie5 2026-08-27 2:37 ` [PATCH v4 15/44] net/sxe2: fix QinQ and RSS offload capability report liujie5 2026-08-27 2:37 ` [PATCH v4 16/44] net/sxe2: use regular write for mapped registers liujie5 2026-08-27 2:37 ` [PATCH v4 17/44] net/sxe2: move PCI register read macro to common header liujie5 2026-08-27 2:38 ` [PATCH v4 18/44] net/sxe2: validate PCI map resource type liujie5 2026-08-27 2:38 ` [PATCH v4 19/44] net/sxe2: guard PCI BAR unmap when not initialized liujie5 2026-08-27 2:38 ` [PATCH v4 20/44] net/sxe2: fix null dereference in dev uninit liujie5 2026-08-27 2:38 ` [PATCH v4 21/44] net/sxe2: fix duplicated cleanup in dev close liujie5 2026-08-27 2:38 ` [PATCH v4 22/44] net/sxe2: align dev init and cleanup order liujie5 2026-08-27 2:38 ` [PATCH v4 23/44] net/sxe2: simplify switchdev representor matching liujie5 2026-08-27 2:38 ` [PATCH v4 24/44] net/sxe2: rename fnav cid manager symbols to flow liujie5 2026-08-27 2:38 ` [PATCH v4 25/44] net/sxe2: move tunnel port helpers into flow module liujie5 2026-08-27 2:38 ` [PATCH v4 26/44] net/sxe2: add ACL engine event statistics support liujie5 2026-08-27 2:38 ` [PATCH v4 27/44] net/sxe2: guard Rx queue event FD free in unregister liujie5 2026-08-27 2:39 ` [PATCH v4 28/44] net/sxe2: refactor primary process MP message handling liujie5 2026-08-27 2:39 ` [PATCH v4 29/44] net/sxe2: refactor Tx queue reset operations liujie5 2026-08-27 2:39 ` [PATCH v4 30/44] net/sxe2: unify vectorized Tx buffer handling liujie5 2026-08-27 2:39 ` [PATCH v4 31/44] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 2026-08-27 2:39 ` [PATCH v4 32/44] net/sxe2: fix RSS action attribute validation liujie5 2026-08-27 2:39 ` [PATCH v4 33/44] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 2026-08-27 2:39 ` [PATCH v4 34/44] net/sxe2: restore link update call in status query liujie5 2026-08-27 2:39 ` [PATCH v4 35/44] net/sxe2: validate representor ID against VF count liujie5 2026-08-27 2:39 ` [PATCH v4 36/44] net/sxe2: use primary VSI ID for representor VSI liujie5 2026-08-27 2:39 ` [PATCH v4 37/44] net/sxe2: wrap command params fill debug log in macro liujie5 2026-08-27 2:40 ` [PATCH v4 38/44] net/sxe2: restore Rx queue buffer split fill support liujie5 2026-08-27 2:40 ` [PATCH v4 39/44] net/sxe2: skip tunnel config fill on get failure liujie5 2026-08-27 2:40 ` [PATCH v4 40/44] net/sxe2: skip flow id assignment on filter add failure liujie5 2026-08-27 2:40 ` [PATCH v4 41/44] net/sxe2: fix command channel log messages liujie5 2026-08-27 2:40 ` [PATCH v4 42/44] net/sxe2: align command structs with historical kernel layout liujie5 2026-08-27 2:40 ` [PATCH v4 43/44] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-27 2:40 ` [PATCH v4 44/44] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 3:23 ` [PATCH v5 00/45] net/sxe2: add Stars SXE2 net driver with fixes liujie5 2026-08-28 3:23 ` [PATCH v5 01/45] common/sxe2: fix null pointer in class driver remove liujie5 2026-08-28 3:23 ` [PATCH v5 02/45] common/sxe2: allow munmap during kernel reset liujie5 2026-08-28 3:23 ` [PATCH v5 03/45] net/sxe2: fix VF PCI device ID liujie5 2026-08-28 3:23 ` [PATCH v5 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 2026-08-28 3:23 ` [PATCH v5 05/45] net/sxe2: restore pf and port index caps assignment liujie5 2026-08-28 3:23 ` [PATCH v5 06/45] net/sxe2: fix VSI lifecycle management liujie5 2026-08-28 3:23 ` [PATCH v5 07/45] net/sxe2: initialize stats in representor device init liujie5 2026-08-28 3:23 ` [PATCH v5 08/45] net/sxe2: use base device name for representor naming liujie5 2026-08-28 3:23 ` [PATCH v5 09/45] net/sxe2: propagate LSC event to VF representors liujie5 2026-08-28 3:24 ` [PATCH v5 10/45] net/sxe2: clear security context pointer on uninit liujie5 2026-08-28 3:24 ` [PATCH v5 11/45] net/sxe2: rename representor VSI ID fields liujie5 2026-08-28 3:24 ` [PATCH v5 12/45] net/sxe2: clean up duplicate function declarations liujie5 2026-08-28 3:24 ` [PATCH v5 13/45] net/sxe2: fix null VSI dereference in device info liujie5 2026-08-28 3:24 ` [PATCH v5 14/45] net/sxe2: fill MAC and queue counts " liujie5 2026-08-28 3:24 ` [PATCH v5 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 2026-08-28 3:24 ` [PATCH v5 16/45] net/sxe2: use regular write for mapped registers liujie5 2026-08-28 3:24 ` [PATCH v5 17/45] net/sxe2: move PCI register read macro to common header liujie5 2026-08-28 3:24 ` [PATCH v5 18/45] net/sxe2: validate PCI map resource type liujie5 2026-08-28 3:24 ` [PATCH v5 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 2026-08-28 3:25 ` [PATCH v5 20/45] net/sxe2: fix null dereference in dev uninit liujie5 2026-08-28 3:25 ` [PATCH v5 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 2026-08-28 3:25 ` [PATCH v5 22/45] net/sxe2: align dev init and cleanup order liujie5 2026-08-28 3:25 ` [PATCH v5 23/45] net/sxe2: simplify switchdev representor matching liujie5 2026-08-28 3:25 ` [PATCH v5 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 2026-08-28 3:25 ` [PATCH v5 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 2026-08-28 3:25 ` [PATCH v5 26/45] net/sxe2: add ACL engine event statistics support liujie5 2026-08-28 3:25 ` [PATCH v5 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 2026-08-28 3:25 ` [PATCH v5 28/45] net/sxe2: refactor primary process MP message handling liujie5 2026-08-28 3:25 ` [PATCH v5 29/45] net/sxe2: refactor Tx queue reset operations liujie5 2026-08-28 3:26 ` [PATCH v5 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 2026-08-28 3:26 ` [PATCH v5 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 2026-08-28 3:26 ` [PATCH v5 32/45] net/sxe2: fix RSS action attribute validation liujie5 2026-08-28 3:26 ` [PATCH v5 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 2026-08-28 3:26 ` [PATCH v5 34/45] net/sxe2: restore link update call in status query liujie5 2026-08-28 3:26 ` [PATCH v5 35/45] net/sxe2: validate representor ID against VF count liujie5 2026-08-28 3:26 ` [PATCH v5 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 2026-08-28 3:26 ` [PATCH v5 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 2026-08-28 3:26 ` [PATCH v5 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 2026-08-28 3:26 ` [PATCH v5 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 2026-08-28 3:27 ` [PATCH v5 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 2026-08-28 3:27 ` [PATCH v5 41/45] net/sxe2: fix command channel log messages liujie5 2026-08-28 3:27 ` [PATCH v5 42/45] net/sxe2: align command structs with historical kernel layout liujie5 2026-08-28 3:27 ` [PATCH v5 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-28 3:27 ` [PATCH v5 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 3:27 ` [PATCH v5 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-28 7:36 ` [PATCH v6 00/45] net/sxe2: update SXE2 poll mode driver liujie5 2026-08-28 16:49 ` Stephen Hemminger 2026-08-28 7:36 ` [PATCH v6 01/45] common/sxe2: fix null pointer in class driver remove liujie5 2026-08-28 7:36 ` [PATCH v6 02/45] common/sxe2: allow munmap during kernel reset liujie5 2026-08-28 7:36 ` [PATCH v6 03/45] net/sxe2: fix VF PCI device ID liujie5 2026-08-28 7:37 ` [PATCH v6 04/45] net/sxe2: fix MSIX register width in PF map table liujie5 2026-08-28 7:37 ` [PATCH v6 05/45] net/sxe2: restore pf and port index caps assignment liujie5 2026-08-28 7:37 ` [PATCH v6 06/45] net/sxe2: fix VSI lifecycle management liujie5 2026-08-28 7:37 ` [PATCH v6 07/45] net/sxe2: initialize stats in representor device init liujie5 2026-08-28 7:37 ` [PATCH v6 08/45] net/sxe2: use base device name for representor naming liujie5 2026-08-28 7:37 ` [PATCH v6 09/45] net/sxe2: propagate LSC event to VF representors liujie5 2026-08-28 7:37 ` [PATCH v6 10/45] net/sxe2: clear security context pointer on uninit liujie5 2026-08-28 7:37 ` [PATCH v6 11/45] net/sxe2: rename representor VSI ID fields liujie5 2026-08-28 7:37 ` [PATCH v6 12/45] net/sxe2: clean up duplicate function declarations liujie5 2026-08-28 7:37 ` [PATCH v6 13/45] net/sxe2: fix null VSI dereference in device info liujie5 2026-08-28 7:37 ` [PATCH v6 14/45] net/sxe2: fill MAC and queue counts " liujie5 2026-08-28 7:38 ` [PATCH v6 15/45] net/sxe2: fix QinQ and RSS offload capability report liujie5 2026-08-28 7:38 ` [PATCH v6 16/45] net/sxe2: use regular write for mapped registers liujie5 2026-08-28 7:38 ` [PATCH v6 17/45] net/sxe2: move PCI register read macro to common header liujie5 2026-08-28 7:38 ` [PATCH v6 18/45] net/sxe2: validate PCI map resource type liujie5 2026-08-28 7:38 ` [PATCH v6 19/45] net/sxe2: guard PCI BAR unmap when not initialized liujie5 2026-08-28 7:38 ` [PATCH v6 20/45] net/sxe2: fix null dereference in dev uninit liujie5 2026-08-28 7:38 ` [PATCH v6 21/45] net/sxe2: fix duplicated cleanup in dev close liujie5 2026-08-28 7:38 ` [PATCH v6 22/45] net/sxe2: align dev init and cleanup order liujie5 2026-08-28 7:38 ` [PATCH v6 23/45] net/sxe2: simplify switchdev representor matching liujie5 2026-08-28 7:38 ` [PATCH v6 24/45] net/sxe2: rename fnav cid manager symbols to flow liujie5 2026-08-28 7:39 ` [PATCH v6 25/45] net/sxe2: move tunnel port helpers into flow module liujie5 2026-08-28 7:39 ` [PATCH v6 26/45] net/sxe2: add ACL engine event statistics support liujie5 2026-08-28 7:39 ` [PATCH v6 27/45] net/sxe2: guard Rx queue event FD free in unregister liujie5 2026-08-28 7:39 ` [PATCH v6 28/45] net/sxe2: refactor primary process MP message handling liujie5 2026-08-28 7:39 ` [PATCH v6 29/45] net/sxe2: refactor Tx queue reset operations liujie5 2026-08-28 7:39 ` [PATCH v6 30/45] net/sxe2: unify vectorized Tx buffer handling liujie5 2026-08-28 7:39 ` [PATCH v6 31/45] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 2026-08-28 7:39 ` [PATCH v6 32/45] net/sxe2: fix RSS action attribute validation liujie5 2026-08-28 7:39 ` [PATCH v6 33/45] net/sxe2: restore PF-only guard in udp tunnel port add liujie5 2026-08-28 7:39 ` [PATCH v6 34/45] net/sxe2: restore link update call in status query liujie5 2026-08-28 7:39 ` [PATCH v6 35/45] net/sxe2: validate representor ID against VF count liujie5 2026-08-28 7:40 ` [PATCH v6 36/45] net/sxe2: use primary VSI ID for representor VSI liujie5 2026-08-28 7:40 ` [PATCH v6 37/45] net/sxe2: wrap command params fill debug log in macro liujie5 2026-08-28 7:40 ` [PATCH v6 38/45] net/sxe2: restore Rx queue buffer split fill support liujie5 2026-08-28 7:40 ` [PATCH v6 39/45] net/sxe2: skip tunnel config fill on get failure liujie5 2026-08-28 7:40 ` [PATCH v6 40/45] net/sxe2: skip flow id assignment on filter add failure liujie5 2026-08-28 7:40 ` [PATCH v6 41/45] net/sxe2: fix command channel log messages liujie5 2026-08-28 7:40 ` [PATCH v6 42/45] net/sxe2: align command structs with historical kernel layout liujie5 2026-08-28 7:40 ` [PATCH v6 43/45] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-28 7:40 ` [PATCH v6 44/45] doc/sxe2: remove drv-sw-stats parameter documentation liujie5 2026-08-28 7:40 ` [PATCH v6 45/45] net/sxe2: remove ineffective queue counts in representor info liujie5 2026-08-31 2:34 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings Jie Liu 2026-08-31 2:34 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove Jie Liu 2026-08-31 2:34 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset Jie Liu 2026-08-31 2:34 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID Jie Liu 2026-08-31 2:34 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table Jie Liu 2026-08-31 2:34 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment Jie Liu 2026-08-31 2:34 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management Jie Liu 2026-08-31 2:34 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init Jie Liu 2026-08-31 2:34 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming Jie Liu 2026-08-31 2:34 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors Jie Liu 2026-08-31 2:34 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit Jie Liu 2026-08-31 2:34 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields Jie Liu 2026-08-31 2:34 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations Jie Liu 2026-08-31 2:34 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info Jie Liu 2026-08-31 2:34 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " Jie Liu 2026-08-31 2:34 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report Jie Liu 2026-08-31 2:34 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers Jie Liu 2026-08-31 2:34 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header Jie Liu 2026-08-31 2:34 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type Jie Liu 2026-08-31 2:34 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized Jie Liu 2026-08-31 2:34 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit Jie Liu 2026-08-31 2:41 ` [PATCH v7 00/47] net/sxe2: re-align with reference and fix review findings liujie5 2026-08-31 7:46 ` David Marchand 2026-08-31 16:18 ` Stephen Hemminger 2026-08-31 2:41 ` [PATCH v7 01/47] common/sxe2: fix null pointer in class driver remove liujie5 2026-08-31 2:41 ` [PATCH v7 02/47] common/sxe2: allow munmap during kernel reset liujie5 2026-08-31 2:41 ` [PATCH v7 03/47] net/sxe2: fix VF PCI device ID liujie5 2026-08-31 2:41 ` [PATCH v7 04/47] net/sxe2: fix MSIX register width in PF map table liujie5 2026-08-31 2:41 ` [PATCH v7 05/47] net/sxe2: restore PF and port index caps assignment liujie5 2026-08-31 2:41 ` [PATCH v7 06/47] net/sxe2: fix VSI lifecycle management liujie5 2026-08-31 2:41 ` [PATCH v7 07/47] net/sxe2: initialize stats in representor device init liujie5 2026-08-31 2:41 ` [PATCH v7 08/47] net/sxe2: use base device name for representor naming liujie5 2026-08-31 2:41 ` [PATCH v7 09/47] net/sxe2: propagate LSC event to VF representors liujie5 2026-08-31 2:42 ` [PATCH v7 10/47] net/sxe2: clear security context pointer on uninit liujie5 2026-08-31 2:42 ` [PATCH v7 11/47] net/sxe2: rename representor VSI ID fields liujie5 2026-08-31 2:42 ` [PATCH v7 12/47] net/sxe2: clean up duplicate function declarations liujie5 2026-08-31 2:42 ` [PATCH v7 13/47] net/sxe2: fix null VSI dereference in device info liujie5 2026-08-31 2:42 ` [PATCH v7 14/47] net/sxe2: fill MAC addresses " liujie5 2026-08-31 2:42 ` [PATCH v7 15/47] net/sxe2: fix QinQ and RSS offload capability report liujie5 2026-08-31 2:42 ` [PATCH v7 16/47] net/sxe2: use regular write for mapped registers liujie5 2026-08-31 2:42 ` [PATCH v7 17/47] net/sxe2: move PCI register read macro to common header liujie5 2026-08-31 2:42 ` [PATCH v7 18/47] net/sxe2: validate PCI map resource type liujie5 2026-08-31 2:42 ` [PATCH v7 19/47] net/sxe2: guard PCI BAR unmap when not initialized liujie5 2026-08-31 2:42 ` [PATCH v7 20/47] net/sxe2: fix null dereference in dev uninit liujie5 2026-08-31 2:43 ` [PATCH v7 21/47] net/sxe2: fix duplicated cleanup in dev close liujie5 2026-08-31 2:43 ` [PATCH v7 22/47] net/sxe2: align dev init and cleanup order liujie5 2026-08-31 2:43 ` [PATCH v7 23/47] net/sxe2: simplify switchdev representor matching liujie5 2026-08-31 2:43 ` [PATCH v7 24/47] net/sxe2: rename fnav cid manager symbols to flow liujie5 2026-08-31 2:43 ` [PATCH v7 25/47] net/sxe2: move tunnel port helpers into flow module liujie5 2026-08-31 2:43 ` [PATCH v7 26/47] net/sxe2: add ACL engine event statistics support liujie5 2026-08-31 2:43 ` [PATCH v7 27/47] net/sxe2: refactor primary process MP message handling liujie5 2026-08-31 2:43 ` [PATCH v7 28/47] net/sxe2: refactor Tx queue reset operations liujie5 2026-08-31 2:43 ` [PATCH v7 29/47] net/sxe2: unify vectorized Tx buffer handling liujie5 2026-08-31 2:43 ` [PATCH v7 30/47] net/sxe2: optimize NEON Tx descriptor fill liujie5 2026-08-31 2:44 ` [PATCH v7 31/47] net/sxe2: fix NEON Rx ptype mapping and memory ordering liujie5 2026-08-31 2:44 ` [PATCH v7 32/47] net/sxe2: refine vectorized Tx/Rx mode setup liujie5 2026-08-31 2:44 ` [PATCH v7 33/47] net/sxe2: fix RSS action attribute validation liujie5 2026-08-31 2:44 ` [PATCH v7 34/47] net/sxe2: restore PF-only guard in UDP tunnel port add liujie5 2026-08-31 2:44 ` [PATCH v7 35/47] net/sxe2: restore link update call in status query liujie5 2026-08-31 2:44 ` [PATCH v7 36/47] net/sxe2: validate representor ID against VF count liujie5 2026-08-31 2:44 ` [PATCH v7 37/47] net/sxe2: use primary VSI ID for representor VSI liujie5 2026-08-31 2:44 ` [PATCH v7 38/47] net/sxe2: wrap command params fill debug log in macro liujie5 2026-08-31 2:44 ` [PATCH v7 39/47] net/sxe2: restore Rx queue buffer split fill support liujie5 2026-08-31 2:44 ` [PATCH v7 40/47] net/sxe2: skip tunnel config fill on get failure liujie5 2026-08-31 2:45 ` [PATCH v7 41/47] net/sxe2: skip flow ID assignment on filter add failure liujie5 2026-08-31 2:45 ` [PATCH v7 42/47] net/sxe2: correct command channel log messages liujie5 2026-08-31 2:45 ` [PATCH v7 43/47] net/sxe2: align command structs with kernel layout liujie5 2026-08-31 2:45 ` [PATCH v7 44/47] common/sxe2: fix ioctl channel log and close handling liujie5 2026-08-31 2:45 ` [PATCH v7 45/47] doc/sxe2: remove drv-SW-stats parameter documentation liujie5 2026-08-31 2:45 ` [PATCH v7 46/47] net/sxe2: remove ineffective representor queue counts liujie5 2026-08-31 2:45 ` [PATCH v7 47/47] net/sxe2: fix VEC mode selection in mode set functions liujie5 2026-08-18 14:22 ` [PATCH v1 00/13] net/sxe2: fix bugs Stephen Hemminger
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.