patches for DPDK stable branches
 help / color / mirror / Atom feed
From: "Guo, Jia" <jia.guo@intel.com>
To: "Di, ChenxuX" <chenxux.di@intel.com>, "dev@dpdk.org" <dev@dpdk.org>
Cc: "Xing, Beilei" <beilei.xing@intel.com>,
	"Wang, Haiyue" <haiyue.wang@intel.com>,
	"Di, ChenxuX" <chenxux.di@intel.com>,
	"stable@dpdk.org" <stable@dpdk.org>
Subject: Re: [dpdk-stable] [PATCH 2/2] net/i40e: fix incorrect FDIR flex pit
Date: Wed, 4 Nov 2020 09:18:49 +0000
Message-ID: <36fa7db4c27244ddb043fb7fd3e0f11a@intel.com> (raw)
In-Reply-To: <20201104082959.63800-3-chenxux.di@intel.com>

Hi, chenxu

> -----Original Message-----
> From: Chenxu Di <chenxux.di@intel.com>
> Sent: Wednesday, November 4, 2020 4:30 PM
> To: dev@dpdk.org
> Cc: Xing, Beilei <beilei.xing@intel.com>; Guo, Jia <jia.guo@intel.com>; Wang,
> Haiyue <haiyue.wang@intel.com>; Di, ChenxuX <chenxux.di@intel.com>;
> stable@dpdk.org
> Subject: [PATCH 2/2] net/i40e: fix incorrect FDIR flex pit
> 
> The register of FDIR flex pit should not be set during flow validate.
> It should be set when flow create.
> 
> Fixes: 6ced3dd72f5f ("net/i40e: support flexible payload parsing for FDIR")
> Cc: stable@dpdk.org
> 
> Signed-off-by: Chenxu Di <chenxux.di@intel.com>
> ---
>  drivers/net/i40e/i40e_ethdev.h |  21 ++++---
>  drivers/net/i40e/i40e_fdir.c   | 100
> +++++++++++++++++++++++++++++++++
>  drivers/net/i40e/i40e_flow.c   |  98 +++-----------------------------
>  3 files changed, 119 insertions(+), 100 deletions(-)
> 
> diff --git a/drivers/net/i40e/i40e_ethdev.h
> b/drivers/net/i40e/i40e_ethdev.h index 6be929f65..e00133c88 100644
> --- a/drivers/net/i40e/i40e_ethdev.h
> +++ b/drivers/net/i40e/i40e_ethdev.h
> @@ -599,12 +599,22 @@ enum i40e_fdir_ip_type {
>  	I40E_FDIR_IPTYPE_IPV6,
>  };
> 
> +/*
> + * Structure to store flex pit for flow diretor.
> + */
> +struct i40e_fdir_flex_pit {
> +	uint8_t src_offset; /* offset in words from the beginning of payload
> */
> +	uint8_t size;       /* size in words */
> +	uint8_t dst_offset; /* offset in words of flexible payload */ };
> +
>  /* A structure used to contain extend input of flow */  struct
> i40e_fdir_flow_ext {
>  	uint16_t vlan_tci;
>  	uint8_t flexbytes[RTE_ETH_FDIR_MAX_FLEXLEN];
>  	/* It is filled by the flexible payload to match. */
>  	uint8_t flex_mask[I40E_FDIR_MAX_FLEX_LEN];
> +	uint8_t raw_id;
>  	uint8_t is_vf;   /* 1 for VF, 0 for port dev */
>  	uint16_t dst_id; /* VF ID, available when is_vf is 1*/
>  	bool inner_ip;   /* If there is inner ip */
> @@ -613,6 +623,8 @@ struct i40e_fdir_flow_ext {
>  	bool customized_pctype; /* If customized pctype is used */
>  	bool pkt_template; /* If raw packet template is used */
>  	bool is_udp; /* ipv4|ipv6 udp flow */
> +	enum i40e_flxpld_layer_idx layer_idx;
> +	struct i40e_fdir_flex_pit flex_pit[I40E_MAX_FLXPLD_LAYER *
> +I40E_MAX_FLXPLD_FIED];
>  };
> 
>  /* A structure used to define the input for a flow director filter entry */ @@
> -664,15 +676,6 @@ struct i40e_fdir_filter_conf {
>  	struct i40e_fdir_action action;  /* Action taken when match */  };
> 
> -/*
> - * Structure to store flex pit for flow diretor.
> - */
> -struct i40e_fdir_flex_pit {
> -	uint8_t src_offset;    /* offset in words from the beginning of payload
> */
> -	uint8_t size;          /* size in words */
> -	uint8_t dst_offset;    /* offset in words of flexible payload */
> -};
> -
>  struct i40e_fdir_flex_mask {
>  	uint8_t word_mask;  /**< Bit i enables word i of flexible payload */
>  	uint8_t nb_bitmask;
> diff --git a/drivers/net/i40e/i40e_fdir.c b/drivers/net/i40e/i40e_fdir.c index
> e31464eb7..e64cb2fd0 100644
> --- a/drivers/net/i40e/i40e_fdir.c
> +++ b/drivers/net/i40e/i40e_fdir.c
> @@ -1765,6 +1765,81 @@ i40e_add_del_fdir_filter(struct rte_eth_dev *dev,
>  	return ret;
>  }
> 
> +static int
> +i40e_flow_store_flex_pit(struct i40e_pf *pf,
> +			 struct i40e_fdir_flex_pit *flex_pit,
> +			 enum i40e_flxpld_layer_idx layer_idx,
> +			 uint8_t raw_id)
> +{
> +	uint8_t field_idx;
> +
> +	field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + raw_id;
> +	/* Check if the configuration is conflicted */
> +	if (pf->fdir.flex_pit_flag[layer_idx] &&
> +	    (pf->fdir.flex_set[field_idx].src_offset != flex_pit->src_offset ||
> +	     pf->fdir.flex_set[field_idx].size != flex_pit->size ||
> +	     pf->fdir.flex_set[field_idx].dst_offset != flex_pit->dst_offset))
> +		return -1;
> +
> +	/* Check if the configuration exists. */
> +	if (pf->fdir.flex_pit_flag[layer_idx] &&
> +	    (pf->fdir.flex_set[field_idx].src_offset == flex_pit->src_offset &&
> +	     pf->fdir.flex_set[field_idx].size == flex_pit->size &&
> +	     pf->fdir.flex_set[field_idx].dst_offset == flex_pit->dst_offset))
> +		return 1;
> +
> +	pf->fdir.flex_set[field_idx].src_offset =
> +		flex_pit->src_offset;
> +	pf->fdir.flex_set[field_idx].size =
> +		flex_pit->size;
> +	pf->fdir.flex_set[field_idx].dst_offset =
> +		flex_pit->dst_offset;
> +
> +	return 0;
> +}
> +
> +static void
> +i40e_flow_set_fdir_flex_pit(struct i40e_pf *pf,
> +			    enum i40e_flxpld_layer_idx layer_idx,
> +			    uint8_t raw_id)
> +{
> +	struct i40e_hw *hw = I40E_PF_TO_HW(pf);
> +	uint32_t flx_pit, flx_ort;
> +	uint8_t field_idx;
> +	uint16_t min_next_off = 0;  /* in words */
> +	uint8_t i;
> +
> +	if (raw_id) {
> +		flx_ort = (1 << I40E_GLQF_ORT_FLX_PAYLOAD_SHIFT) |
> +			  (raw_id << I40E_GLQF_ORT_FIELD_CNT_SHIFT) |
> +			  (layer_idx * I40E_MAX_FLXPLD_FIED);
> +		I40E_WRITE_GLB_REG(hw, I40E_GLQF_ORT(33 + layer_idx),
> flx_ort);
> +	}
> +
> +	/* Set flex pit */
> +	for (i = 0; i < raw_id; i++) {
> +		field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + i;
> +		flx_pit = MK_FLX_PIT(pf->fdir.flex_set[field_idx].src_offset,
> +				     pf->fdir.flex_set[field_idx].size,
> +				     pf->fdir.flex_set[field_idx].dst_offset);
> +
> +		I40E_WRITE_REG(hw, I40E_PRTQF_FLX_PIT(field_idx),
> flx_pit);
> +		min_next_off = pf->fdir.flex_set[field_idx].src_offset +
> +			pf->fdir.flex_set[field_idx].size;
> +	}
> +
> +	for (; i < I40E_MAX_FLXPLD_FIED; i++) {
> +		/* set the non-used register obeying register's constrain */
> +		field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + i;
> +		flx_pit = MK_FLX_PIT(min_next_off,
> NONUSE_FLX_PIT_FSIZE,
> +				     NONUSE_FLX_PIT_DEST_OFF);
> +		I40E_WRITE_REG(hw, I40E_PRTQF_FLX_PIT(field_idx),
> flx_pit);
> +		min_next_off++;
> +	}
> +
> +	pf->fdir.flex_pit_flag[layer_idx] = 1; }
> +
>  static int
>  i40e_flow_store_flex_mask(struct i40e_pf *pf,
>  			  enum i40e_filter_pctype pctype,
> @@ -1889,13 +1964,17 @@ i40e_flow_add_del_fdir_filter(struct
> rte_eth_dev *dev,  {
>  	struct i40e_hw *hw = I40E_DEV_PRIVATE_TO_HW(dev->data-
> >dev_private);
>  	struct i40e_pf *pf = I40E_DEV_PRIVATE_TO_PF(dev->data-
> >dev_private);
> +	enum i40e_flxpld_layer_idx layer_idx = I40E_FLXPLD_L2_IDX;
>  	unsigned char *pkt = NULL;
>  	enum i40e_filter_pctype pctype;
>  	struct i40e_fdir_info *fdir_info = &pf->fdir;
>  	uint8_t flex_mask[I40E_FDIR_MAX_FLEX_LEN];
>  	struct i40e_fdir_filter *node;
>  	struct i40e_fdir_filter check_filter; /* Check if the filter exists */
> +	struct i40e_fdir_flex_pit flex_pit;
> +	bool cfg_flex_pit = true;
>  	bool wait_status = true;
> +	uint8_t field_idx;
>  	int ret = 0;
>  	int i;
> 
> @@ -1931,6 +2010,27 @@ i40e_flow_add_del_fdir_filter(struct rte_eth_dev
> *dev,
> 
>  	if (add) {
>  		if (!filter->input.flow_ext.customized_pctype) {
> +			for (i = 0; i < filter->input.flow_ext.raw_id; i++) {
> +				layer_idx = filter->input.flow_ext.layer_idx;
> +				field_idx = layer_idx *
> I40E_MAX_FLXPLD_FIED + i;
> +				flex_pit = filter-
> >input.flow_ext.flex_pit[field_idx];
> +
> +				/* Store flex pit to SW */
> +				ret = i40e_flow_store_flex_pit(pf, &flex_pit,
> +							       layer_idx, i);
> +				if (ret < 0) {
> +					PMD_DRV_LOG(ERR, "Conflict with
> the"
> +						    " first flexible rule.");
> +					return -EINVAL;
> +				} else if (ret > 0) {
> +					cfg_flex_pit = false;
> +				}
> +			}
> +
> +			if (cfg_flex_pit)
> +				i40e_flow_set_fdir_flex_pit(pf, layer_idx,
> +						filter-
> >input.flow_ext.raw_id);
> +
>  			/* Store flex mask to SW */
>  			for (i = 0; i < I40E_FDIR_MAX_FLEX_LEN; i++)
>  				flex_mask[i] =
> diff --git a/drivers/net/i40e/i40e_flow.c b/drivers/net/i40e/i40e_flow.c
> index 4f916494e..098ae13ab 100644
> --- a/drivers/net/i40e/i40e_flow.c
> +++ b/drivers/net/i40e/i40e_flow.c
> @@ -2240,81 +2240,6 @@ i40e_flow_check_raw_item(const struct
> rte_flow_item *item,
>  	return 0;
>  }
> 
> -static int
> -i40e_flow_store_flex_pit(struct i40e_pf *pf,
> -			 struct i40e_fdir_flex_pit *flex_pit,
> -			 enum i40e_flxpld_layer_idx layer_idx,
> -			 uint8_t raw_id)
> -{
> -	uint8_t field_idx;
> -
> -	field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + raw_id;
> -	/* Check if the configuration is conflicted */
> -	if (pf->fdir.flex_pit_flag[layer_idx] &&
> -	    (pf->fdir.flex_set[field_idx].src_offset != flex_pit->src_offset ||
> -	     pf->fdir.flex_set[field_idx].size != flex_pit->size ||
> -	     pf->fdir.flex_set[field_idx].dst_offset != flex_pit->dst_offset))
> -		return -1;
> -
> -	/* Check if the configuration exists. */
> -	if (pf->fdir.flex_pit_flag[layer_idx] &&
> -	    (pf->fdir.flex_set[field_idx].src_offset == flex_pit->src_offset &&
> -	     pf->fdir.flex_set[field_idx].size == flex_pit->size &&
> -	     pf->fdir.flex_set[field_idx].dst_offset == flex_pit->dst_offset))
> -		return 1;
> -
> -	pf->fdir.flex_set[field_idx].src_offset =
> -		flex_pit->src_offset;
> -	pf->fdir.flex_set[field_idx].size =
> -		flex_pit->size;
> -	pf->fdir.flex_set[field_idx].dst_offset =
> -		flex_pit->dst_offset;
> -
> -	return 0;
> -}
> -
> -static void
> -i40e_flow_set_fdir_flex_pit(struct i40e_pf *pf,
> -			    enum i40e_flxpld_layer_idx layer_idx,
> -			    uint8_t raw_id)
> -{
> -	struct i40e_hw *hw = I40E_PF_TO_HW(pf);
> -	uint32_t flx_pit, flx_ort;
> -	uint8_t field_idx;
> -	uint16_t min_next_off = 0;  /* in words */
> -	uint8_t i;
> -
> -	if (raw_id) {
> -		flx_ort = (1 << I40E_GLQF_ORT_FLX_PAYLOAD_SHIFT) |
> -			  (raw_id << I40E_GLQF_ORT_FIELD_CNT_SHIFT) |
> -			  (layer_idx * I40E_MAX_FLXPLD_FIED);
> -		I40E_WRITE_GLB_REG(hw, I40E_GLQF_ORT(33 + layer_idx),
> flx_ort);
> -	}
> -
> -	/* Set flex pit */
> -	for (i = 0; i < raw_id; i++) {
> -		field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + i;
> -		flx_pit = MK_FLX_PIT(pf->fdir.flex_set[field_idx].src_offset,
> -				     pf->fdir.flex_set[field_idx].size,
> -				     pf->fdir.flex_set[field_idx].dst_offset);
> -
> -		I40E_WRITE_REG(hw, I40E_PRTQF_FLX_PIT(field_idx),
> flx_pit);
> -		min_next_off = pf->fdir.flex_set[field_idx].src_offset +
> -			pf->fdir.flex_set[field_idx].size;
> -	}
> -
> -	for (; i < I40E_MAX_FLXPLD_FIED; i++) {
> -		/* set the non-used register obeying register's constrain */
> -		field_idx = layer_idx * I40E_MAX_FLXPLD_FIED + i;
> -		flx_pit = MK_FLX_PIT(min_next_off,
> NONUSE_FLX_PIT_FSIZE,
> -				     NONUSE_FLX_PIT_DEST_OFF);
> -		I40E_WRITE_REG(hw, I40E_PRTQF_FLX_PIT(field_idx),
> flx_pit);
> -		min_next_off++;
> -	}
> -
> -	pf->fdir.flex_pit_flag[layer_idx] = 1;
> -}
> -
>  static int
>  i40e_flow_set_fdir_inset(struct i40e_pf *pf,
>  			 enum i40e_filter_pctype pctype,
> @@ -2534,10 +2459,10 @@ i40e_flow_parse_fdir_pattern(struct
> rte_eth_dev *dev,
>  	struct i40e_fdir_flex_pit flex_pit;
>  	uint8_t next_dst_off = 0;
>  	uint16_t flex_size;
> -	bool cfg_flex_pit = true;
>  	uint16_t ether_type;
>  	uint32_t vtc_flow_cpu;
>  	bool outer_ip = true;
> +	uint8_t field_idx;
>  	int ret;
> 
>  	memset(off_arr, 0, sizeof(off_arr));
> @@ -3089,6 +3014,7 @@ i40e_flow_parse_fdir_pattern(struct rte_eth_dev
> *dev,
> 
>  			flex_size = 0;
>  			memset(&flex_pit, 0, sizeof(struct
> i40e_fdir_flex_pit));
> +			field_idx = layer_idx * I40E_MAX_FLXPLD_FIED +
> raw_id;
>  			flex_pit.size =
>  				raw_spec->length / sizeof(uint16_t);
>  			flex_pit.dst_offset =
> @@ -3115,18 +3041,6 @@ i40e_flow_parse_fdir_pattern(struct rte_eth_dev
> *dev,
>  				return -rte_errno;
>  			}
> 
> -			/* Store flex pit to SW */
> -			ret = i40e_flow_store_flex_pit(pf, &flex_pit,
> -						       layer_idx, raw_id);
> -			if (ret < 0) {
> -				rte_flow_error_set(error, EINVAL,
> -				   RTE_FLOW_ERROR_TYPE_ITEM,
> -				   item,
> -				   "Conflict with the first flexible rule.");
> -				return -rte_errno;
> -			} else if (ret > 0)
> -				cfg_flex_pit = false;
> -
>  			for (i = 0; i < raw_spec->length; i++) {
>  				j = i + next_dst_off;
>  				filter->input.flow_ext.flexbytes[j] = @@ -
> 3137,6 +3051,11 @@ i40e_flow_parse_fdir_pattern(struct rte_eth_dev *dev,
> 
>  			next_dst_off += raw_spec->length;
>  			raw_id++;
> +
> +			memcpy(&filter->input.flow_ext.flex_pit[field_idx],
> +			       &flex_pit, sizeof(struct i40e_fdir_flex_pit));
> +			filter->input.flow_ext.layer_idx = layer_idx;
> +			filter->input.flow_ext.raw_id = raw_id;
>  			break;
>  		case RTE_FLOW_ITEM_TYPE_VF:
>  			vf_spec = item->spec;
> @@ -3222,9 +3141,6 @@ i40e_flow_parse_fdir_pattern(struct rte_eth_dev
> *dev,
>  					   "Invalid pattern mask.");
>  			return -rte_errno;
>  		}
> -
> -		if (cfg_flex_pit)
> -			i40e_flow_set_fdir_flex_pit(pf, layer_idx, raw_id);

Seems that multiple switch case set the layer_idx not only the place you delete, please double check if these case all need to handle.

>  	}
> 
>  	filter->input.pctype = pctype;
> --
> 2.17.1


  reply	other threads:[~2020-11-04  9:18 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <20201104082959.63800-1-chenxux.di@intel.com>
2020-11-04  8:29 ` [dpdk-stable] [PATCH 1/2] net/i40e: fix incorrect FDIR flex mask Chenxu Di
2020-11-04  9:40   ` Guo, Jia
2020-11-04  8:29 ` [dpdk-stable] [PATCH 2/2] net/i40e: fix incorrect FDIR flex pit Chenxu Di
2020-11-04  9:18   ` Guo, Jia [this message]
2020-11-06  6:47 ` [dpdk-stable] [PATCH v2] net/i40e: fix incorrect FDIR flex configuration Chenxu Di
2020-11-09  3:23   ` [dpdk-stable] [dpdk-dev] " Zhou, JunX W
2020-11-10  5:42 ` [dpdk-stable] [PATCH v3] " Chenxu Di
2020-11-10  6:54   ` Guo, Jia
2020-11-10  7:08 ` [dpdk-stable] [PATCH v4] " Chenxu Di
2020-11-10  8:27   ` Zhang, Qi Z

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=36fa7db4c27244ddb043fb7fd3e0f11a@intel.com \
    --to=jia.guo@intel.com \
    --cc=beilei.xing@intel.com \
    --cc=chenxux.di@intel.com \
    --cc=dev@dpdk.org \
    --cc=haiyue.wang@intel.com \
    --cc=stable@dpdk.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

patches for DPDK stable branches

This inbox may be cloned and mirrored by anyone:

	git clone --mirror https://inbox.dpdk.org/stable/0 stable/git/0.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 stable stable/ https://inbox.dpdk.org/stable \
		stable@dpdk.org
	public-inbox-index stable

Example config snippet for mirrors.
Newsgroup available over NNTP:
	nntp://inbox.dpdk.org/inbox.dpdk.stable


AGPL code for this site: git clone https://public-inbox.org/public-inbox.git