From patchwork Fri Oct 18 11:16:01 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Cao, Yahui" X-Patchwork-Id: 61455 X-Patchwork-Delegate: xiaolong.ye@intel.com Return-Path: X-Original-To: patchwork@dpdk.org Delivered-To: patchwork@dpdk.org Received: from [92.243.14.124] (localhost [127.0.0.1]) by dpdk.org (Postfix) with ESMTP id A9CFA1E8B6; Fri, 18 Oct 2019 05:34:05 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by dpdk.org (Postfix) with ESMTP id 579DA1E56A for ; Fri, 18 Oct 2019 05:33:54 +0200 (CEST) X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga003.fm.intel.com ([10.253.24.29]) by fmsmga103.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 17 Oct 2019 20:33:54 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.67,310,1566889200"; d="scan'208";a="202577951" Received: from dpdk-yahui-skylake.sh.intel.com ([10.67.119.16]) by FMSMGA003.fm.intel.com with ESMTP; 17 Oct 2019 20:33:52 -0700 From: Yahui Cao To: Qiming Yang , Wenzhuo Lu Cc: dev@dpdk.org, Qi Zhang , Xiaolong Ye , Beilei Xing , Yahui Cao Date: Fri, 18 Oct 2019 19:16:01 +0800 Message-Id: <20191018111602.26742-9-yahui.cao@intel.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20191018111602.26742-1-yahui.cao@intel.com> References: <20191017160454.14518-1-yahui.cao@intel.com> <20191018111602.26742-1-yahui.cao@intel.com> Subject: [dpdk-dev] [PATCH v7 8/9] net/ice: add FDIR vxlan tunnel support X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org Sender: "dev" Enable FDIR vxlan tunnel matching for RTE_FLOW Signed-off-by: Yahui Cao Acked-by: Qi Zhang --- drivers/net/ice/ice_ethdev.h | 8 +++ drivers/net/ice/ice_fdir_filter.c | 108 ++++++++++++++++++++++++++---- 2 files changed, 104 insertions(+), 12 deletions(-) diff --git a/drivers/net/ice/ice_ethdev.h b/drivers/net/ice/ice_ethdev.h index ab8b452e4..d47c5dd93 100644 --- a/drivers/net/ice/ice_ethdev.h +++ b/drivers/net/ice/ice_ethdev.h @@ -241,6 +241,11 @@ struct ice_vsi { bool offset_loaded; }; +enum ice_fdir_tunnel_type { + ICE_FDIR_TUNNEL_TYPE_NONE = 0, + ICE_FDIR_TUNNEL_TYPE_VXLAN, +}; + struct rte_flow; TAILQ_HEAD(ice_flow_list, rte_flow); @@ -249,6 +254,7 @@ TAILQ_HEAD(ice_parser_list, ice_flow_parser_node); struct ice_fdir_filter_conf { struct ice_fdir_fltr input; + enum ice_fdir_tunnel_type tunnel_type; struct ice_fdir_counter *counter; /* flow specific counter context */ struct rte_flow_action_count act_count; @@ -268,6 +274,8 @@ struct ice_fdir_fltr_pattern { struct ice_fdir_extra ext_data; struct ice_fdir_extra ext_mask; + + enum ice_fdir_tunnel_type tunnel_type; }; #define ICE_FDIR_COUNTER_DEFAULT_POOL_SIZE 1 diff --git a/drivers/net/ice/ice_fdir_filter.c b/drivers/net/ice/ice_fdir_filter.c index 1b6101ec6..d18e9245d 100644 --- a/drivers/net/ice/ice_fdir_filter.c +++ b/drivers/net/ice/ice_fdir_filter.c @@ -47,6 +47,21 @@ ICE_FDIR_INSET_ETH_IPV6 | \ ICE_INSET_SCTP_SRC_PORT | ICE_INSET_SCTP_DST_PORT) +#define ICE_FDIR_INSET_VXLAN_IPV4 (\ + ICE_INSET_TUN_IPV4_SRC | ICE_INSET_TUN_IPV4_DST) + +#define ICE_FDIR_INSET_VXLAN_IPV4_TCP (\ + ICE_FDIR_INSET_VXLAN_IPV4 | \ + ICE_INSET_TUN_TCP_SRC_PORT | ICE_INSET_TUN_TCP_DST_PORT) + +#define ICE_FDIR_INSET_VXLAN_IPV4_UDP (\ + ICE_FDIR_INSET_VXLAN_IPV4 | \ + ICE_INSET_TUN_UDP_SRC_PORT | ICE_INSET_TUN_UDP_DST_PORT) + +#define ICE_FDIR_INSET_VXLAN_IPV4_SCTP (\ + ICE_FDIR_INSET_VXLAN_IPV4 | \ + ICE_INSET_TUN_SCTP_SRC_PORT | ICE_INSET_TUN_SCTP_DST_PORT) + static struct ice_pattern_match_item ice_fdir_pattern[] = { {pattern_eth_ipv4, ICE_FDIR_INSET_ETH_IPV4, ICE_INSET_NONE}, {pattern_eth_ipv4_udp, ICE_FDIR_INSET_ETH_IPV4_UDP, ICE_INSET_NONE}, @@ -56,6 +71,22 @@ static struct ice_pattern_match_item ice_fdir_pattern[] = { {pattern_eth_ipv6_udp, ICE_FDIR_INSET_ETH_IPV6_UDP, ICE_INSET_NONE}, {pattern_eth_ipv6_tcp, ICE_FDIR_INSET_ETH_IPV6_TCP, ICE_INSET_NONE}, {pattern_eth_ipv6_sctp, ICE_FDIR_INSET_ETH_IPV6_SCTP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_ipv4, + ICE_FDIR_INSET_VXLAN_IPV4, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_ipv4_udp, + ICE_FDIR_INSET_VXLAN_IPV4_UDP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_ipv4_tcp, + ICE_FDIR_INSET_VXLAN_IPV4_TCP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_ipv4_sctp, + ICE_FDIR_INSET_VXLAN_IPV4_SCTP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_eth_ipv4, + ICE_FDIR_INSET_VXLAN_IPV4, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_eth_ipv4_udp, + ICE_FDIR_INSET_VXLAN_IPV4_UDP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_eth_ipv4_tcp, + ICE_FDIR_INSET_VXLAN_IPV4_TCP, ICE_INSET_NONE}, + {pattern_eth_ipv4_udp_vxlan_eth_ipv4_sctp, + ICE_FDIR_INSET_VXLAN_IPV4_SCTP, ICE_INSET_NONE}, }; static struct ice_flow_parser ice_fdir_parser; @@ -650,6 +681,14 @@ ice_fdir_input_set_parse(uint64_t inset, enum ice_flow_field *field) {ICE_INSET_UDP_DST_PORT, ICE_FLOW_FIELD_IDX_UDP_DST_PORT}, {ICE_INSET_SCTP_SRC_PORT, ICE_FLOW_FIELD_IDX_SCTP_SRC_PORT}, {ICE_INSET_SCTP_DST_PORT, ICE_FLOW_FIELD_IDX_SCTP_DST_PORT}, + {ICE_INSET_TUN_IPV4_SRC, ICE_FLOW_FIELD_IDX_IPV4_SA}, + {ICE_INSET_TUN_IPV4_DST, ICE_FLOW_FIELD_IDX_IPV4_DA}, + {ICE_INSET_TUN_TCP_SRC_PORT, ICE_FLOW_FIELD_IDX_TCP_SRC_PORT}, + {ICE_INSET_TUN_TCP_DST_PORT, ICE_FLOW_FIELD_IDX_TCP_DST_PORT}, + {ICE_INSET_TUN_UDP_SRC_PORT, ICE_FLOW_FIELD_IDX_UDP_SRC_PORT}, + {ICE_INSET_TUN_UDP_DST_PORT, ICE_FLOW_FIELD_IDX_UDP_DST_PORT}, + {ICE_INSET_TUN_SCTP_SRC_PORT, ICE_FLOW_FIELD_IDX_SCTP_SRC_PORT}, + {ICE_INSET_TUN_SCTP_DST_PORT, ICE_FLOW_FIELD_IDX_SCTP_DST_PORT}, }; for (i = 0, j = 0; i < RTE_DIM(ice_inset_map); i++) { @@ -799,6 +838,7 @@ ice_fdir_add_del_filter(struct ice_pf *pf, struct ice_fltr_desc desc; struct ice_hw *hw = ICE_PF_TO_HW(pf); unsigned char *pkt = (unsigned char *)pf->fdir.prg_pkt; + bool is_tun; int ret; filter->input.dest_vsi = pf->main_vsi->idx; @@ -806,8 +846,10 @@ ice_fdir_add_del_filter(struct ice_pf *pf, memset(&desc, 0, sizeof(desc)); ice_fdir_get_prgm_desc(hw, &filter->input, &desc, add); + is_tun = filter->tunnel_type ? true : false; + memset(pkt, 0, ICE_FDIR_PKT_LEN); - ret = ice_fdir_get_prgm_pkt(&filter->input, pkt, false); + ret = ice_fdir_get_gen_prgm_pkt(hw, &filter->input, pkt, false, is_tun); if (ret) { PMD_DRV_LOG(ERR, "Generate dummy packet failed"); return -EINVAL; @@ -828,6 +870,8 @@ ice_fdir_extract_fltr_key(struct ice_fdir_fltr_pattern *key, rte_memcpy(&key->mask, &input->mask, sizeof(key->mask)); rte_memcpy(&key->ext_data, &input->ext_data, sizeof(key->ext_data)); rte_memcpy(&key->ext_mask, &input->ext_mask, sizeof(key->ext_mask)); + + key->tunnel_type = filter->tunnel_type; } /* Check if there exists the flow director filter */ @@ -895,6 +939,7 @@ ice_fdir_create_filter(struct ice_adapter *ad, struct ice_fdir_info *fdir_info = &pf->fdir; struct ice_fdir_filter_conf *entry, *node; struct ice_fdir_fltr_pattern key; + bool is_tun; int ret; ice_fdir_extract_fltr_key(&key, filter); @@ -914,8 +959,10 @@ ice_fdir_create_filter(struct ice_adapter *ad, return -rte_errno; } + is_tun = filter->tunnel_type ? true : false; + ret = ice_fdir_input_set_conf(pf, filter->input.flow_type, - filter->input_set, false); + filter->input_set, is_tun); if (ret) { rte_flow_error_set(error, -ret, RTE_FLOW_ERROR_TYPE_HANDLE, NULL, @@ -957,7 +1004,7 @@ ice_fdir_create_filter(struct ice_adapter *ad, } flow->rule = entry; - ice_fdir_cnt_update(pf, filter->input.flow_type, false, true); + ice_fdir_cnt_update(pf, filter->input.flow_type, is_tun, true); return 0; @@ -981,10 +1028,13 @@ ice_fdir_destroy_filter(struct ice_adapter *ad, struct ice_fdir_info *fdir_info = &pf->fdir; struct ice_fdir_filter_conf *filter, *entry; struct ice_fdir_fltr_pattern key; + bool is_tun; int ret; filter = (struct ice_fdir_filter_conf *)flow->rule; + is_tun = filter->tunnel_type ? true : false; + if (filter->counter) { ice_fdir_counter_free(pf, filter->counter); filter->counter = NULL; @@ -1015,7 +1065,7 @@ ice_fdir_destroy_filter(struct ice_adapter *ad, return -rte_errno; } - ice_fdir_cnt_update(pf, filter->input.flow_type, false, false); + ice_fdir_cnt_update(pf, filter->input.flow_type, is_tun, false); flow->rule = NULL; rte_free(filter); @@ -1243,12 +1293,14 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, const struct rte_flow_item *item = pattern; enum rte_flow_item_type item_type; enum rte_flow_item_type l3 = RTE_FLOW_ITEM_TYPE_END; + enum ice_fdir_tunnel_type tunnel_type = ICE_FDIR_TUNNEL_TYPE_NONE; const struct rte_flow_item_eth *eth_spec, *eth_mask; const struct rte_flow_item_ipv4 *ipv4_spec, *ipv4_mask; const struct rte_flow_item_ipv6 *ipv6_spec, *ipv6_mask; const struct rte_flow_item_tcp *tcp_spec, *tcp_mask; const struct rte_flow_item_udp *udp_spec, *udp_mask; const struct rte_flow_item_sctp *sctp_spec, *sctp_mask; + const struct rte_flow_item_vxlan *vxlan_spec, *vxlan_mask; uint64_t input_set = ICE_INSET_NONE; uint8_t flow_type = ICE_FLTR_PTYPE_NONF_NONE; uint8_t ipv6_addr_mask[16] = { @@ -1316,9 +1368,13 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, return -rte_errno; } if (ipv4_mask->hdr.src_addr == UINT32_MAX) - input_set |= ICE_INSET_IPV4_SRC; + input_set |= tunnel_type ? + ICE_INSET_TUN_IPV4_SRC : + ICE_INSET_IPV4_SRC; if (ipv4_mask->hdr.dst_addr == UINT32_MAX) - input_set |= ICE_INSET_IPV4_DST; + input_set |= tunnel_type ? + ICE_INSET_TUN_IPV4_DST : + ICE_INSET_IPV4_DST; if (ipv4_mask->hdr.type_of_service == UINT8_MAX) input_set |= ICE_INSET_IPV4_TOS; if (ipv4_mask->hdr.time_to_live == UINT8_MAX) @@ -1412,9 +1468,13 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, } if (tcp_mask->hdr.src_port == UINT16_MAX) - input_set |= ICE_INSET_TCP_SRC_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_TCP_SRC_PORT : + ICE_INSET_TCP_SRC_PORT; if (tcp_mask->hdr.dst_port == UINT16_MAX) - input_set |= ICE_INSET_TCP_DST_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_TCP_DST_PORT : + ICE_INSET_TCP_DST_PORT; /* Get filter info */ if (l3 == RTE_FLOW_ITEM_TYPE_IPV4) { @@ -1450,9 +1510,13 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, } if (udp_mask->hdr.src_port == UINT16_MAX) - input_set |= ICE_INSET_UDP_SRC_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_UDP_SRC_PORT : + ICE_INSET_UDP_SRC_PORT; if (udp_mask->hdr.dst_port == UINT16_MAX) - input_set |= ICE_INSET_UDP_DST_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_UDP_DST_PORT : + ICE_INSET_UDP_DST_PORT; /* Get filter info */ if (l3 == RTE_FLOW_ITEM_TYPE_IPV4) { @@ -1487,9 +1551,13 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, } if (sctp_mask->hdr.src_port == UINT16_MAX) - input_set |= ICE_INSET_SCTP_SRC_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_SCTP_SRC_PORT : + ICE_INSET_SCTP_SRC_PORT; if (sctp_mask->hdr.dst_port == UINT16_MAX) - input_set |= ICE_INSET_SCTP_DST_PORT; + input_set |= tunnel_type ? + ICE_INSET_TUN_SCTP_DST_PORT : + ICE_INSET_SCTP_DST_PORT; /* Get filter info */ if (l3 == RTE_FLOW_ITEM_TYPE_IPV4) { @@ -1511,6 +1579,21 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, break; case RTE_FLOW_ITEM_TYPE_VOID: break; + case RTE_FLOW_ITEM_TYPE_VXLAN: + l3 = RTE_FLOW_ITEM_TYPE_END; + vxlan_spec = item->spec; + vxlan_mask = item->mask; + + if (vxlan_spec || vxlan_mask) { + rte_flow_error_set(error, EINVAL, + RTE_FLOW_ERROR_TYPE_ITEM, + item, + "Invalid vxlan field"); + return -rte_errno; + } + + tunnel_type = ICE_FDIR_TUNNEL_TYPE_VXLAN; + break; default: rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_ITEM, @@ -1520,6 +1603,7 @@ ice_fdir_parse_pattern(__rte_unused struct ice_adapter *ad, } } + filter->tunnel_type = tunnel_type; filter->input.flow_type = flow_type; filter->input_set = input_set;