From patchwork Wed Apr 15 06:39:56 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Suanming Mou X-Patchwork-Id: 68479 X-Patchwork-Delegate: rasland@nvidia.com Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from dpdk.org (dpdk.org [92.243.14.124]) by inbox.dpdk.org (Postfix) with ESMTP id 4D188A0577; Wed, 15 Apr 2020 08:41:37 +0200 (CEST) Received: from [92.243.14.124] (localhost [127.0.0.1]) by dpdk.org (Postfix) with ESMTP id EE5C31D452; Wed, 15 Apr 2020 08:40:23 +0200 (CEST) Received: from git-send-mailer.rdmz.labs.mlnx (unknown [37.142.13.130]) by dpdk.org (Postfix) with ESMTP id 58D181C2FB for ; Wed, 15 Apr 2020 08:40:21 +0200 (CEST) From: Suanming Mou To: Matan Azrad , Shahaf Shuler , Viacheslav Ovsiienko Cc: wentaoc@mellanox.com, rasland@mellanox.com, dev@dpdk.org Date: Wed, 15 Apr 2020 14:39:56 +0800 Message-Id: <1586932797-99533-10-git-send-email-suanmingm@mellanox.com> X-Mailer: git-send-email 1.8.3.1 In-Reply-To: <1586932797-99533-1-git-send-email-suanmingm@mellanox.com> References: <1586932797-99533-1-git-send-email-suanmingm@mellanox.com> Subject: [dpdk-dev] [PATCH 09/10] net/mlx5: optimize flow director filter memory 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" From: Wentao Cui This commit is for mlx5 fdir flow memory optimization. Currently for the fdir member in rte_flow structure. It saves the fidr memory pointer directly. As fidr is fading away, use one bit help to indicate the function in the flow and add the content to an extra list save the memory for the other widely usage cases. Signed-off-by: Wentao Cui Signed-off-by: Suanming Mou --- drivers/net/mlx5/mlx5.h | 1 + drivers/net/mlx5/mlx5_flow.c | 62 ++++++++++++++++++++++++++++++++++++-------- drivers/net/mlx5/mlx5_flow.h | 9 ++++++- 3 files changed, 60 insertions(+), 12 deletions(-) diff --git a/drivers/net/mlx5/mlx5.h b/drivers/net/mlx5/mlx5.h index 1141935..41be692 100644 --- a/drivers/net/mlx5/mlx5.h +++ b/drivers/net/mlx5/mlx5.h @@ -600,6 +600,7 @@ struct mlx5_priv { #endif uint8_t skip_default_rss_reta; /* Skip configuration of default reta. */ uint8_t fdb_def_rule; /* Whether fdb jump to table 1 is configured. */ + LIST_HEAD(fdir, mlx5_fdir_flow) fdir_flows; /* fdir flows. */ }; #define PORT_ID(priv) ((priv)->dev_data->port_id) diff --git a/drivers/net/mlx5/mlx5_flow.c b/drivers/net/mlx5/mlx5_flow.c index 0d2e3df..007e5c4 100644 --- a/drivers/net/mlx5/mlx5_flow.c +++ b/drivers/net/mlx5/mlx5_flow.c @@ -4501,6 +4501,7 @@ struct rte_flow * struct rte_flow *flow) { struct mlx5_priv *priv = dev->data->dev_private; + struct mlx5_fdir_flow *priv_fdir_flow = NULL; /* * Update RX queue flags only if port is started, otherwise it is @@ -4515,7 +4516,17 @@ struct rte_flow * if (list) TAILQ_REMOVE(list, flow, next); flow_mreg_del_copy_action(dev, flow); - rte_free(flow->fdir); + if (flow->fdir) { + LIST_FOREACH(priv_fdir_flow, &priv->fdir_flows, next) { + if (priv_fdir_flow->flow == flow) + break; + } + if (priv_fdir_flow) { + LIST_REMOVE(priv_fdir_flow, next); + rte_free(priv_fdir_flow->flow); + rte_free(priv_fdir_flow); + } + } if (flow->idx) mlx5_ipool_free(priv->sh->ipool[MLX5_IPOOL_RTE_FLOW], flow->idx); @@ -5211,12 +5222,14 @@ struct rte_flow * { struct mlx5_priv *priv = dev->data->dev_private; struct rte_flow *flow = NULL; + struct mlx5_fdir_flow *priv_fdir_flow = NULL; MLX5_ASSERT(fdir_flow); - TAILQ_FOREACH(flow, &priv->flows, next) { - if (flow->fdir && !flow_fdir_cmp(flow->fdir, fdir_flow)) { + LIST_FOREACH(priv_fdir_flow, &priv->fdir_flows, next) { + if (!flow_fdir_cmp(priv_fdir_flow->fdir, fdir_flow)) { DRV_LOG(DEBUG, "port %u found FDIR flow %p", dev->data->port_id, (void *)flow); + flow = priv_fdir_flow->flow; break; } } @@ -5241,6 +5254,7 @@ struct rte_flow * struct mlx5_priv *priv = dev->data->dev_private; struct mlx5_fdir *fdir_flow; struct rte_flow *flow; + struct mlx5_fdir_flow *priv_fdir_flow = NULL; int ret; fdir_flow = rte_zmalloc(__func__, sizeof(*fdir_flow), 0); @@ -5256,17 +5270,26 @@ struct rte_flow * rte_errno = EEXIST; goto error; } + priv_fdir_flow = rte_zmalloc(__func__, sizeof(struct mlx5_fdir_flow), + 0); + if (!priv_fdir_flow) { + rte_errno = ENOMEM; + goto error; + } flow = flow_list_create(dev, &priv->flows, &fdir_flow->attr, fdir_flow->items, fdir_flow->actions, true, NULL); if (!flow) goto error; - MLX5_ASSERT(!flow->fdir); - flow->fdir = fdir_flow; + flow->fdir = 1; + priv_fdir_flow->fdir = fdir_flow; + priv_fdir_flow->flow = flow; + LIST_INSERT_HEAD(&priv->fdir_flows, priv_fdir_flow, next); DRV_LOG(DEBUG, "port %u created FDIR flow %p", dev->data->port_id, (void *)flow); return 0; error: + rte_free(priv_fdir_flow); rte_free(fdir_flow); return -rte_errno; } @@ -5291,17 +5314,26 @@ struct rte_flow * struct mlx5_fdir fdir_flow = { .attr.group = 0, }; + struct mlx5_fdir_flow *priv_fdir_flow = NULL; int ret; ret = flow_fdir_filter_convert(dev, fdir_filter, &fdir_flow); if (ret) return -rte_errno; - flow = flow_fdir_filter_lookup(dev, &fdir_flow); - if (!flow) { - rte_errno = ENOENT; - return -rte_errno; + LIST_FOREACH(priv_fdir_flow, &priv->fdir_flows, next) { + /* Find the fdir in priv list */ + if (!flow_fdir_cmp(priv_fdir_flow->fdir, &fdir_flow)) + break; } + if (!priv_fdir_flow) + return 0; + LIST_REMOVE(priv_fdir_flow, next); + flow = priv_fdir_flow->flow; + /* Fdir resource will be releasd after flow destroy. */ + flow->fdir = 0; flow_list_destroy(dev, &priv->flows, flow); + rte_free(priv_fdir_flow->fdir); + rte_free(priv_fdir_flow); DRV_LOG(DEBUG, "port %u deleted FDIR flow %p", dev->data->port_id, (void *)flow); return 0; @@ -5340,8 +5372,16 @@ struct rte_flow * flow_fdir_filter_flush(struct rte_eth_dev *dev) { struct mlx5_priv *priv = dev->data->dev_private; - - mlx5_flow_list_flush(dev, &priv->flows, false); + struct mlx5_fdir_flow *priv_fdir_flow = NULL; + + while (!LIST_EMPTY(&priv->fdir_flows)) { + priv_fdir_flow = LIST_FIRST(&priv->fdir_flows); + LIST_REMOVE(priv_fdir_flow, next); + priv_fdir_flow->flow->fdir = 0; + flow_list_destroy(dev, &priv->flows, priv_fdir_flow->flow); + rte_free(priv_fdir_flow->fdir); + rte_free(priv_fdir_flow); + } } /** diff --git a/drivers/net/mlx5/mlx5_flow.h b/drivers/net/mlx5/mlx5_flow.h index 7611410..911007b 100644 --- a/drivers/net/mlx5/mlx5_flow.h +++ b/drivers/net/mlx5/mlx5_flow.h @@ -753,6 +753,13 @@ struct mlx5_flow_meter_profile { uint32_t ref_cnt; /**< Use count. */ }; +/* Fdir flow struture */ +struct mlx5_fdir_flow { + LIST_ENTRY(mlx5_fdir_flow) next; /* Pointer to the next element. */ + struct mlx5_fdir *fdir; /* Pointer to fdir. */ + struct rte_flow *flow; /* Pointer to flow. */ +}; + /* Flow structure. */ struct rte_flow { TAILQ_ENTRY(rte_flow) next; /**< Pointer to the next flow structure. */ @@ -764,7 +771,7 @@ struct rte_flow { uint16_t meter; /**< Holds flow meter id. */ uint32_t dev_handles; /**< Device flow handles that are part of the flow. */ - struct mlx5_fdir *fdir; /**< Pointer to associated FDIR if any. */ + uint32_t fdir:1; /**< Identifier of associated FDIR if any. */ uint32_t hairpin_flow_id; /**< The flow id used for hairpin. */ uint32_t copy_applied:1; /**< The MARK copy Flow os applied. */ uint32_t idx; /**< Index to the rte flow allocated from indexed pool. */