DPDK patches and discussions
 help / color / mirror / Atom feed
* [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission
@ 2023-10-31 12:25 Gregory Etelson
  2023-10-31 12:25 ` [PATCH 01/10] net/mlx5/hws: check the rule status on rule update Gregory Etelson
                   ` (9 more replies)
  0 siblings, 10 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev; +Cc: getelson, mkashani, rasland, Alex Vesker, Matan Azrad

IPSEC reparse submission.

Alex Vesker (3):
  net/mlx5/hws: allow jump to TIR over FDB
  net/mlx5/hws: support dynamic re-parse
  net/mlx5/hws: dynamic re-parse for modify header

Hamdan Igbaria (6):
  net/mlx5/hws: support IPsec encryption/decryption action
  net/mlx5/hws: support ASO IPsec action
  net/mlx5/hws: support reformat trailer action
  net/mlx5/hws: support ASO first hit action
  net/mlx5/hws: support insert header action
  net/mlx5/hws: support remove header action

Itamar Gozlan (1):
  net/mlx5/hws: check the rule status on rule update

 drivers/common/mlx5/mlx5_prm.h         |  41 +-
 drivers/net/mlx5/hws/mlx5dr.h          | 198 ++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c   | 615 +++++++++++++++++++++++--
 drivers/net/mlx5/hws/mlx5dr_action.h   |  64 ++-
 drivers/net/mlx5/hws/mlx5dr_cmd.c      |  27 +-
 drivers/net/mlx5/hws/mlx5dr_cmd.h      |  10 +-
 drivers/net/mlx5/hws/mlx5dr_context.c  |  15 +
 drivers/net/mlx5/hws/mlx5dr_context.h  |   9 +-
 drivers/net/mlx5/hws/mlx5dr_debug.c    |   7 +
 drivers/net/mlx5/hws/mlx5dr_internal.h |   1 +
 drivers/net/mlx5/hws/mlx5dr_matcher.c  |   7 +
 drivers/net/mlx5/hws/mlx5dr_pat_arg.c  |  41 +-
 drivers/net/mlx5/hws/mlx5dr_pat_arg.h  |   2 +
 drivers/net/mlx5/hws/mlx5dr_rule.c     |   6 +
 14 files changed, 973 insertions(+), 70 deletions(-)

Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>

-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 01/10] net/mlx5/hws: check the rule status on rule update
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 02/10] net/mlx5/hws: support IPsec encryption/decryption action Gregory Etelson
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Itamar Gozlan, Hamdan Igbaria,
	Alex Vesker, Matan Azrad, Viacheslav Ovsiienko, Ori Kam,
	Suanming Mou

From: Itamar Gozlan <igozlan@nvidia.com>

Only allow rule updates for rules with their status value equal to
MLX5DR_RULE_STATUS_CREATED.
Otherwise, the rule may be in an unstable stage like deleting and
this will result in a faulty unexpected scenario.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/net/mlx5/hws/mlx5dr_rule.c | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/drivers/net/mlx5/hws/mlx5dr_rule.c b/drivers/net/mlx5/hws/mlx5dr_rule.c
index 980a99b226..70d5c19e1f 100644
--- a/drivers/net/mlx5/hws/mlx5dr_rule.c
+++ b/drivers/net/mlx5/hws/mlx5dr_rule.c
@@ -756,6 +756,12 @@ int mlx5dr_rule_action_update(struct mlx5dr_rule *rule_handle,
 	if (mlx5dr_rule_enqueue_precheck(matcher->tbl->ctx, attr))
 		return -rte_errno;
 
+	if (rule_handle->status != MLX5DR_RULE_STATUS_CREATED) {
+		DR_LOG(ERR, "Current rule status does not allow update");
+		rte_errno = EBUSY;
+		return -rte_errno;
+	}
+
 	ret = mlx5dr_rule_create_hws(rule_handle,
 				     attr,
 				     0,
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 02/10] net/mlx5/hws: support IPsec encryption/decryption action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
  2023-10-31 12:25 ` [PATCH 01/10] net/mlx5/hws: check the rule status on rule update Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 03/10] net/mlx5/hws: support ASO IPsec action Gregory Etelson
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support crypto action creation, this action allows encryption/decryption
of the packet according a specific security crypto protocol.
For now we support encryption/decryption according ipsec protocol.
ipsec encryption handles the encoding of the data.
ipsec decryption handles the decoding of the data and a decryption result
status will be placed in the ipsec_syndrome field.
Both operations should be used only for packets that have esp header and
ipsec trailer.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h        |  12 ++
 drivers/net/mlx5/hws/mlx5dr.h         |  42 +++++++
 drivers/net/mlx5/hws/mlx5dr_action.c  | 172 +++++++++++++++++++++++++-
 drivers/net/mlx5/hws/mlx5dr_action.h  |  44 ++++---
 drivers/net/mlx5/hws/mlx5dr_cmd.c     |   8 ++
 drivers/net/mlx5/hws/mlx5dr_cmd.h     |   2 +-
 drivers/net/mlx5/hws/mlx5dr_debug.c   |   2 +
 drivers/net/mlx5/hws/mlx5dr_matcher.c |   5 +
 8 files changed, 266 insertions(+), 21 deletions(-)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index 2b499666f8..0eecf0691b 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -3498,6 +3498,8 @@ enum mlx5_ifc_stc_action_type {
 	MLX5_IFC_STC_ACTION_TYPE_HEADER_INSERT = 0x0b,
 	MLX5_IFC_STC_ACTION_TYPE_TAG = 0x0c,
 	MLX5_IFC_STC_ACTION_TYPE_ACC_MODIFY_LIST = 0x0e,
+	MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION = 0x10,
+	MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION = 0x11,
 	MLX5_IFC_STC_ACTION_TYPE_ASO = 0x12,
 	MLX5_IFC_STC_ACTION_TYPE_COUNTER = 0x14,
 	MLX5_IFC_STC_ACTION_TYPE_ADD_FIELD = 0x1b,
@@ -3546,6 +3548,14 @@ struct mlx5_ifc_stc_ste_param_execute_aso_bits {
 	u8 reserved_at_28[0x18];
 };
 
+struct mlx5_ifc_stc_ste_param_ipsec_encrypt_bits {
+	u8 ipsec_object_id[0x20];
+};
+
+struct mlx5_ifc_stc_ste_param_ipsec_decrypt_bits {
+	u8 ipsec_object_id[0x20];
+};
+
 struct mlx5_ifc_stc_ste_param_header_modify_list_bits {
 	u8 header_modify_pattern_id[0x20];
 	u8 header_modify_argument_id[0x20];
@@ -3612,6 +3622,8 @@ union mlx5_ifc_stc_param_bits {
 	struct mlx5_ifc_set_action_in_bits set;
 	struct mlx5_ifc_copy_action_in_bits copy;
 	struct mlx5_ifc_stc_ste_param_vport_bits vport;
+	struct mlx5_ifc_stc_ste_param_ipsec_encrypt_bits ipsec_encrypt;
+	struct mlx5_ifc_stc_ste_param_ipsec_decrypt_bits ipsec_decrypt;
 	u8 reserved_at_0[0x80];
 };
 
diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index 39d902e762..74d05229c7 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -45,6 +45,8 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_PUSH_VLAN,
 	MLX5DR_ACTION_TYP_ASO_METER,
 	MLX5DR_ACTION_TYP_ASO_CT,
+	MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT,
+	MLX5DR_ACTION_TYP_CRYPTO_DECRYPT,
 	MLX5DR_ACTION_TYP_DEST_ROOT,
 	MLX5DR_ACTION_TYP_DEST_ARRAY,
 	MLX5DR_ACTION_TYP_MAX,
@@ -176,6 +178,22 @@ struct mlx5dr_action_mh_pattern {
 	__be64 *data;
 };
 
+enum mlx5dr_action_crypto_op {
+	MLX5DR_ACTION_CRYPTO_OP_NONE,
+	MLX5DR_ACTION_CRYPTO_OP_ENCRYPT,
+	MLX5DR_ACTION_CRYPTO_OP_DECRYPT,
+};
+
+enum mlx5dr_action_crypto_type {
+	MLX5DR_ACTION_CRYPTO_TYPE_NISP,
+	MLX5DR_ACTION_CRYPTO_TYPE_IPSEC,
+};
+
+struct mlx5dr_action_crypto_attr {
+	enum mlx5dr_action_crypto_type crypto_type;
+	enum mlx5dr_action_crypto_op op;
+};
+
 /* In actions that take offset, the offset is unique, pointing to a single
  * resource and the user should not reuse the same index because data changing
  * is not atomic.
@@ -216,6 +234,10 @@ struct mlx5dr_rule_action {
 			uint32_t offset;
 			enum mlx5dr_action_aso_ct_flags direction;
 		} aso_ct;
+
+		struct {
+			uint32_t offset;
+		} crypto;
 	};
 };
 
@@ -691,6 +713,26 @@ mlx5dr_action_create_dest_root(struct mlx5dr_context *ctx,
 				uint16_t priority,
 				uint32_t flags);
 
+/* Create crypto action, this action will create specific security protocol
+ * encryption/decryption, for now we only support IPSec protocol.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] devx_obj
+ *	The SADB corresponding devx obj
+ * @param[in] attr
+ *	attributes: specifies if to encrypt/decrypt,
+ *	also specifies the crypto security protocol.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_crypto(struct mlx5dr_context *ctx,
+			    struct mlx5dr_devx_obj *devx_obj,
+			    struct mlx5dr_action_crypto_attr *attr,
+			    uint32_t flags);
+
 /* Destroy direct rule action.
  *
  * @param[in] action
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 11a7c58925..4910b4f730 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -9,11 +9,12 @@
 #define MLX5DR_ACTION_METER_INIT_COLOR_OFFSET 1
 
 /* This is the maximum allowed action order for each table type:
- *	 TX: POP_VLAN, CTR, ASO_METER, AS_CT, PUSH_VLAN, MODIFY, ENCAP, Term
- *	 RX: TAG, DECAP, POP_VLAN, CTR, ASO_METER, ASO_CT, PUSH_VLAN, MODIFY,
- *	     ENCAP, Term
- *	FDB: DECAP, POP_VLAN, CTR, ASO_METER, ASO_CT, PUSH_VLAN, MODIFY,
- *	     ENCAP, Term
+ *	 TX: POP_VLAN, CTR, ASO_METER, AS_CT, PUSH_VLAN, MODIFY, ENCAP, ENCRYPT,
+ *	     Term
+ *	 RX: TAG, DECAP, POP_VLAN, CTR, DECRYPT, ASO_METER, ASO_CT, PUSH_VLAN,
+ *	     MODIFY, ENCAP, Term
+ *	FDB: DECAP, POP_VLAN, CTR, DECRYPT, ASO_METER, ASO_CT, PUSH_VLAN, MODIFY,
+ *	     ENCAP, ENCRYPT, Term
  */
 static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_MAX] = {
 	[MLX5DR_TABLE_TYPE_NIC_RX] = {
@@ -23,6 +24,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
 		BIT(MLX5DR_ACTION_TYP_CTR),
+		BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT),
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
@@ -49,6 +51,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
+		BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT),
 		BIT(MLX5DR_ACTION_TYP_TBL) |
 		BIT(MLX5DR_ACTION_TYP_MISS) |
 		BIT(MLX5DR_ACTION_TYP_DROP) |
@@ -61,6 +64,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
 		BIT(MLX5DR_ACTION_TYP_CTR),
+		BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT),
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
@@ -68,6 +72,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
+		BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT),
 		BIT(MLX5DR_ACTION_TYP_TBL) |
 		BIT(MLX5DR_ACTION_TYP_MISS) |
 		BIT(MLX5DR_ACTION_TYP_VPORT) |
@@ -266,6 +271,41 @@ bool mlx5dr_action_check_combo(enum mlx5dr_action_type *user_actions,
 	return valid_combo;
 }
 
+bool mlx5dr_action_check_restrictions(struct mlx5dr_matcher *matcher,
+				      enum mlx5dr_action_type *actions)
+{
+	uint32_t restricted_bits;
+	uint8_t idx = 0;
+
+	/* Check for restricted actions, these actions are restricted
+	 * to RX or TX only in FDB domain.
+	 * if one of these actions presented require correct optimize_flow_src.
+	 */
+	if (matcher->tbl->type != MLX5DR_TABLE_TYPE_FDB)
+		return false;
+
+	switch (matcher->attr.optimize_flow_src) {
+	case MLX5DR_MATCHER_FLOW_SRC_WIRE:
+		restricted_bits = BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT);
+		break;
+	case MLX5DR_MATCHER_FLOW_SRC_VPORT:
+		restricted_bits = BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT);
+		break;
+	default:
+		restricted_bits = BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT) |
+				  BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT);
+	}
+
+	while (actions[idx] != MLX5DR_ACTION_TYP_LAST) {
+		if (BIT(actions[idx++]) & restricted_bits) {
+			DR_LOG(ERR, "Invalid actions combination containing restricted actions was provided");
+			return true;
+		}
+	}
+
+	return false;
+}
+
 int mlx5dr_action_root_build_attr(struct mlx5dr_rule_action rule_actions[],
 				  uint32_t num_actions,
 				  struct mlx5dv_flow_action_attr *attr)
@@ -383,6 +423,24 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		use_fixup = true;
 		break;
 
+	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION:
+		if (fw_tbl_type == FS_FT_FDB_RX) {
+			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
+			fixup_stc_attr->action_offset = stc_attr->action_offset;
+			fixup_stc_attr->stc_offset = stc_attr->stc_offset;
+			use_fixup = true;
+		}
+		break;
+
+	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION:
+		if (fw_tbl_type == FS_FT_FDB_TX) {
+			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
+			fixup_stc_attr->action_offset = stc_attr->action_offset;
+			fixup_stc_attr->stc_offset = stc_attr->stc_offset;
+			use_fixup = true;
+		}
+		break;
+
 	default:
 		break;
 	}
@@ -605,6 +663,16 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->insert_header.insert_offset = MLX5DR_ACTION_HDR_LEN_L2_MACS;
 		attr->insert_header.header_size = MLX5DR_ACTION_HDR_LEN_L2_VLAN;
 		break;
+	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
+		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION;
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->id = obj->id;
+		break;
+	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
+		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION;
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->id = obj->id;
+		break;
 	default:
 		DR_LOG(ERR, "Invalid action type %d", action->type);
 		assert(false);
@@ -1943,6 +2011,55 @@ mlx5dr_action_create_dest_root(struct mlx5dr_context *ctx,
 	return NULL;
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_crypto(struct mlx5dr_context *ctx,
+			    struct mlx5dr_devx_obj *devx_obj,
+			    struct mlx5dr_action_crypto_attr *attr,
+			    uint32_t flags)
+{
+	enum mlx5dr_action_type action_type;
+	struct mlx5dr_action *action;
+
+	if (mlx5dr_action_is_root_flags(flags)) {
+		DR_LOG(ERR, "Action flags must be only non root (HWS)");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (attr->crypto_type != MLX5DR_ACTION_CRYPTO_TYPE_IPSEC) {
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (attr->op == MLX5DR_ACTION_CRYPTO_OP_ENCRYPT) {
+		if (flags & MLX5DR_ACTION_FLAG_HWS_RX) {
+			rte_errno = EINVAL;
+			return NULL;
+		}
+		action_type = MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT;
+	} else if (attr->op == MLX5DR_ACTION_CRYPTO_OP_DECRYPT) {
+		if (flags & MLX5DR_ACTION_FLAG_HWS_TX) {
+			rte_errno = EINVAL;
+			return NULL;
+		}
+		action_type = MLX5DR_ACTION_TYP_CRYPTO_DECRYPT;
+	} else {
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	action = mlx5dr_action_create_generic(ctx, flags, action_type);
+	if (!action)
+		return NULL;
+
+	if (mlx5dr_action_create_stcs(action, devx_obj)) {
+		simple_free(action);
+		return NULL;
+	}
+
+	return action;
+}
+
 static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 {
 	struct mlx5dr_devx_obj *obj = NULL;
@@ -1963,6 +2080,8 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 	case MLX5DR_ACTION_TYP_ASO_METER:
 	case MLX5DR_ACTION_TYP_ASO_CT:
 	case MLX5DR_ACTION_TYP_PUSH_VLAN:
+	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
+	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
 		mlx5dr_action_destroy_stcs(action);
 		break;
 	case MLX5DR_ACTION_TYP_DEST_ROOT:
@@ -2460,6 +2579,33 @@ mlx5dr_action_setter_common_decap(struct mlx5dr_actions_apply_data *apply,
 							    MLX5DR_CONTEXT_SHARED_STC_DECAP));
 }
 
+static void
+mlx5dr_action_setter_crypto_encryption(struct mlx5dr_actions_apply_data *apply,
+				       struct mlx5dr_actions_wqe_setter *setter)
+{
+	struct mlx5dr_rule_action *rule_action;
+
+	rule_action = &apply->rule_action[setter->idx_single];
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = htobe32(rule_action->crypto.offset);
+	mlx5dr_action_apply_stc(apply, MLX5DR_ACTION_STC_IDX_DW5, setter->idx_single);
+}
+
+static void
+mlx5dr_action_setter_crypto_decryption(struct mlx5dr_actions_apply_data *apply,
+				       struct mlx5dr_actions_wqe_setter *setter)
+{
+	struct mlx5dr_rule_action *rule_action;
+
+	rule_action = &apply->rule_action[setter->idx_triple];
+
+	mlx5dr_action_apply_stc(apply, MLX5DR_ACTION_STC_IDX_DW5, setter->idx_triple);
+	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW6] = 0;
+	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW7] = 0;
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = htobe32(rule_action->crypto.offset);
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW6] = 0;
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW7] = 0;
+}
+
 int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 {
 	struct mlx5dr_actions_wqe_setter *start_setter = at->setters + 1;
@@ -2594,6 +2740,22 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 			setter->idx_ctr = i;
 			break;
 
+		case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
+			/* Single encryption action, consume triple due to HW limitations */
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_TRIPLE);
+			setter->flags |= ASF_TRIPLE;
+			setter->set_single = &mlx5dr_action_setter_crypto_encryption;
+			setter->idx_single = i;
+			break;
+
+		case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
+			/* Triple decryption action */
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_TRIPLE);
+			setter->flags |= ASF_TRIPLE;
+			setter->set_triple = &mlx5dr_action_setter_crypto_decryption;
+			setter->idx_triple = i;
+			break;
+
 		default:
 			DR_LOG(ERR, "Unsupported action type: %d", action_type[i]);
 			rte_errno = ENOTSUP;
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index 582a38bebc..6bfa0bcc4a 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -21,6 +21,8 @@ enum mlx5dr_action_stc_idx {
 	MLX5DR_ACTION_STC_IDX_LAST_COMBO1 = 3,
 	/* STC combo2: CTR, 3 x SINGLE, Hit */
 	MLX5DR_ACTION_STC_IDX_LAST_COMBO2 = 4,
+	/* STC combo2: CTR, TRIPLE, Hit */
+	MLX5DR_ACTION_STC_IDX_LAST_COMBO3 = 2,
 };
 
 enum mlx5dr_action_offset {
@@ -52,6 +54,7 @@ enum mlx5dr_action_setter_flag {
 	ASF_SINGLE2 = 1 << 1,
 	ASF_SINGLE3 = 1 << 2,
 	ASF_DOUBLE = ASF_SINGLE2 | ASF_SINGLE3,
+	ASF_TRIPLE = ASF_SINGLE1 | ASF_DOUBLE,
 	ASF_REPARSE = 1 << 3,
 	ASF_REMOVE = 1 << 4,
 	ASF_MODIFY = 1 << 5,
@@ -94,10 +97,12 @@ typedef void (*mlx5dr_action_setter_fp)
 struct mlx5dr_actions_wqe_setter {
 	mlx5dr_action_setter_fp set_single;
 	mlx5dr_action_setter_fp set_double;
+	mlx5dr_action_setter_fp set_triple;
 	mlx5dr_action_setter_fp set_hit;
 	mlx5dr_action_setter_fp set_ctr;
 	uint8_t idx_single;
 	uint8_t idx_double;
+	uint8_t idx_triple;
 	uint8_t idx_ctr;
 	uint8_t idx_hit;
 	uint8_t flags;
@@ -183,6 +188,9 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at);
 bool mlx5dr_action_check_combo(enum mlx5dr_action_type *user_actions,
 			       enum mlx5dr_table_type table_type);
 
+bool mlx5dr_action_check_restrictions(struct mlx5dr_matcher *matcher,
+				      enum mlx5dr_action_type *actions);
+
 int mlx5dr_action_alloc_single_stc(struct mlx5dr_context *ctx,
 				   struct mlx5dr_cmd_stc_modify_attr *stc_attr,
 				   uint32_t table_type,
@@ -230,26 +238,32 @@ mlx5dr_action_apply_setter(struct mlx5dr_actions_apply_data *apply,
 	uint8_t num_of_actions;
 
 	/* Set control counter */
-	if (setter->flags & ASF_CTR)
+	if (setter->set_ctr)
 		setter->set_ctr(apply, setter);
 	else
 		mlx5dr_action_setter_default_ctr(apply, setter);
 
-	/* Set single and double on match */
 	if (!is_jumbo) {
-		if (setter->flags & ASF_SINGLE1)
-			setter->set_single(apply, setter);
-		else
-			mlx5dr_action_setter_default_single(apply, setter);
-
-		if (setter->flags & ASF_DOUBLE)
-			setter->set_double(apply, setter);
-		else
-			mlx5dr_action_setter_default_double(apply, setter);
-
-		num_of_actions = setter->flags & ASF_DOUBLE ?
-			MLX5DR_ACTION_STC_IDX_LAST_COMBO1 :
-			MLX5DR_ACTION_STC_IDX_LAST_COMBO2;
+		if (unlikely(setter->set_triple)) {
+			/* Set triple on match */
+			setter->set_triple(apply, setter);
+			num_of_actions = MLX5DR_ACTION_STC_IDX_LAST_COMBO3;
+		} else {
+			/* Set single and double on match */
+			if (setter->set_single)
+				setter->set_single(apply, setter);
+			else
+				mlx5dr_action_setter_default_single(apply, setter);
+
+			if (setter->set_double)
+				setter->set_double(apply, setter);
+			else
+				mlx5dr_action_setter_default_double(apply, setter);
+
+			num_of_actions = setter->set_double ?
+				MLX5DR_ACTION_STC_IDX_LAST_COMBO1 :
+				MLX5DR_ACTION_STC_IDX_LAST_COMBO2;
+		}
 	} else {
 		apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = 0;
 		apply->wqe_data[MLX5DR_ACTION_OFFSET_DW6] = 0;
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.c b/drivers/net/mlx5/hws/mlx5dr_cmd.c
index c52cdd0767..3b3690699d 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.c
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.c
@@ -541,6 +541,14 @@ mlx5dr_cmd_stc_modify_set_stc_param(struct mlx5dr_cmd_stc_modify_attr *stc_attr,
 		MLX5_SET(stc_ste_param_remove_words, stc_parm,
 			 remove_size, stc_attr->remove_words.num_of_words);
 		break;
+	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION:
+		MLX5_SET(stc_ste_param_ipsec_encrypt, stc_parm, ipsec_object_id,
+			 stc_attr->id);
+		break;
+	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION:
+		MLX5_SET(stc_ste_param_ipsec_decrypt, stc_parm, ipsec_object_id,
+			 stc_attr->id);
+		break;
 	default:
 		DR_LOG(ERR, "Not supported type %d", stc_attr->action_type);
 		rte_errno = EINVAL;
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.h b/drivers/net/mlx5/hws/mlx5dr_cmd.h
index 03db62e2e2..7bbb684dbd 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.h
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.h
@@ -100,7 +100,7 @@ struct mlx5dr_cmd_stc_modify_attr {
 	uint8_t action_offset;
 	enum mlx5_ifc_stc_action_type action_type;
 	union {
-		uint32_t id; /* TIRN, TAG, FT ID, STE ID */
+		uint32_t id; /* TIRN, TAG, FT ID, STE ID, CRYPTO */
 		struct {
 			uint8_t decap;
 			uint16_t start_anchor;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index e7b1f2cc32..8cf3909606 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -24,6 +24,8 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_ASO_CT] = "ASO_CT",
 	[MLX5DR_ACTION_TYP_DEST_ROOT] = "DEST_ROOT",
 	[MLX5DR_ACTION_TYP_DEST_ARRAY] = "DEST_ARRAY",
+	[MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT] = "CRYPTO_ENCRYPT",
+	[MLX5DR_ACTION_TYP_CRYPTO_DECRYPT] = "CRYPTO_DECRYPT",
 };
 
 static_assert(ARRAY_SIZE(mlx5dr_debug_action_type_str) == MLX5DR_ACTION_TYP_MAX,
diff --git a/drivers/net/mlx5/hws/mlx5dr_matcher.c b/drivers/net/mlx5/hws/mlx5dr_matcher.c
index a82c182460..6f74cf3677 100644
--- a/drivers/net/mlx5/hws/mlx5dr_matcher.c
+++ b/drivers/net/mlx5/hws/mlx5dr_matcher.c
@@ -714,6 +714,11 @@ static int mlx5dr_matcher_check_and_process_at(struct mlx5dr_matcher *matcher,
 		return rte_errno;
 	}
 
+	if (mlx5dr_action_check_restrictions(matcher, at->action_type_arr)) {
+		rte_errno = EINVAL;
+		return rte_errno;
+	}
+
 	/* Process action template to setters */
 	ret = mlx5dr_action_template_process(at);
 	if (ret) {
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 03/10] net/mlx5/hws: support ASO IPsec action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
  2023-10-31 12:25 ` [PATCH 01/10] net/mlx5/hws: check the rule status on rule update Gregory Etelson
  2023-10-31 12:25 ` [PATCH 02/10] net/mlx5/hws: support IPsec encryption/decryption action Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 04/10] net/mlx5/hws: support reformat trailer action Gregory Etelson
                   ` (6 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support ASO IPsec action, this action will allow performing
some of ipsec full offload operations, for example replay
protection and sequence number incrementation.
In Tx flow this action used before encrypting the packet to
increase the sequence number.
In Rx flow this action used after decrypting the packet to
check it against the replay protection window for validity.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h       |  1 +
 drivers/net/mlx5/hws/mlx5dr.h        | 23 ++++++++++++++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c | 32 +++++++++++++++++++++++++---
 drivers/net/mlx5/hws/mlx5dr_debug.c  |  1 +
 4 files changed, 54 insertions(+), 3 deletions(-)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index 0eecf0691b..31ebec7bcf 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -3539,6 +3539,7 @@ struct mlx5_ifc_stc_ste_param_flow_counter_bits {
 enum {
 	MLX5_ASO_CT_NUM_PER_OBJ = 1,
 	MLX5_ASO_METER_NUM_PER_OBJ = 2,
+	MLX5_ASO_IPSEC_NUM_PER_OBJ = 1,
 };
 
 struct mlx5_ifc_stc_ste_param_execute_aso_bits {
diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index 74d05229c7..bd352fa26d 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -45,6 +45,7 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_PUSH_VLAN,
 	MLX5DR_ACTION_TYP_ASO_METER,
 	MLX5DR_ACTION_TYP_ASO_CT,
+	MLX5DR_ACTION_TYP_ASO_IPSEC,
 	MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT,
 	MLX5DR_ACTION_TYP_CRYPTO_DECRYPT,
 	MLX5DR_ACTION_TYP_DEST_ROOT,
@@ -235,6 +236,10 @@ struct mlx5dr_rule_action {
 			enum mlx5dr_action_aso_ct_flags direction;
 		} aso_ct;
 
+		struct {
+			uint32_t offset;
+		} aso_ipsec;
+
 		struct {
 			uint32_t offset;
 		} crypto;
@@ -659,6 +664,24 @@ mlx5dr_action_create_aso_ct(struct mlx5dr_context *ctx,
 			    uint8_t return_reg_id,
 			    uint32_t flags);
 
+/* Create direct rule ASO IPSEC action.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] devx_obj
+ *	The DEVX ASO object.
+ * @param[in] return_reg_id
+ *	Copy the ASO object value into this reg_id, after a packet hits a rule with this ASO object.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_aso_ipsec(struct mlx5dr_context *ctx,
+			       struct mlx5dr_devx_obj *devx_obj,
+			       uint8_t return_reg_id,
+			       uint32_t flags);
+
 /* Create direct rule pop vlan action.
  * @param[in] ctx
  *	The context in which the new action will be created.
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 4910b4f730..956909a628 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -9,11 +9,11 @@
 #define MLX5DR_ACTION_METER_INIT_COLOR_OFFSET 1
 
 /* This is the maximum allowed action order for each table type:
- *	 TX: POP_VLAN, CTR, ASO_METER, AS_CT, PUSH_VLAN, MODIFY, ENCAP, ENCRYPT,
+ *	 TX: POP_VLAN, CTR, ASO, PUSH_VLAN, MODIFY, ENCAP, ENCRYPT,
  *	     Term
- *	 RX: TAG, DECAP, POP_VLAN, CTR, DECRYPT, ASO_METER, ASO_CT, PUSH_VLAN,
+ *	 RX: TAG, DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN,
  *	     MODIFY, ENCAP, Term
- *	FDB: DECAP, POP_VLAN, CTR, DECRYPT, ASO_METER, ASO_CT, PUSH_VLAN, MODIFY,
+ *	FDB: DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN, MODIFY,
  *	     ENCAP, ENCRYPT, Term
  */
 static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_MAX] = {
@@ -27,6 +27,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT),
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
+		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -46,6 +47,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_CTR),
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
+		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -67,6 +69,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT),
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
+		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -642,6 +645,13 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->aso.devx_obj_id = obj->id;
 		attr->aso.return_reg_id = action->aso.return_reg_id;
 		break;
+	case MLX5DR_ACTION_TYP_ASO_IPSEC:
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
+		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_ASO;
+		attr->aso.aso_type = ASO_OPC_MOD_IPSEC;
+		attr->aso.devx_obj_id = obj->id;
+		attr->aso.return_reg_id = action->aso.return_reg_id;
+		break;
 	case MLX5DR_ACTION_TYP_VPORT:
 		attr->action_offset = MLX5DR_ACTION_OFFSET_HIT;
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_VPORT;
@@ -1076,6 +1086,16 @@ mlx5dr_action_create_aso_ct(struct mlx5dr_context *ctx,
 					devx_obj, return_reg_id, flags);
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_aso_ipsec(struct mlx5dr_context *ctx,
+			       struct mlx5dr_devx_obj *devx_obj,
+			       uint8_t return_reg_id,
+			       uint32_t flags)
+{
+	return mlx5dr_action_create_aso(ctx, MLX5DR_ACTION_TYP_ASO_IPSEC,
+					devx_obj, return_reg_id, flags);
+}
+
 struct mlx5dr_action *
 mlx5dr_action_create_counter(struct mlx5dr_context *ctx,
 			     struct mlx5dr_devx_obj *obj,
@@ -2079,6 +2099,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 	case MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2:
 	case MLX5DR_ACTION_TYP_ASO_METER:
 	case MLX5DR_ACTION_TYP_ASO_CT:
+	case MLX5DR_ACTION_TYP_ASO_IPSEC:
 	case MLX5DR_ACTION_TYP_PUSH_VLAN:
 	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
 	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
@@ -2490,6 +2511,10 @@ mlx5dr_action_setter_aso(struct mlx5dr_actions_apply_data *apply,
 		offset = rule_action->aso_ct.offset / MLX5_ASO_CT_NUM_PER_OBJ;
 		exe_aso_ctrl = rule_action->aso_ct.direction;
 		break;
+	case MLX5DR_ACTION_TYP_ASO_IPSEC:
+		offset = rule_action->aso_ipsec.offset / MLX5_ASO_IPSEC_NUM_PER_OBJ;
+		exe_aso_ctrl = 0;
+		break;
 	default:
 		DR_LOG(ERR, "Unsupported ASO action type: %d", rule_action->action->type);
 		rte_errno = ENOTSUP;
@@ -2679,6 +2704,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 
 		case MLX5DR_ACTION_TYP_ASO_METER:
 		case MLX5DR_ACTION_TYP_ASO_CT:
+		case MLX5DR_ACTION_TYP_ASO_IPSEC:
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE);
 			setter->flags |= ASF_DOUBLE;
 			setter->set_double = &mlx5dr_action_setter_aso;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index 8cf3909606..74893f61fb 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -22,6 +22,7 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_PUSH_VLAN] = "PUSH_VLAN",
 	[MLX5DR_ACTION_TYP_ASO_METER] = "ASO_METER",
 	[MLX5DR_ACTION_TYP_ASO_CT] = "ASO_CT",
+	[MLX5DR_ACTION_TYP_ASO_IPSEC] = "ASO_IPSEC",
 	[MLX5DR_ACTION_TYP_DEST_ROOT] = "DEST_ROOT",
 	[MLX5DR_ACTION_TYP_DEST_ARRAY] = "DEST_ARRAY",
 	[MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT] = "CRYPTO_ENCRYPT",
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 04/10] net/mlx5/hws: support reformat trailer action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (2 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 03/10] net/mlx5/hws: support ASO IPsec action Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 05/10] net/mlx5/hws: support ASO first hit action Gregory Etelson
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support reformat trailer action, this action allows
to insert/remove specific crypto security protocol
trailer on the packet.
For now support IPsec crypto protocol trailer.
The trailer should be added before encrypting the
packet in Tx flow, and it can be removed after decryption
in Rx flow.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h       |  11 +++
 drivers/net/mlx5/hws/mlx5dr.h        |  32 ++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c | 114 ++++++++++++++++++++++++++-
 drivers/net/mlx5/hws/mlx5dr_action.h |   5 ++
 drivers/net/mlx5/hws/mlx5dr_cmd.c    |   8 ++
 drivers/net/mlx5/hws/mlx5dr_cmd.h    |   5 ++
 drivers/net/mlx5/hws/mlx5dr_debug.c  |   1 +
 7 files changed, 172 insertions(+), 4 deletions(-)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index 31ebec7bcf..793fc1a674 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -3501,6 +3501,7 @@ enum mlx5_ifc_stc_action_type {
 	MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION = 0x10,
 	MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION = 0x11,
 	MLX5_IFC_STC_ACTION_TYPE_ASO = 0x12,
+	MLX5_IFC_STC_ACTION_TYPE_TRAILER = 0x13,
 	MLX5_IFC_STC_ACTION_TYPE_COUNTER = 0x14,
 	MLX5_IFC_STC_ACTION_TYPE_ADD_FIELD = 0x1b,
 	MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_STE_TABLE = 0x80,
@@ -3557,6 +3558,15 @@ struct mlx5_ifc_stc_ste_param_ipsec_decrypt_bits {
 	u8 ipsec_object_id[0x20];
 };
 
+struct mlx5_ifc_stc_ste_param_trailer_bits {
+	u8 reserved_at_0[0x8];
+	u8 command[0x4];
+	u8 reserved_at_c[0x2];
+	u8 type[0x2];
+	u8 reserved_at_10[0xa];
+	u8 length[0x6];
+};
+
 struct mlx5_ifc_stc_ste_param_header_modify_list_bits {
 	u8 header_modify_pattern_id[0x20];
 	u8 header_modify_argument_id[0x20];
@@ -3625,6 +3635,7 @@ union mlx5_ifc_stc_param_bits {
 	struct mlx5_ifc_stc_ste_param_vport_bits vport;
 	struct mlx5_ifc_stc_ste_param_ipsec_encrypt_bits ipsec_encrypt;
 	struct mlx5_ifc_stc_ste_param_ipsec_decrypt_bits ipsec_decrypt;
+	struct mlx5_ifc_stc_ste_param_trailer_bits trailer;
 	u8 reserved_at_0[0x80];
 };
 
diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index bd352fa26d..e425a8803a 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -33,6 +33,7 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2,
 	MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2,
 	MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3,
+	MLX5DR_ACTION_TYP_REFORMAT_TRAILER,
 	MLX5DR_ACTION_TYP_DROP,
 	MLX5DR_ACTION_TYP_TIR,
 	MLX5DR_ACTION_TYP_TBL,
@@ -195,6 +196,21 @@ struct mlx5dr_action_crypto_attr {
 	enum mlx5dr_action_crypto_op op;
 };
 
+enum mlx5dr_action_trailer_type {
+	MLX5DR_ACTION_TRAILER_TYPE_IPSEC,
+};
+
+enum mlx5dr_action_trailer_op {
+	MLX5DR_ACTION_TRAILER_OP_INSERT,
+	MLX5DR_ACTION_TRAILER_OP_REMOVE,
+};
+
+struct mlx5dr_action_trailer_attr {
+	enum mlx5dr_action_trailer_type type;
+	enum mlx5dr_action_trailer_op op;
+	uint8_t size;
+};
+
 /* In actions that take offset, the offset is unique, pointing to a single
  * resource and the user should not reuse the same index because data changing
  * is not atomic.
@@ -607,6 +623,22 @@ mlx5dr_action_create_reformat(struct mlx5dr_context *ctx,
 			      uint32_t log_bulk_size,
 			      uint32_t flags);
 
+/* Create reformat trailer action.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] attr
+ *	attributes: specifies if to insert/remove trailer,
+ *	also specifies the trailer type and size in bytes.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_reformat_trailer(struct mlx5dr_context *ctx,
+				      struct mlx5dr_action_trailer_attr *attr,
+				      uint32_t flags);
+
 /* Create direct rule modify header action.
  *
  * @param[in] ctx
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 956909a628..f8de3d8d98 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -9,16 +9,17 @@
 #define MLX5DR_ACTION_METER_INIT_COLOR_OFFSET 1
 
 /* This is the maximum allowed action order for each table type:
- *	 TX: POP_VLAN, CTR, ASO, PUSH_VLAN, MODIFY, ENCAP, ENCRYPT,
+ *	 TX: POP_VLAN, CTR, ASO, PUSH_VLAN, MODIFY, ENCAP, TRAILER, ENCRYPT,
  *	     Term
- *	 RX: TAG, DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN,
+ *	 RX: TAG, TRAILER, DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN,
  *	     MODIFY, ENCAP, Term
- *	FDB: DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN, MODIFY,
+ *	FDB: TRAILER, DECAP, POP_VLAN, CTR, DECRYPT, ASO, PUSH_VLAN, MODIFY,
  *	     ENCAP, ENCRYPT, Term
  */
 static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_MAX] = {
 	[MLX5DR_TABLE_TYPE_NIC_RX] = {
 		BIT(MLX5DR_ACTION_TYP_TAG),
+		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
@@ -53,6 +54,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
+		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
 		BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT),
 		BIT(MLX5DR_ACTION_TYP_TBL) |
 		BIT(MLX5DR_ACTION_TYP_MISS) |
@@ -61,6 +63,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_LAST),
 	},
 	[MLX5DR_TABLE_TYPE_FDB] = {
+		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
@@ -75,6 +78,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
+		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
 		BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT),
 		BIT(MLX5DR_ACTION_TYP_TBL) |
 		BIT(MLX5DR_ACTION_TYP_MISS) |
@@ -296,7 +300,8 @@ bool mlx5dr_action_check_restrictions(struct mlx5dr_matcher *matcher,
 		break;
 	default:
 		restricted_bits = BIT(MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT) |
-				  BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT);
+				  BIT(MLX5DR_ACTION_TYP_CRYPTO_DECRYPT) |
+				  BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER);
 	}
 
 	while (actions[idx] != MLX5DR_ACTION_TYP_LAST) {
@@ -377,6 +382,7 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 	struct mlx5dr_devx_obj *devx_obj;
 	bool use_fixup = false;
 	uint32_t fw_tbl_type;
+	uint32_t val;
 
 	fw_tbl_type = mlx5dr_table_get_res_fw_ft_type(table_type, is_mirror);
 
@@ -444,6 +450,20 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		}
 		break;
 
+	case MLX5_IFC_STC_ACTION_TYPE_TRAILER:
+		if (table_type != MLX5DR_TABLE_TYPE_FDB)
+			break;
+
+		val = stc_attr->reformat_trailer.op;
+		if ((val == MLX5DR_ACTION_TRAILER_OP_INSERT && !is_mirror) ||
+		    (val == MLX5DR_ACTION_TRAILER_OP_REMOVE && is_mirror)) {
+			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
+			fixup_stc_attr->action_offset = stc_attr->action_offset;
+			fixup_stc_attr->stc_offset = stc_attr->stc_offset;
+			use_fixup = true;
+		}
+		break;
+
 	default:
 		break;
 	}
@@ -683,6 +703,13 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
 		attr->id = obj->id;
 		break;
+	case MLX5DR_ACTION_TYP_REFORMAT_TRAILER:
+		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_TRAILER;
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->reformat_trailer.type = action->reformat_trailer.type;
+		attr->reformat_trailer.op = action->reformat_trailer.op;
+		attr->reformat_trailer.size = action->reformat_trailer.size;
+		break;
 	default:
 		DR_LOG(ERR, "Invalid action type %d", action->type);
 		assert(false);
@@ -2080,6 +2107,64 @@ mlx5dr_action_create_crypto(struct mlx5dr_context *ctx,
 	return action;
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_reformat_trailer(struct mlx5dr_context *ctx,
+				      struct mlx5dr_action_trailer_attr *attr,
+				      uint32_t flags)
+{
+	struct mlx5dr_action *action;
+
+	if (mlx5dr_action_is_root_flags(flags)) {
+		DR_LOG(ERR, "Action flags must be only non root (HWS)");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (attr->type != MLX5DR_ACTION_TRAILER_TYPE_IPSEC) {
+		DR_LOG(ERR, "Only trailer of IPsec is supported");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (attr->op == MLX5DR_ACTION_TRAILER_OP_INSERT) {
+		if (flags & MLX5DR_ACTION_FLAG_HWS_RX) {
+			DR_LOG(ERR, "Trailer insertion is not supported in Rx");
+			rte_errno = EINVAL;
+			return NULL;
+		}
+	} else if (attr->op == MLX5DR_ACTION_TRAILER_OP_REMOVE) {
+		if (flags & MLX5DR_ACTION_FLAG_HWS_TX) {
+			DR_LOG(ERR, "Trailer removal is not supported in Tx");
+			rte_errno = EINVAL;
+			return NULL;
+		}
+	} else {
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (attr->size % DW_SIZE) {
+		DR_LOG(ERR, "Wrong trailer size, size should divide by %u", DW_SIZE);
+		rte_errno = EINVAL;
+		return NULL;
+	}
+
+	action = mlx5dr_action_create_generic(ctx, flags, MLX5DR_ACTION_TYP_REFORMAT_TRAILER);
+	if (!action)
+		return NULL;
+
+	action->reformat_trailer.type = attr->type;
+	action->reformat_trailer.op = attr->op;
+	action->reformat_trailer.size = attr->size;
+
+	if (mlx5dr_action_create_stcs(action, NULL)) {
+		simple_free(action);
+		return NULL;
+	}
+
+	return action;
+}
+
 static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 {
 	struct mlx5dr_devx_obj *obj = NULL;
@@ -2103,6 +2188,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 	case MLX5DR_ACTION_TYP_PUSH_VLAN:
 	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
 	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
+	case MLX5DR_ACTION_TYP_REFORMAT_TRAILER:
 		mlx5dr_action_destroy_stcs(action);
 		break;
 	case MLX5DR_ACTION_TYP_DEST_ROOT:
@@ -2631,6 +2717,18 @@ mlx5dr_action_setter_crypto_decryption(struct mlx5dr_actions_apply_data *apply,
 	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW7] = 0;
 }
 
+static void
+mlx5dr_action_setter_reformat_trailer(struct mlx5dr_actions_apply_data *apply,
+				      struct mlx5dr_actions_wqe_setter *setter)
+{
+	mlx5dr_action_apply_stc(apply, MLX5DR_ACTION_STC_IDX_DW5, setter->idx_triple);
+	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW6] = 0;
+	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW7] = 0;
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = 0;
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW6] = 0;
+	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW7] = 0;
+}
+
 int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 {
 	struct mlx5dr_actions_wqe_setter *start_setter = at->setters + 1;
@@ -2782,6 +2880,14 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 			setter->idx_triple = i;
 			break;
 
+		case MLX5DR_ACTION_TYP_REFORMAT_TRAILER:
+			/* Single push trailer, consume triple due to HW limitations */
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_TRIPLE);
+			setter->flags |= ASF_TRIPLE;
+			setter->set_triple = &mlx5dr_action_setter_reformat_trailer;
+			setter->idx_triple = i;
+			break;
+
 		default:
 			DR_LOG(ERR, "Unsupported action type: %d", action_type[i]);
 			rte_errno = ENOTSUP;
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index 6bfa0bcc4a..b64d6cc9a8 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -153,6 +153,11 @@ struct mlx5dr_action {
 				struct {
 					struct mlx5dv_steering_anchor *sa;
 				} root_tbl;
+				struct {
+					uint8_t type;
+					uint8_t op;
+					uint8_t size;
+				} reformat_trailer;
 				struct {
 					struct mlx5dr_devx_obj *devx_obj;
 				} devx_dest;
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.c b/drivers/net/mlx5/hws/mlx5dr_cmd.c
index 3b3690699d..02547e7178 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.c
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.c
@@ -549,6 +549,14 @@ mlx5dr_cmd_stc_modify_set_stc_param(struct mlx5dr_cmd_stc_modify_attr *stc_attr,
 		MLX5_SET(stc_ste_param_ipsec_decrypt, stc_parm, ipsec_object_id,
 			 stc_attr->id);
 		break;
+	case MLX5_IFC_STC_ACTION_TYPE_TRAILER:
+		MLX5_SET(stc_ste_param_trailer, stc_parm, command,
+			 stc_attr->reformat_trailer.op);
+		MLX5_SET(stc_ste_param_trailer, stc_parm, type,
+			 stc_attr->reformat_trailer.type);
+		MLX5_SET(stc_ste_param_trailer, stc_parm, length,
+			 stc_attr->reformat_trailer.size);
+		break;
 	default:
 		DR_LOG(ERR, "Not supported type %d", stc_attr->action_type);
 		rte_errno = EINVAL;
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.h b/drivers/net/mlx5/hws/mlx5dr_cmd.h
index 7bbb684dbd..c082157538 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.h
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.h
@@ -141,6 +141,11 @@ struct mlx5dr_cmd_stc_modify_attr {
 			uint16_t start_anchor;
 			uint16_t num_of_words;
 		} remove_words;
+		struct {
+			uint8_t type;
+			uint8_t op;
+			uint8_t size;
+		} reformat_trailer;
 
 		uint32_t dest_table_id;
 		uint32_t dest_tir_num;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index 74893f61fb..976a1993e3 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -10,6 +10,7 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2] = "L2_TO_TNL_L2",
 	[MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2] = "TNL_L3_TO_L2",
 	[MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3] = "L2_TO_TNL_L3",
+	[MLX5DR_ACTION_TYP_REFORMAT_TRAILER] = "REFORMAT_TRAILER",
 	[MLX5DR_ACTION_TYP_DROP] = "DROP",
 	[MLX5DR_ACTION_TYP_TIR] = "TIR",
 	[MLX5DR_ACTION_TYP_TBL] = "TBL",
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 05/10] net/mlx5/hws: support ASO first hit action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (3 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 04/10] net/mlx5/hws: support reformat trailer action Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 06/10] net/mlx5/hws: support insert header action Gregory Etelson
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support ASO first hit action.
This action allows tracking if a rule gets hit by a packet.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h       |  5 +++++
 drivers/net/mlx5/hws/mlx5dr.h        | 25 +++++++++++++++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c | 33 ++++++++++++++++++++++++++++
 drivers/net/mlx5/hws/mlx5dr_debug.c  |  1 +
 4 files changed, 64 insertions(+)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index 793fc1a674..40e461cb82 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -3541,6 +3541,7 @@ enum {
 	MLX5_ASO_CT_NUM_PER_OBJ = 1,
 	MLX5_ASO_METER_NUM_PER_OBJ = 2,
 	MLX5_ASO_IPSEC_NUM_PER_OBJ = 1,
+	MLX5_ASO_FIRST_HIT_NUM_PER_OBJ = 512,
 };
 
 struct mlx5_ifc_stc_ste_param_execute_aso_bits {
@@ -5371,6 +5372,10 @@ enum {
 	MLX5_FLOW_COLOR_UNDEFINED,
 };
 
+enum {
+	MLX5_ASO_FIRST_HIT_SET = 1,
+};
+
 /* Maximum value of srTCM & trTCM metering parameters. */
 #define MLX5_SRTCM_XBS_MAX (0xFF * (1ULL << 0x1F))
 #define MLX5_SRTCM_XIR_MAX (8 * (1ULL << 30) * 0xFF)
diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index e425a8803a..e7d89ad7ec 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -47,6 +47,7 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_ASO_METER,
 	MLX5DR_ACTION_TYP_ASO_CT,
 	MLX5DR_ACTION_TYP_ASO_IPSEC,
+	MLX5DR_ACTION_TYP_ASO_FIRST_HIT,
 	MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT,
 	MLX5DR_ACTION_TYP_CRYPTO_DECRYPT,
 	MLX5DR_ACTION_TYP_DEST_ROOT,
@@ -256,6 +257,11 @@ struct mlx5dr_rule_action {
 			uint32_t offset;
 		} aso_ipsec;
 
+		struct {
+			uint32_t offset;
+			bool set;
+		} aso_first_hit;
+
 		struct {
 			uint32_t offset;
 		} crypto;
@@ -714,6 +720,25 @@ mlx5dr_action_create_aso_ipsec(struct mlx5dr_context *ctx,
 			       uint8_t return_reg_id,
 			       uint32_t flags);
 
+/* Create direct rule ASO FIRST HIT action.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] devx_obj
+ *	The DEVX ASO object.
+ * @param[in] return_reg_id
+ *	When a packet hits a flow connected to this object, a flag is set indicating this event,
+ *	copy the original value of this flag into this reg_id.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_aso_first_hit(struct mlx5dr_context *ctx,
+				   struct mlx5dr_devx_obj *devx_obj,
+				   uint8_t return_reg_id,
+				   uint32_t flags);
+
 /* Create direct rule pop vlan action.
  * @param[in] ctx
  *	The context in which the new action will be created.
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index f8de3d8d98..fe9c39b207 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -7,6 +7,7 @@
 #define WIRE_PORT 0xFFFF
 
 #define MLX5DR_ACTION_METER_INIT_COLOR_OFFSET 1
+#define MLX5DR_ACTION_ASO_FIRST_HIT_SET_OFFSET 9
 
 /* This is the maximum allowed action order for each table type:
  *	 TX: POP_VLAN, CTR, ASO, PUSH_VLAN, MODIFY, ENCAP, TRAILER, ENCRYPT,
@@ -29,6 +30,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
 		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
+		BIT(MLX5DR_ACTION_TYP_ASO_FIRST_HIT),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -49,6 +51,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
 		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
+		BIT(MLX5DR_ACTION_TYP_ASO_FIRST_HIT),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -73,6 +76,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_ASO_METER),
 		BIT(MLX5DR_ACTION_TYP_ASO_CT),
 		BIT(MLX5DR_ACTION_TYP_ASO_IPSEC),
+		BIT(MLX5DR_ACTION_TYP_ASO_FIRST_HIT),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
@@ -672,6 +676,13 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->aso.devx_obj_id = obj->id;
 		attr->aso.return_reg_id = action->aso.return_reg_id;
 		break;
+	case MLX5DR_ACTION_TYP_ASO_FIRST_HIT:
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
+		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_ASO;
+		attr->aso.aso_type = ASO_OPC_MOD_FLOW_HIT;
+		attr->aso.devx_obj_id = obj->id;
+		attr->aso.return_reg_id = action->aso.return_reg_id;
+		break;
 	case MLX5DR_ACTION_TYP_VPORT:
 		attr->action_offset = MLX5DR_ACTION_OFFSET_HIT;
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_VPORT;
@@ -1123,6 +1134,16 @@ mlx5dr_action_create_aso_ipsec(struct mlx5dr_context *ctx,
 					devx_obj, return_reg_id, flags);
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_aso_first_hit(struct mlx5dr_context *ctx,
+				   struct mlx5dr_devx_obj *devx_obj,
+				   uint8_t return_reg_id,
+				   uint32_t flags)
+{
+	return mlx5dr_action_create_aso(ctx, MLX5DR_ACTION_TYP_ASO_FIRST_HIT,
+					devx_obj, return_reg_id, flags);
+}
+
 struct mlx5dr_action *
 mlx5dr_action_create_counter(struct mlx5dr_context *ctx,
 			     struct mlx5dr_devx_obj *obj,
@@ -2185,6 +2206,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 	case MLX5DR_ACTION_TYP_ASO_METER:
 	case MLX5DR_ACTION_TYP_ASO_CT:
 	case MLX5DR_ACTION_TYP_ASO_IPSEC:
+	case MLX5DR_ACTION_TYP_ASO_FIRST_HIT:
 	case MLX5DR_ACTION_TYP_PUSH_VLAN:
 	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
 	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
@@ -2601,6 +2623,15 @@ mlx5dr_action_setter_aso(struct mlx5dr_actions_apply_data *apply,
 		offset = rule_action->aso_ipsec.offset / MLX5_ASO_IPSEC_NUM_PER_OBJ;
 		exe_aso_ctrl = 0;
 		break;
+	case MLX5DR_ACTION_TYP_ASO_FIRST_HIT:
+		/* exe_aso_ctrl FIRST HIT format:
+		 * [STC only and reserved bits 22b][set 1b][offset 9b]
+		 */
+		offset = rule_action->aso_first_hit.offset / MLX5_ASO_FIRST_HIT_NUM_PER_OBJ;
+		exe_aso_ctrl = rule_action->aso_first_hit.offset % MLX5_ASO_FIRST_HIT_NUM_PER_OBJ;
+		exe_aso_ctrl |= rule_action->aso_first_hit.set <<
+				MLX5DR_ACTION_ASO_FIRST_HIT_SET_OFFSET;
+		break;
 	default:
 		DR_LOG(ERR, "Unsupported ASO action type: %d", rule_action->action->type);
 		rte_errno = ENOTSUP;
@@ -2803,6 +2834,8 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_ASO_METER:
 		case MLX5DR_ACTION_TYP_ASO_CT:
 		case MLX5DR_ACTION_TYP_ASO_IPSEC:
+		case MLX5DR_ACTION_TYP_ASO_FIRST_HIT:
+			/* Double ASO action */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE);
 			setter->flags |= ASF_DOUBLE;
 			setter->set_double = &mlx5dr_action_setter_aso;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index 976a1993e3..552dba5e63 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -24,6 +24,7 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_ASO_METER] = "ASO_METER",
 	[MLX5DR_ACTION_TYP_ASO_CT] = "ASO_CT",
 	[MLX5DR_ACTION_TYP_ASO_IPSEC] = "ASO_IPSEC",
+	[MLX5DR_ACTION_TYP_ASO_FIRST_HIT] = "ASO_FIRST_HIT",
 	[MLX5DR_ACTION_TYP_DEST_ROOT] = "DEST_ROOT",
 	[MLX5DR_ACTION_TYP_DEST_ARRAY] = "DEST_ARRAY",
 	[MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT] = "CRYPTO_ENCRYPT",
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 06/10] net/mlx5/hws: support insert header action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (4 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 05/10] net/mlx5/hws: support ASO first hit action Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 07/10] net/mlx5/hws: support remove " Gregory Etelson
                   ` (3 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support insert header action, this will allow encap at
a specific anchor and offset selected by the user.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/net/mlx5/hws/mlx5dr.h          |  36 ++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c   | 112 +++++++++++++++++++++----
 drivers/net/mlx5/hws/mlx5dr_action.h   |   5 +-
 drivers/net/mlx5/hws/mlx5dr_cmd.c      |   4 +-
 drivers/net/mlx5/hws/mlx5dr_debug.c    |   1 +
 drivers/net/mlx5/hws/mlx5dr_internal.h |   1 +
 6 files changed, 141 insertions(+), 18 deletions(-)

diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index e7d89ad7ec..a6bbb85eed 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -50,6 +50,7 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_ASO_FIRST_HIT,
 	MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT,
 	MLX5DR_ACTION_TYP_CRYPTO_DECRYPT,
+	MLX5DR_ACTION_TYP_INSERT_HEADER,
 	MLX5DR_ACTION_TYP_DEST_ROOT,
 	MLX5DR_ACTION_TYP_DEST_ARRAY,
 	MLX5DR_ACTION_TYP_MAX,
@@ -174,6 +175,20 @@ struct mlx5dr_action_reformat_header {
 	void *data;
 };
 
+struct mlx5dr_action_insert_header {
+	struct mlx5dr_action_reformat_header hdr;
+	/* PRM start anchor to which header will be inserted */
+	uint8_t anchor;
+	/* Header insertion offset in bytes, from the start
+	 * anchor to the location where new header will be inserted.
+	 */
+	uint8_t offset;
+	/* Indicates this header insertion adds encapsulation header to the packet,
+	 * requiring device to update offloaded fields (for example IPv4 total length).
+	 */
+	bool encap;
+};
+
 struct mlx5dr_action_mh_pattern {
 	/* Byte size of modify actions provided by "data" */
 	size_t sz;
@@ -813,6 +828,27 @@ mlx5dr_action_create_crypto(struct mlx5dr_context *ctx,
 			    struct mlx5dr_action_crypto_attr *attr,
 			    uint32_t flags);
 
+/* Create insert header action.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] num_of_hdrs
+ *	Number of provided headers in "hdrs" array.
+ * @param[in] hdrs
+ *	Headers array containing header information.
+ * @param[in] log_bulk_size
+ *	Number of unique values used with this insert header.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_insert_header(struct mlx5dr_context *ctx,
+				   uint8_t num_of_hdrs,
+				   struct mlx5dr_action_insert_header *hdrs,
+				   uint32_t log_bulk_size,
+				   uint32_t flags);
+
 /* Destroy direct rule action.
  *
  * @param[in] action
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index fe9c39b207..9885555a8f 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -34,6 +34,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
+		BIT(MLX5DR_ACTION_TYP_INSERT_HEADER) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
 		BIT(MLX5DR_ACTION_TYP_TBL) |
@@ -55,6 +56,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
+		BIT(MLX5DR_ACTION_TYP_INSERT_HEADER) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
@@ -80,6 +82,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_PUSH_VLAN),
 		BIT(MLX5DR_ACTION_TYP_MODIFY_HDR),
+		BIT(MLX5DR_ACTION_TYP_INSERT_HEADER) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
@@ -640,20 +643,15 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->remove_header.end_anchor = MLX5_HEADER_ANCHOR_INNER_MAC;
 		break;
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2:
-		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_INSERT;
-		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
-		attr->insert_header.encap = 1;
-		attr->insert_header.insert_anchor = MLX5_HEADER_ANCHOR_PACKET_START;
-		attr->insert_header.arg_id = action->reformat.arg_obj->id;
-		attr->insert_header.header_size = action->reformat.header_size;
-		break;
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3:
+	case MLX5DR_ACTION_TYP_INSERT_HEADER:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_INSERT;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
-		attr->insert_header.encap = 1;
-		attr->insert_header.insert_anchor = MLX5_HEADER_ANCHOR_PACKET_START;
+		attr->insert_header.encap = action->reformat.encap;
+		attr->insert_header.insert_anchor = action->reformat.anchor;
 		attr->insert_header.arg_id = action->reformat.arg_obj->id;
 		attr->insert_header.header_size = action->reformat.header_size;
+		attr->insert_header.insert_offset = action->reformat.offset;
 		break;
 	case MLX5DR_ACTION_TYP_ASO_METER:
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
@@ -1382,7 +1380,7 @@ mlx5dr_action_create_reformat_root(struct mlx5dr_action *action,
 }
 
 static int
-mlx5dr_action_handle_l2_to_tunnel_l2(struct mlx5dr_action *action,
+mlx5dr_action_handle_insert_with_ptr(struct mlx5dr_action *action,
 				     uint8_t num_of_hdrs,
 				     struct mlx5dr_action_reformat_header *hdrs,
 				     uint32_t log_bulk_sz)
@@ -1392,8 +1390,8 @@ mlx5dr_action_handle_l2_to_tunnel_l2(struct mlx5dr_action *action,
 	int ret, i;
 
 	for (i = 0; i < num_of_hdrs; i++) {
-		if (hdrs[i].sz % 2 != 0) {
-			DR_LOG(ERR, "Header data size should be multiply of 2");
+		if (hdrs[i].sz % W_SIZE != 0) {
+			DR_LOG(ERR, "Header data size should be in WORD granularity");
 			rte_errno = EINVAL;
 			return rte_errno;
 		}
@@ -1415,6 +1413,13 @@ mlx5dr_action_handle_l2_to_tunnel_l2(struct mlx5dr_action *action,
 		action[i].reformat.num_of_hdrs = num_of_hdrs;
 		action[i].reformat.max_hdr_sz = max_sz;
 
+		if (action[i].type == MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2 ||
+		    action[i].type == MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3) {
+			action[i].reformat.anchor = MLX5_HEADER_ANCHOR_PACKET_START;
+			action[i].reformat.offset = 0;
+			action[i].reformat.encap = 1;
+		}
+
 		ret = mlx5dr_action_create_stcs(&action[i], NULL);
 		if (ret) {
 			DR_LOG(ERR, "Failed to create stc for reformat");
@@ -1448,7 +1453,7 @@ mlx5dr_action_handle_l2_to_tunnel_l3(struct mlx5dr_action *action,
 	}
 
 	/* Reuse the insert with pointer for the L2L3 header */
-	ret = mlx5dr_action_handle_l2_to_tunnel_l2(action,
+	ret = mlx5dr_action_handle_insert_with_ptr(action,
 						   num_of_hdrs,
 						   hdrs,
 						   log_bulk_sz);
@@ -1592,7 +1597,7 @@ mlx5dr_action_create_reformat_hws(struct mlx5dr_action *action,
 		ret = mlx5dr_action_create_stcs(action, NULL);
 		break;
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2:
-		ret = mlx5dr_action_handle_l2_to_tunnel_l2(action, num_of_hdrs, hdrs, bulk_size);
+		ret = mlx5dr_action_handle_insert_with_ptr(action, num_of_hdrs, hdrs, bulk_size);
 		break;
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3:
 		ret = mlx5dr_action_handle_l2_to_tunnel_l3(action, num_of_hdrs, hdrs, bulk_size);
@@ -1622,6 +1627,7 @@ mlx5dr_action_create_reformat(struct mlx5dr_context *ctx,
 
 	if (!num_of_hdrs) {
 		DR_LOG(ERR, "Reformat num_of_hdrs cannot be zero");
+		rte_errno = EINVAL;
 		return NULL;
 	}
 
@@ -1657,7 +1663,6 @@ mlx5dr_action_create_reformat(struct mlx5dr_context *ctx,
 	ret = mlx5dr_action_create_reformat_hws(action, num_of_hdrs, hdrs, log_bulk_size);
 	if (ret) {
 		DR_LOG(ERR, "Failed to create HWS reformat action");
-		rte_errno = EINVAL;
 		goto free_action;
 	}
 
@@ -2186,6 +2191,81 @@ mlx5dr_action_create_reformat_trailer(struct mlx5dr_context *ctx,
 	return action;
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_insert_header(struct mlx5dr_context *ctx,
+				   uint8_t num_of_hdrs,
+				   struct mlx5dr_action_insert_header *hdrs,
+				   uint32_t log_bulk_size,
+				   uint32_t flags)
+{
+	struct mlx5dr_action_reformat_header *reformat_hdrs;
+	struct mlx5dr_action *action;
+	int i, ret;
+
+	if (!num_of_hdrs) {
+		DR_LOG(ERR, "Reformat num_of_hdrs cannot be zero");
+		return NULL;
+	}
+
+	if (mlx5dr_action_is_root_flags(flags)) {
+		DR_LOG(ERR, "Dynamic reformat action not supported over root");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	if (!mlx5dr_action_is_hws_flags(flags) ||
+	    ((flags & MLX5DR_ACTION_FLAG_SHARED) && (log_bulk_size || num_of_hdrs > 1))) {
+		DR_LOG(ERR, "Reformat flags don't fit HWS (flags: 0x%x)", flags);
+		rte_errno = EINVAL;
+		return NULL;
+	}
+
+	action = mlx5dr_action_create_generic_bulk(ctx, flags,
+						   MLX5DR_ACTION_TYP_INSERT_HEADER,
+						   num_of_hdrs);
+	if (!action)
+		return NULL;
+
+	reformat_hdrs = simple_calloc(num_of_hdrs, sizeof(*reformat_hdrs));
+	if (!reformat_hdrs) {
+		DR_LOG(ERR, "Failed to allocate memory for reformat_hdrs");
+		rte_errno = ENOMEM;
+		goto free_action;
+	}
+
+	for (i = 0; i < num_of_hdrs; i++) {
+		if (hdrs[i].offset % W_SIZE != 0) {
+			DR_LOG(ERR, "Header offset should be in WORD granularity");
+			rte_errno = EINVAL;
+			goto free_reformat_hdrs;
+		}
+
+		action[i].reformat.anchor = hdrs[i].anchor;
+		action[i].reformat.encap = hdrs[i].encap;
+		action[i].reformat.offset = hdrs[i].offset;
+		reformat_hdrs[i].sz = hdrs[i].hdr.sz;
+		reformat_hdrs[i].data = hdrs[i].hdr.data;
+	}
+
+	ret = mlx5dr_action_handle_insert_with_ptr(action, num_of_hdrs,
+						   reformat_hdrs, log_bulk_size);
+	if (ret) {
+		DR_LOG(ERR, "Failed to create HWS reformat action");
+		rte_errno = EINVAL;
+		goto free_reformat_hdrs;
+	}
+
+	simple_free(reformat_hdrs);
+
+	return action;
+
+free_reformat_hdrs:
+	simple_free(reformat_hdrs);
+free_action:
+	simple_free(action);
+	return NULL;
+}
+
 static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 {
 	struct mlx5dr_devx_obj *obj = NULL;
@@ -2252,6 +2332,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 			mlx5dr_action_destroy_stcs(&action[i]);
 		mlx5dr_cmd_destroy_obj(action->reformat.arg_obj);
 		break;
+	case MLX5DR_ACTION_TYP_INSERT_HEADER:
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2:
 		for (i = 0; i < action->reformat.num_of_hdrs; i++)
 			mlx5dr_action_destroy_stcs(&action[i]);
@@ -2850,6 +2931,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 			setter->idx_single = i;
 			break;
 
+		case MLX5DR_ACTION_TYP_INSERT_HEADER:
 		case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2:
 			/* Double insert header with pointer */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE);
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index b64d6cc9a8..02358da4cb 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -136,8 +136,11 @@ struct mlx5dr_action {
 				struct {
 					struct mlx5dr_devx_obj *arg_obj;
 					uint32_t header_size;
-					uint8_t num_of_hdrs;
 					uint16_t max_hdr_sz;
+					uint8_t num_of_hdrs;
+					uint8_t anchor;
+					uint8_t offset;
+					bool encap;
 				} reformat;
 				struct {
 					struct mlx5dr_devx_obj *devx_obj;
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.c b/drivers/net/mlx5/hws/mlx5dr_cmd.c
index 02547e7178..0ba4774f08 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.c
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.c
@@ -492,9 +492,9 @@ mlx5dr_cmd_stc_modify_set_stc_param(struct mlx5dr_cmd_stc_modify_attr *stc_attr,
 			 stc_attr->insert_header.insert_anchor);
 		/* HW gets the next 2 sizes in words */
 		MLX5_SET(stc_ste_param_insert, stc_parm, insert_size,
-			 stc_attr->insert_header.header_size / 2);
+			 stc_attr->insert_header.header_size / W_SIZE);
 		MLX5_SET(stc_ste_param_insert, stc_parm, insert_offset,
-			 stc_attr->insert_header.insert_offset / 2);
+			 stc_attr->insert_header.insert_offset / W_SIZE);
 		MLX5_SET(stc_ste_param_insert, stc_parm, insert_argument,
 			 stc_attr->insert_header.arg_id);
 		break;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index 552dba5e63..29e207765b 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -29,6 +29,7 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_DEST_ARRAY] = "DEST_ARRAY",
 	[MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT] = "CRYPTO_ENCRYPT",
 	[MLX5DR_ACTION_TYP_CRYPTO_DECRYPT] = "CRYPTO_DECRYPT",
+	[MLX5DR_ACTION_TYP_INSERT_HEADER] = "INSERT_HEADER",
 };
 
 static_assert(ARRAY_SIZE(mlx5dr_debug_action_type_str) == MLX5DR_ACTION_TYP_MAX,
diff --git a/drivers/net/mlx5/hws/mlx5dr_internal.h b/drivers/net/mlx5/hws/mlx5dr_internal.h
index 021d599a56..b9efdc4a9a 100644
--- a/drivers/net/mlx5/hws/mlx5dr_internal.h
+++ b/drivers/net/mlx5/hws/mlx5dr_internal.h
@@ -40,6 +40,7 @@
 #include "mlx5dr_pat_arg.h"
 #include "mlx5dr_crc32.h"
 
+#define W_SIZE		2
 #define DW_SIZE		4
 #define BITS_IN_BYTE	8
 #define BITS_IN_DW	(BITS_IN_BYTE * DW_SIZE)
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 07/10] net/mlx5/hws: support remove header action
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (5 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 06/10] net/mlx5/hws: support insert header action Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 08/10] net/mlx5/hws: allow jump to TIR over FDB Gregory Etelson
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Hamdan Igbaria, Alex Vesker,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Hamdan Igbaria <hamdani@nvidia.com>

Support remove header action, this action will allow the user
to execute dynamic decaps by choosing to decap by providing a
start anchor and number of words to remove, or providing a
start anchor and end anchor.

Signed-off-by: Hamdan Igbaria <hamdani@nvidia.com>
Reviewed-by: Alex Vesker <valex@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/net/mlx5/hws/mlx5dr.h        | 40 ++++++++++++++
 drivers/net/mlx5/hws/mlx5dr_action.c | 78 ++++++++++++++++++++++++++++
 drivers/net/mlx5/hws/mlx5dr_action.h |  7 +++
 drivers/net/mlx5/hws/mlx5dr_debug.c  |  1 +
 4 files changed, 126 insertions(+)

diff --git a/drivers/net/mlx5/hws/mlx5dr.h b/drivers/net/mlx5/hws/mlx5dr.h
index a6bbb85eed..2e692f76c3 100644
--- a/drivers/net/mlx5/hws/mlx5dr.h
+++ b/drivers/net/mlx5/hws/mlx5dr.h
@@ -51,6 +51,7 @@ enum mlx5dr_action_type {
 	MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT,
 	MLX5DR_ACTION_TYP_CRYPTO_DECRYPT,
 	MLX5DR_ACTION_TYP_INSERT_HEADER,
+	MLX5DR_ACTION_TYP_REMOVE_HEADER,
 	MLX5DR_ACTION_TYP_DEST_ROOT,
 	MLX5DR_ACTION_TYP_DEST_ARRAY,
 	MLX5DR_ACTION_TYP_MAX,
@@ -189,6 +190,29 @@ struct mlx5dr_action_insert_header {
 	bool encap;
 };
 
+enum mlx5dr_action_remove_header_type {
+	MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_OFFSET,
+	MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_HEADER,
+};
+
+struct mlx5dr_action_remove_header_attr {
+	enum mlx5dr_action_remove_header_type type;
+	union {
+		struct {
+			/* PRM start anchor from which header will be removed */
+			uint8_t start_anchor;
+			/* PRM end anchor till which header will be removed */
+			uint8_t end_anchor;
+			bool decap;
+		} by_anchor;
+		struct {
+			/* PRM start anchor from which header will be removed */
+			uint8_t start_anchor;
+			uint8_t size;
+		} by_offset;
+	};
+};
+
 struct mlx5dr_action_mh_pattern {
 	/* Byte size of modify actions provided by "data" */
 	size_t sz;
@@ -849,6 +873,22 @@ mlx5dr_action_create_insert_header(struct mlx5dr_context *ctx,
 				   uint32_t log_bulk_size,
 				   uint32_t flags);
 
+/* Create remove header action.
+ *
+ * @param[in] ctx
+ *	The context in which the new action will be created.
+ * @param[in] attr
+ *	attributes: specifies the remove header type, PRM start anchor and
+ *	the PRM end anchor or the PRM start anchor and remove size in bytes.
+ * @param[in] flags
+ *	Action creation flags. (enum mlx5dr_action_flags)
+ * @return pointer to mlx5dr_action on success NULL otherwise.
+ */
+struct mlx5dr_action *
+mlx5dr_action_create_remove_header(struct mlx5dr_context *ctx,
+				   struct mlx5dr_action_remove_header_attr *attr,
+				   uint32_t flags);
+
 /* Destroy direct rule action.
  *
  * @param[in] action
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 9885555a8f..1a6296a728 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -9,6 +9,9 @@
 #define MLX5DR_ACTION_METER_INIT_COLOR_OFFSET 1
 #define MLX5DR_ACTION_ASO_FIRST_HIT_SET_OFFSET 9
 
+/* Header removal size limited to 128B (64 words) */
+#define MLX5DR_ACTION_REMOVE_HEADER_MAX_SIZE 128
+
 /* This is the maximum allowed action order for each table type:
  *	 TX: POP_VLAN, CTR, ASO, PUSH_VLAN, MODIFY, ENCAP, TRAILER, ENCRYPT,
  *	     Term
@@ -21,6 +24,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 	[MLX5DR_TABLE_TYPE_NIC_RX] = {
 		BIT(MLX5DR_ACTION_TYP_TAG),
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
+		BIT(MLX5DR_ACTION_TYP_REMOVE_HEADER) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
@@ -69,6 +73,7 @@ static const uint32_t action_order_arr[MLX5DR_TABLE_TYPE_MAX][MLX5DR_ACTION_TYP_
 	},
 	[MLX5DR_TABLE_TYPE_FDB] = {
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TRAILER),
+		BIT(MLX5DR_ACTION_TYP_REMOVE_HEADER) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2) |
 		BIT(MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2),
 		BIT(MLX5DR_ACTION_TYP_POP_VLAN),
@@ -719,6 +724,19 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 		attr->reformat_trailer.op = action->reformat_trailer.op;
 		attr->reformat_trailer.size = action->reformat_trailer.size;
 		break;
+	case MLX5DR_ACTION_TYP_REMOVE_HEADER:
+		if (action->remove_header.type == MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_HEADER) {
+			attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_REMOVE;
+			attr->remove_header.decap = action->remove_header.decap;
+			attr->remove_header.start_anchor = action->remove_header.start_anchor;
+			attr->remove_header.end_anchor = action->remove_header.end_anchor;
+		} else {
+			attr->action_type = MLX5_IFC_STC_ACTION_TYPE_REMOVE_WORDS;
+			attr->remove_words.start_anchor = action->remove_header.start_anchor;
+			attr->remove_words.num_of_words = action->remove_header.num_of_words;
+		}
+		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		break;
 	default:
 		DR_LOG(ERR, "Invalid action type %d", action->type);
 		assert(false);
@@ -2266,6 +2284,64 @@ mlx5dr_action_create_insert_header(struct mlx5dr_context *ctx,
 	return NULL;
 }
 
+struct mlx5dr_action *
+mlx5dr_action_create_remove_header(struct mlx5dr_context *ctx,
+				   struct mlx5dr_action_remove_header_attr *attr,
+				   uint32_t flags)
+{
+	struct mlx5dr_action *action;
+
+	if (mlx5dr_action_is_root_flags(flags)) {
+		DR_LOG(ERR, "Remove header action not supported over root");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
+	action = mlx5dr_action_create_generic(ctx, flags, MLX5DR_ACTION_TYP_REMOVE_HEADER);
+	if (!action)
+		return NULL;
+
+	switch (attr->type) {
+	case MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_HEADER:
+		action->remove_header.type = MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_HEADER;
+		action->remove_header.start_anchor = attr->by_anchor.start_anchor;
+		action->remove_header.end_anchor = attr->by_anchor.end_anchor;
+		action->remove_header.decap = attr->by_anchor.decap;
+		break;
+	case MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_OFFSET:
+		if (attr->by_offset.size % W_SIZE != 0) {
+			DR_LOG(ERR, "Invalid size, HW supports header remove in WORD granularity");
+			rte_errno = EINVAL;
+			goto free_action;
+		}
+
+		if (attr->by_offset.size > MLX5DR_ACTION_REMOVE_HEADER_MAX_SIZE) {
+			DR_LOG(ERR, "Header removal size limited to %u bytes",
+			       MLX5DR_ACTION_REMOVE_HEADER_MAX_SIZE);
+			rte_errno = EINVAL;
+			goto free_action;
+		}
+
+		action->remove_header.type = MLX5DR_ACTION_REMOVE_HEADER_TYPE_BY_OFFSET;
+		action->remove_header.start_anchor = attr->by_offset.start_anchor;
+		action->remove_header.num_of_words = attr->by_offset.size / W_SIZE;
+		break;
+	default:
+		DR_LOG(ERR, "Unsupported remove header type %u", attr->type);
+		rte_errno = ENOTSUP;
+		goto free_action;
+	}
+
+	if (mlx5dr_action_create_stcs(action, NULL))
+		goto free_action;
+
+	return action;
+
+free_action:
+	simple_free(action);
+	return NULL;
+}
+
 static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 {
 	struct mlx5dr_devx_obj *obj = NULL;
@@ -2291,6 +2367,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 	case MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT:
 	case MLX5DR_ACTION_TYP_CRYPTO_DECRYPT:
 	case MLX5DR_ACTION_TYP_REFORMAT_TRAILER:
+	case MLX5DR_ACTION_TYP_REMOVE_HEADER:
 		mlx5dr_action_destroy_stcs(action);
 		break;
 	case MLX5DR_ACTION_TYP_DEST_ROOT:
@@ -2923,6 +3000,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 			setter->idx_double = i;
 			break;
 
+		case MLX5DR_ACTION_TYP_REMOVE_HEADER:
 		case MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2:
 			/* Single remove header to header */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_SINGLE1 | ASF_MODIFY);
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index 02358da4cb..4046f658e6 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -161,6 +161,13 @@ struct mlx5dr_action {
 					uint8_t op;
 					uint8_t size;
 				} reformat_trailer;
+				struct {
+					uint8_t type;
+					uint8_t start_anchor;
+					uint8_t end_anchor;
+					uint8_t num_of_words;
+					bool decap;
+				} remove_header;
 				struct {
 					struct mlx5dr_devx_obj *devx_obj;
 				} devx_dest;
diff --git a/drivers/net/mlx5/hws/mlx5dr_debug.c b/drivers/net/mlx5/hws/mlx5dr_debug.c
index 29e207765b..5111f41648 100644
--- a/drivers/net/mlx5/hws/mlx5dr_debug.c
+++ b/drivers/net/mlx5/hws/mlx5dr_debug.c
@@ -30,6 +30,7 @@ const char *mlx5dr_debug_action_type_str[] = {
 	[MLX5DR_ACTION_TYP_CRYPTO_ENCRYPT] = "CRYPTO_ENCRYPT",
 	[MLX5DR_ACTION_TYP_CRYPTO_DECRYPT] = "CRYPTO_DECRYPT",
 	[MLX5DR_ACTION_TYP_INSERT_HEADER] = "INSERT_HEADER",
+	[MLX5DR_ACTION_TYP_REMOVE_HEADER] = "REMOVE_HEADER",
 };
 
 static_assert(ARRAY_SIZE(mlx5dr_debug_action_type_str) == MLX5DR_ACTION_TYP_MAX,
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 08/10] net/mlx5/hws: allow jump to TIR over FDB
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (6 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 07/10] net/mlx5/hws: support remove " Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 09/10] net/mlx5/hws: support dynamic re-parse Gregory Etelson
  2023-10-31 12:25 ` [PATCH 10/10] net/mlx5/hws: dynamic re-parse for modify header Gregory Etelson
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Alex Vesker, Erez Shitrit,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Alex Vesker <valex@nvidia.com>

Current TIR action is allowed to be used only for NIC RX,
this will allow TIR action over FDB for RX traffic in case
of TX traffic packets will be dropped.

Signed-off-by: Alex Vesker <valex@nvidia.com>
Reviewed-by: Erez Shitrit <erezsh@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h       |  2 ++
 drivers/net/mlx5/hws/mlx5dr_action.c | 27 ++++++++++++++++++++++-----
 drivers/net/mlx5/hws/mlx5dr_cmd.c    |  4 ++++
 drivers/net/mlx5/hws/mlx5dr_cmd.h    |  1 +
 4 files changed, 29 insertions(+), 5 deletions(-)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index 40e461cb82..bb2b990d5b 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -2418,6 +2418,8 @@ struct mlx5_ifc_wqe_based_flow_table_cap_bits {
 	u8 reserved_at_180[0x10];
 	u8 ste_format_gen_wqe[0x10];
 	u8 linear_match_definer_reg_c3[0x20];
+	u8 fdb_jump_to_tir_stc[0x1];
+	u8 reserved_at_1c1[0x1f];
 };
 
 union mlx5_ifc_hca_cap_union_bits {
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 1a6296a728..05b6e97576 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -445,6 +445,7 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		break;
 
 	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_ENCRYPTION:
+		/* Encrypt is allowed on RX side, requires mask in case of FDB */
 		if (fw_tbl_type == FS_FT_FDB_RX) {
 			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
 			fixup_stc_attr->action_offset = stc_attr->action_offset;
@@ -454,6 +455,7 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		break;
 
 	case MLX5_IFC_STC_ACTION_TYPE_CRYPTO_IPSEC_DECRYPTION:
+		/* Decrypt is allowed on TX side, requires mask in case of FDB */
 		if (fw_tbl_type == FS_FT_FDB_TX) {
 			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
 			fixup_stc_attr->action_offset = stc_attr->action_offset;
@@ -463,12 +465,10 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		break;
 
 	case MLX5_IFC_STC_ACTION_TYPE_TRAILER:
-		if (table_type != MLX5DR_TABLE_TYPE_FDB)
-			break;
-
+		/* Trailer has FDB limitations on RX and TX based on operation */
 		val = stc_attr->reformat_trailer.op;
-		if ((val == MLX5DR_ACTION_TRAILER_OP_INSERT && !is_mirror) ||
-		    (val == MLX5DR_ACTION_TRAILER_OP_REMOVE && is_mirror)) {
+		if ((val == MLX5DR_ACTION_TRAILER_OP_INSERT && fw_tbl_type == FS_FT_FDB_RX) ||
+		    (val == MLX5DR_ACTION_TRAILER_OP_REMOVE && fw_tbl_type == FS_FT_FDB_TX)) {
 			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
 			fixup_stc_attr->action_offset = stc_attr->action_offset;
 			fixup_stc_attr->stc_offset = stc_attr->stc_offset;
@@ -476,6 +476,16 @@ mlx5dr_action_fixup_stc_attr(struct mlx5dr_context *ctx,
 		}
 		break;
 
+	case MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_TIR:
+		/* TIR is allowed on RX side, requires mask in case of FDB */
+		if (fw_tbl_type == FS_FT_FDB_TX) {
+			fixup_stc_attr->action_type = MLX5_IFC_STC_ACTION_TYPE_DROP;
+			fixup_stc_attr->action_offset = MLX5DR_ACTION_OFFSET_HIT;
+			fixup_stc_attr->stc_offset = stc_attr->stc_offset;
+			use_fixup = true;
+		}
+		break;
+
 	default:
 		break;
 	}
@@ -976,6 +986,13 @@ mlx5dr_action_create_dest_tir(struct mlx5dr_context *ctx,
 		return NULL;
 	}
 
+	if ((flags & MLX5DR_ACTION_FLAG_ROOT_FDB) ||
+	    (flags & MLX5DR_ACTION_FLAG_HWS_FDB && !ctx->caps->fdb_tir_stc)) {
+		DR_LOG(ERR, "TIR action not support on FDB");
+		rte_errno = ENOTSUP;
+		return NULL;
+	}
+
 	if (!is_local) {
 		DR_LOG(ERR, "TIR should be created on local ibv_device, flags: 0x%x",
 		       flags);
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.c b/drivers/net/mlx5/hws/mlx5dr_cmd.c
index 0ba4774f08..135d31dca1 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.c
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.c
@@ -1275,6 +1275,10 @@ int mlx5dr_cmd_query_caps(struct ibv_context *ctx,
 		caps->supp_ste_format_gen_wqe = MLX5_GET(query_hca_cap_out, out,
 							 capability.wqe_based_flow_table_cap.
 							 ste_format_gen_wqe);
+
+		caps->fdb_tir_stc = MLX5_GET(query_hca_cap_out, out,
+					     capability.wqe_based_flow_table_cap.
+					     fdb_jump_to_tir_stc);
 	}
 
 	if (caps->eswitch_manager) {
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.h b/drivers/net/mlx5/hws/mlx5dr_cmd.h
index c082157538..cb27212a5b 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.h
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.h
@@ -241,6 +241,7 @@ struct mlx5dr_cmd_query_caps {
 	uint8_t log_header_modify_argument_granularity;
 	uint8_t log_header_modify_argument_max_alloc;
 	uint8_t sq_ts_format;
+	uint8_t fdb_tir_stc;
 	uint64_t definer_format_sup;
 	uint32_t trivial_match_definer;
 	uint32_t vhca_id;
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 09/10] net/mlx5/hws: support dynamic re-parse
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (7 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 08/10] net/mlx5/hws: allow jump to TIR over FDB Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  2023-10-31 12:25 ` [PATCH 10/10] net/mlx5/hws: dynamic re-parse for modify header Gregory Etelson
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Alex Vesker, Erez Shitrit,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Alex Vesker <valex@nvidia.com>

Each steering entry (STE) has a bit called re-parse used for
re-parsing the packet in HW, re-parsing is needed after
reformat (e.g. push/pop/encapsulate/...) or when modifying the
packet headers requiring structure change (e.g. TCP to UDP).
Until now we re-parsed the packet in each STE leading to
longer processing per packet. With supported devices we
can control re-parse bit to allow better performance.

Signed-off-by: Alex Vesker <valex@nvidia.com>
Reviewed-by: Erez Shitrit <erezsh@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/common/mlx5/mlx5_prm.h        | 10 ++++-
 drivers/net/mlx5/hws/mlx5dr_action.c  | 58 +++++++++++++++++----------
 drivers/net/mlx5/hws/mlx5dr_action.h  |  2 +-
 drivers/net/mlx5/hws/mlx5dr_cmd.c     |  3 +-
 drivers/net/mlx5/hws/mlx5dr_cmd.h     |  2 +
 drivers/net/mlx5/hws/mlx5dr_context.c | 15 +++++++
 drivers/net/mlx5/hws/mlx5dr_context.h |  9 ++++-
 drivers/net/mlx5/hws/mlx5dr_matcher.c |  2 +
 8 files changed, 75 insertions(+), 26 deletions(-)

diff --git a/drivers/common/mlx5/mlx5_prm.h b/drivers/common/mlx5/mlx5_prm.h
index bb2b990d5b..a5ecce98e9 100644
--- a/drivers/common/mlx5/mlx5_prm.h
+++ b/drivers/common/mlx5/mlx5_prm.h
@@ -3445,6 +3445,7 @@ enum mlx5_ifc_rtc_ste_format {
 enum mlx5_ifc_rtc_reparse_mode {
 	MLX5_IFC_RTC_REPARSE_NEVER = 0x0,
 	MLX5_IFC_RTC_REPARSE_ALWAYS = 0x1,
+	MLX5_IFC_RTC_REPARSE_BY_STC = 0x2,
 };
 
 #define MLX5_IFC_RTC_LINEAR_LOOKUP_TBL_LOG_MAX 16
@@ -3515,6 +3516,12 @@ enum mlx5_ifc_stc_action_type {
 	MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_UPLINK = 0x86,
 };
 
+enum mlx5_ifc_stc_reparse_mode {
+	MLX5_IFC_STC_REPARSE_IGNORE = 0x0,
+	MLX5_IFC_STC_REPARSE_NEVER = 0x1,
+	MLX5_IFC_STC_REPARSE_ALWAYS = 0x2,
+};
+
 struct mlx5_ifc_stc_ste_param_ste_table_bits {
 	u8 ste_obj_id[0x20];
 	u8 match_definer_id[0x20];
@@ -3648,7 +3655,8 @@ enum {
 
 struct mlx5_ifc_stc_bits {
 	u8 modify_field_select[0x40];
-	u8 reserved_at_40[0x48];
+	u8 reserved_at_40[0x46];
+	u8 reparse_mode[0x2];
 	u8 table_type[0x8];
 	u8 ste_action_offset[0x8];
 	u8 action_type[0x8];
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index 05b6e97576..bdccfb9cf3 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -124,16 +124,18 @@ static int mlx5dr_action_get_shared_stc_nic(struct mlx5dr_context *ctx,
 		goto unlock_and_out;
 	}
 	switch (stc_type) {
-	case MLX5DR_CONTEXT_SHARED_STC_DECAP:
+	case MLX5DR_CONTEXT_SHARED_STC_DECAP_L3:
 		stc_attr.action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_REMOVE;
 		stc_attr.action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		stc_attr.reparse_mode = MLX5_IFC_STC_REPARSE_IGNORE;
 		stc_attr.remove_header.decap = 0;
 		stc_attr.remove_header.start_anchor = MLX5_HEADER_ANCHOR_PACKET_START;
 		stc_attr.remove_header.end_anchor = MLX5_HEADER_ANCHOR_IPV6_IPV4;
 		break;
-	case MLX5DR_CONTEXT_SHARED_STC_POP:
+	case MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP:
 		stc_attr.action_type = MLX5_IFC_STC_ACTION_TYPE_REMOVE_WORDS;
 		stc_attr.action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		stc_attr.reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		stc_attr.remove_words.start_anchor = MLX5_HEADER_ANCHOR_FIRST_VLAN_START;
 		stc_attr.remove_words.num_of_words = MLX5DR_ACTION_HDR_LEN_L2_VLAN;
 		break;
@@ -512,6 +514,11 @@ int mlx5dr_action_alloc_single_stc(struct mlx5dr_context *ctx,
 	}
 
 	stc_attr->stc_offset = stc->offset;
+
+	/* Dynamic reparse not supported, overwrite and use default */
+	if (!mlx5dr_context_cap_dynamic_reparse(ctx))
+		stc_attr->reparse_mode = MLX5_IFC_STC_REPARSE_IGNORE;
+
 	devx_obj_0 = mlx5dr_pool_chunk_get_base_devx_obj(stc_pool, stc);
 
 	/* According to table/action limitation change the stc_attr */
@@ -600,6 +607,8 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 					struct mlx5dr_devx_obj *obj,
 					struct mlx5dr_cmd_stc_modify_attr *attr)
 {
+	attr->reparse_mode = MLX5_IFC_STC_REPARSE_IGNORE;
+
 	switch (action->type) {
 	case MLX5DR_ACTION_TYP_TAG:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_TAG;
@@ -626,6 +635,7 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2:
 	case MLX5DR_ACTION_TYP_MODIFY_HDR:
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		if (action->modify_header.num_of_actions == 1) {
 			attr->modify_action.data = action->modify_header.single_action;
 			attr->action_type = mlx5dr_action_get_mh_stc_type(attr->modify_action.data);
@@ -653,6 +663,7 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_REMOVE;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		attr->remove_header.decap = 1;
 		attr->remove_header.start_anchor = MLX5_HEADER_ANCHOR_PACKET_START;
 		attr->remove_header.end_anchor = MLX5_HEADER_ANCHOR_INNER_MAC;
@@ -662,6 +673,7 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_INSERT_HEADER:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_INSERT;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		attr->insert_header.encap = action->reformat.encap;
 		attr->insert_header.insert_anchor = action->reformat.anchor;
 		attr->insert_header.arg_id = action->reformat.arg_obj->id;
@@ -705,12 +717,14 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_POP_VLAN:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_REMOVE_WORDS;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		attr->remove_words.start_anchor = MLX5_HEADER_ANCHOR_FIRST_VLAN_START;
 		attr->remove_words.num_of_words = MLX5DR_ACTION_HDR_LEN_L2_VLAN / 2;
 		break;
 	case MLX5DR_ACTION_TYP_PUSH_VLAN:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_HEADER_INSERT;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		attr->insert_header.encap = 0;
 		attr->insert_header.is_inline = 1;
 		attr->insert_header.insert_anchor = MLX5_HEADER_ANCHOR_PACKET_START;
@@ -730,6 +744,7 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_REFORMAT_TRAILER:
 		attr->action_type = MLX5_IFC_STC_ACTION_TYPE_TRAILER;
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		attr->reformat_trailer.type = action->reformat_trailer.type;
 		attr->reformat_trailer.op = action->reformat_trailer.op;
 		attr->reformat_trailer.size = action->reformat_trailer.size;
@@ -746,6 +761,7 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 			attr->remove_words.num_of_words = action->remove_header.num_of_words;
 		}
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW5;
+		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
 		break;
 	default:
 		DR_LOG(ERR, "Invalid action type %d", action->type);
@@ -1310,7 +1326,7 @@ mlx5dr_action_create_pop_vlan(struct mlx5dr_context *ctx, uint32_t flags)
 	if (!action)
 		return NULL;
 
-	ret = mlx5dr_action_get_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_POP);
+	ret = mlx5dr_action_get_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP);
 	if (ret) {
 		DR_LOG(ERR, "Failed to create remove stc for reformat");
 		goto free_action;
@@ -1325,7 +1341,7 @@ mlx5dr_action_create_pop_vlan(struct mlx5dr_context *ctx, uint32_t flags)
 	return action;
 
 free_shared:
-	mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_POP);
+	mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP);
 free_action:
 	simple_free(action);
 	return NULL;
@@ -1481,7 +1497,7 @@ mlx5dr_action_handle_l2_to_tunnel_l3(struct mlx5dr_action *action,
 	int ret;
 
 	/* The action is remove-l2-header + insert-l3-header */
-	ret = mlx5dr_action_get_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP);
+	ret = mlx5dr_action_get_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP_L3);
 	if (ret) {
 		DR_LOG(ERR, "Failed to create remove stc for reformat");
 		return ret;
@@ -1498,7 +1514,7 @@ mlx5dr_action_handle_l2_to_tunnel_l3(struct mlx5dr_action *action,
 	return 0;
 
 put_shared_stc:
-	mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP);
+	mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP_L3);
 	return ret;
 }
 
@@ -2393,7 +2409,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 		break;
 	case MLX5DR_ACTION_TYP_POP_VLAN:
 		mlx5dr_action_destroy_stcs(action);
-		mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_POP);
+		mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP);
 		break;
 	case MLX5DR_ACTION_TYP_DEST_ARRAY:
 		mlx5dr_action_destroy_stcs(action);
@@ -2421,7 +2437,7 @@ static void mlx5dr_action_destroy_hws(struct mlx5dr_action *action)
 			mlx5dr_cmd_destroy_obj(obj);
 		break;
 	case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3:
-		mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP);
+		mlx5dr_action_put_shared_stc(action, MLX5DR_CONTEXT_SHARED_STC_DECAP_L3);
 		for (i = 0; i < action->reformat.num_of_hdrs; i++)
 			mlx5dr_action_destroy_stcs(&action[i]);
 		mlx5dr_cmd_destroy_obj(action->reformat.arg_obj);
@@ -2481,6 +2497,7 @@ int mlx5dr_action_get_default_stc(struct mlx5dr_context *ctx,
 
 	stc_attr.action_type = MLX5_IFC_STC_ACTION_TYPE_NOP;
 	stc_attr.action_offset = MLX5DR_ACTION_OFFSET_DW0;
+	stc_attr.reparse_mode = MLX5_IFC_STC_REPARSE_IGNORE;
 	ret = mlx5dr_action_alloc_single_stc(ctx, &stc_attr, tbl_type,
 					     &default_stc->nop_ctr);
 	if (ret) {
@@ -2858,7 +2875,7 @@ mlx5dr_action_setter_single_double_pop(struct mlx5dr_actions_apply_data *apply,
 	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = 0;
 	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW5] =
 		htobe32(mlx5dr_action_get_shared_stc_offset(apply->common_res,
-						    MLX5DR_CONTEXT_SHARED_STC_POP));
+							    MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP));
 }
 
 static void
@@ -2893,7 +2910,7 @@ mlx5dr_action_setter_common_decap(struct mlx5dr_actions_apply_data *apply,
 	apply->wqe_data[MLX5DR_ACTION_OFFSET_DW5] = 0;
 	apply->wqe_ctrl->stc_ix[MLX5DR_ACTION_STC_IDX_DW5] =
 		htobe32(mlx5dr_action_get_shared_stc_offset(apply->common_res,
-							    MLX5DR_CONTEXT_SHARED_STC_DECAP));
+							    MLX5DR_CONTEXT_SHARED_STC_DECAP_L3));
 }
 
 static void
@@ -2983,8 +3000,8 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 				pop_setter->set_single = &mlx5dr_action_setter_single_double_pop;
 				break;
 			}
-			setter = mlx5dr_action_setter_find_first(last_setter, ASF_SINGLE1 | ASF_MODIFY);
-			setter->flags |= ASF_SINGLE1 | ASF_REPARSE | ASF_REMOVE;
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_SINGLE1 | ASF_MODIFY | ASF_INSERT);
+			setter->flags |= ASF_SINGLE1 | ASF_REMOVE;
 			setter->set_single = &mlx5dr_action_setter_single;
 			setter->idx_single = i;
 			pop_setter = setter;
@@ -2993,7 +3010,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_PUSH_VLAN:
 			/* Double insert inline */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE | ASF_REMOVE);
-			setter->flags |= ASF_DOUBLE | ASF_REPARSE | ASF_MODIFY;
+			setter->flags |= ASF_DOUBLE | ASF_INSERT;
 			setter->set_double = &mlx5dr_action_setter_push_vlan;
 			setter->idx_double = i;
 			break;
@@ -3001,7 +3018,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_MODIFY_HDR:
 			/* Double modify header list */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE | ASF_REMOVE);
-			setter->flags |= ASF_DOUBLE | ASF_MODIFY | ASF_REPARSE;
+			setter->flags |= ASF_DOUBLE | ASF_MODIFY;
 			setter->set_double = &mlx5dr_action_setter_modify_header;
 			setter->idx_double = i;
 			break;
@@ -3021,7 +3038,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_REFORMAT_TNL_L2_TO_L2:
 			/* Single remove header to header */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_SINGLE1 | ASF_MODIFY);
-			setter->flags |= ASF_SINGLE1 | ASF_REMOVE | ASF_REPARSE;
+			setter->flags |= ASF_SINGLE1 | ASF_REMOVE;
 			setter->set_single = &mlx5dr_action_setter_single;
 			setter->idx_single = i;
 			break;
@@ -3029,8 +3046,8 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_INSERT_HEADER:
 		case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L2:
 			/* Double insert header with pointer */
-			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE);
-			setter->flags |= ASF_DOUBLE | ASF_REPARSE;
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE | ASF_REMOVE);
+			setter->flags |= ASF_DOUBLE | ASF_INSERT;
 			setter->set_double = &mlx5dr_action_setter_insert_ptr;
 			setter->idx_double = i;
 			break;
@@ -3038,7 +3055,7 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 		case MLX5DR_ACTION_TYP_REFORMAT_L2_TO_TNL_L3:
 			/* Single remove + Double insert header with pointer */
 			setter = mlx5dr_action_setter_find_first(last_setter, ASF_SINGLE1 | ASF_DOUBLE);
-			setter->flags |= ASF_SINGLE1 | ASF_DOUBLE | ASF_REPARSE | ASF_REMOVE;
+			setter->flags |= ASF_SINGLE1 | ASF_DOUBLE;
 			setter->set_double = &mlx5dr_action_setter_insert_ptr;
 			setter->idx_double = i;
 			setter->set_single = &mlx5dr_action_setter_common_decap;
@@ -3047,9 +3064,8 @@ int mlx5dr_action_template_process(struct mlx5dr_action_template *at)
 
 		case MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2:
 			/* Double modify header list with remove and push inline */
-			setter = mlx5dr_action_setter_find_first(last_setter,
-								 ASF_DOUBLE | ASF_REMOVE);
-			setter->flags |= ASF_DOUBLE | ASF_MODIFY | ASF_REPARSE;
+			setter = mlx5dr_action_setter_find_first(last_setter, ASF_DOUBLE | ASF_REMOVE);
+			setter->flags |= ASF_DOUBLE | ASF_MODIFY | ASF_INSERT;
 			setter->set_double = &mlx5dr_action_setter_tnl_l3_to_l2;
 			setter->idx_double = i;
 			break;
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index 4046f658e6..328de65a1e 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -55,7 +55,7 @@ enum mlx5dr_action_setter_flag {
 	ASF_SINGLE3 = 1 << 2,
 	ASF_DOUBLE = ASF_SINGLE2 | ASF_SINGLE3,
 	ASF_TRIPLE = ASF_SINGLE1 | ASF_DOUBLE,
-	ASF_REPARSE = 1 << 3,
+	ASF_INSERT = 1 << 3,
 	ASF_REMOVE = 1 << 4,
 	ASF_MODIFY = 1 << 5,
 	ASF_CTR = 1 << 6,
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.c b/drivers/net/mlx5/hws/mlx5dr_cmd.c
index 135d31dca1..07c820afe5 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.c
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.c
@@ -394,7 +394,7 @@ mlx5dr_cmd_rtc_create(struct ibv_context *ctx,
 	MLX5_SET(rtc, attr, ste_table_base_id, rtc_attr->ste_base);
 	MLX5_SET(rtc, attr, ste_table_offset, rtc_attr->ste_offset);
 	MLX5_SET(rtc, attr, miss_flow_table_id, rtc_attr->miss_ft_id);
-	MLX5_SET(rtc, attr, reparse_mode, MLX5_IFC_RTC_REPARSE_ALWAYS);
+	MLX5_SET(rtc, attr, reparse_mode, rtc_attr->reparse_mode);
 
 	devx_obj->obj = mlx5_glue->devx_obj_create(ctx, in, sizeof(in), out, sizeof(out));
 	if (!devx_obj->obj) {
@@ -586,6 +586,7 @@ mlx5dr_cmd_stc_modify(struct mlx5dr_devx_obj *devx_obj,
 	attr = MLX5_ADDR_OF(create_stc_in, in, stc);
 	MLX5_SET(stc, attr, ste_action_offset, stc_attr->action_offset);
 	MLX5_SET(stc, attr, action_type, stc_attr->action_type);
+	MLX5_SET(stc, attr, reparse_mode, stc_attr->reparse_mode);
 	MLX5_SET64(stc, attr, modify_field_select,
 		   MLX5_IFC_MODIFY_STC_FIELD_SELECT_NEW_STC);
 
diff --git a/drivers/net/mlx5/hws/mlx5dr_cmd.h b/drivers/net/mlx5/hws/mlx5dr_cmd.h
index cb27212a5b..7792fc48aa 100644
--- a/drivers/net/mlx5/hws/mlx5dr_cmd.h
+++ b/drivers/net/mlx5/hws/mlx5dr_cmd.h
@@ -79,6 +79,7 @@ struct mlx5dr_cmd_rtc_create_attr {
 	uint8_t table_type;
 	uint8_t match_definer_0;
 	uint8_t match_definer_1;
+	uint8_t reparse_mode;
 	bool is_frst_jumbo;
 	bool is_scnd_range;
 };
@@ -98,6 +99,7 @@ struct mlx5dr_cmd_stc_create_attr {
 struct mlx5dr_cmd_stc_modify_attr {
 	uint32_t stc_offset;
 	uint8_t action_offset;
+	uint8_t reparse_mode;
 	enum mlx5_ifc_stc_action_type action_type;
 	union {
 		uint32_t id; /* TIRN, TAG, FT ID, STE ID, CRYPTO */
diff --git a/drivers/net/mlx5/hws/mlx5dr_context.c b/drivers/net/mlx5/hws/mlx5dr_context.c
index 08a5ee92a5..15d53c578a 100644
--- a/drivers/net/mlx5/hws/mlx5dr_context.c
+++ b/drivers/net/mlx5/hws/mlx5dr_context.c
@@ -4,6 +4,21 @@
 
 #include "mlx5dr_internal.h"
 
+bool mlx5dr_context_cap_dynamic_reparse(struct mlx5dr_context *ctx)
+{
+	return IS_BIT_SET(ctx->caps->rtc_reparse_mode, MLX5_IFC_RTC_REPARSE_BY_STC);
+}
+
+uint8_t mlx5dr_context_get_reparse_mode(struct mlx5dr_context *ctx)
+{
+	/* Prefer to use dynamic reparse, reparse only specific actions */
+	if (mlx5dr_context_cap_dynamic_reparse(ctx))
+		return MLX5_IFC_RTC_REPARSE_NEVER;
+
+	/* Otherwise use less efficient static */
+	return MLX5_IFC_RTC_REPARSE_ALWAYS;
+}
+
 static int mlx5dr_context_pools_init(struct mlx5dr_context *ctx)
 {
 	struct mlx5dr_pool_attr pool_attr = {0};
diff --git a/drivers/net/mlx5/hws/mlx5dr_context.h b/drivers/net/mlx5/hws/mlx5dr_context.h
index 0ba8d0c92e..f476c2308c 100644
--- a/drivers/net/mlx5/hws/mlx5dr_context.h
+++ b/drivers/net/mlx5/hws/mlx5dr_context.h
@@ -11,8 +11,8 @@ enum mlx5dr_context_flags {
 };
 
 enum mlx5dr_context_shared_stc_type {
-	MLX5DR_CONTEXT_SHARED_STC_DECAP = 0,
-	MLX5DR_CONTEXT_SHARED_STC_POP = 1,
+	MLX5DR_CONTEXT_SHARED_STC_DECAP_L3 = 0,
+	MLX5DR_CONTEXT_SHARED_STC_DOUBLE_POP = 1,
 	MLX5DR_CONTEXT_SHARED_STC_MAX = 2,
 };
 
@@ -60,4 +60,9 @@ mlx5dr_context_get_local_ibv(struct mlx5dr_context *ctx)
 
 	return ctx->ibv_ctx;
 }
+
+bool mlx5dr_context_cap_dynamic_reparse(struct mlx5dr_context *ctx);
+
+uint8_t mlx5dr_context_get_reparse_mode(struct mlx5dr_context *ctx);
+
 #endif /* MLX5DR_CONTEXT_H_ */
diff --git a/drivers/net/mlx5/hws/mlx5dr_matcher.c b/drivers/net/mlx5/hws/mlx5dr_matcher.c
index 6f74cf3677..cd6cbdeceb 100644
--- a/drivers/net/mlx5/hws/mlx5dr_matcher.c
+++ b/drivers/net/mlx5/hws/mlx5dr_matcher.c
@@ -583,6 +583,7 @@ static int mlx5dr_matcher_create_rtc(struct mlx5dr_matcher *matcher,
 	rtc_attr.pd = ctx->pd_num;
 	rtc_attr.ste_base = devx_obj->id;
 	rtc_attr.ste_offset = ste->offset;
+	rtc_attr.reparse_mode = mlx5dr_context_get_reparse_mode(ctx);
 	rtc_attr.table_type = mlx5dr_table_get_res_fw_ft_type(tbl->type, false);
 	mlx5dr_matcher_set_rtc_attr_sz(matcher, &rtc_attr, rtc_type, false);
 
@@ -790,6 +791,7 @@ static int mlx5dr_matcher_bind_at(struct mlx5dr_matcher *matcher)
 	/* Allocate STC for jumps to STE */
 	stc_attr.action_offset = MLX5DR_ACTION_OFFSET_HIT;
 	stc_attr.action_type = MLX5_IFC_STC_ACTION_TYPE_JUMP_TO_STE_TABLE;
+	stc_attr.reparse_mode = MLX5_IFC_STC_REPARSE_NEVER;
 	stc_attr.ste_table.ste = matcher->action_ste.ste;
 	stc_attr.ste_table.ste_pool = matcher->action_ste.pool;
 	stc_attr.ste_table.match_definer_id = ctx->caps->trivial_match_definer;
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 10/10] net/mlx5/hws: dynamic re-parse for modify header
  2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
                   ` (8 preceding siblings ...)
  2023-10-31 12:25 ` [PATCH 09/10] net/mlx5/hws: support dynamic re-parse Gregory Etelson
@ 2023-10-31 12:25 ` Gregory Etelson
  9 siblings, 0 replies; 11+ messages in thread
From: Gregory Etelson @ 2023-10-31 12:25 UTC (permalink / raw)
  To: dev
  Cc: getelson, mkashani, rasland, Alex Vesker, Erez Shitrit,
	Matan Azrad, Viacheslav Ovsiienko, Ori Kam, Suanming Mou

From: Alex Vesker <valex@nvidia.com>

With dynamic re-parse we would always require re-parse but
this is not always necessary. Re-parse is only needed when
the packet structure is changed. This support will allow
dynamically deciding based on the action pattern if re-parse
is required or no.

Signed-off-by: Alex Vesker <valex@nvidia.com>
Reviewed-by: Erez Shitrit <erezsh@nvidia.com>
Acked-by: Matan Azrad <matan@nvidia.com>
---
 drivers/net/mlx5/hws/mlx5dr_action.c  | 15 +++++++---
 drivers/net/mlx5/hws/mlx5dr_action.h  |  1 +
 drivers/net/mlx5/hws/mlx5dr_pat_arg.c | 41 +++++++++++++++++++++++++--
 drivers/net/mlx5/hws/mlx5dr_pat_arg.h |  2 ++
 4 files changed, 53 insertions(+), 6 deletions(-)

diff --git a/drivers/net/mlx5/hws/mlx5dr_action.c b/drivers/net/mlx5/hws/mlx5dr_action.c
index bdccfb9cf3..59be8ae2c5 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.c
+++ b/drivers/net/mlx5/hws/mlx5dr_action.c
@@ -635,7 +635,9 @@ static void mlx5dr_action_fill_stc_attr(struct mlx5dr_action *action,
 	case MLX5DR_ACTION_TYP_REFORMAT_TNL_L3_TO_L2:
 	case MLX5DR_ACTION_TYP_MODIFY_HDR:
 		attr->action_offset = MLX5DR_ACTION_OFFSET_DW6;
-		attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
+		if (action->modify_header.require_reparse)
+			attr->reparse_mode = MLX5_IFC_STC_REPARSE_ALWAYS;
+
 		if (action->modify_header.num_of_actions == 1) {
 			attr->modify_action.data = action->modify_header.single_action;
 			attr->action_type = mlx5dr_action_get_mh_stc_type(attr->modify_action.data);
@@ -1614,6 +1616,8 @@ mlx5dr_action_handle_tunnel_l3_to_l2(struct mlx5dr_action *action,
 		action[i].modify_header.num_of_actions = num_of_actions;
 		action[i].modify_header.arg_obj = arg_obj;
 		action[i].modify_header.pat_obj = pat_obj;
+		action[i].modify_header.require_reparse =
+			mlx5dr_pat_require_reparse((__be64 *)mh_data, num_of_actions);
 
 		ret = mlx5dr_action_create_stcs(&action[i], NULL);
 		if (ret) {
@@ -1760,7 +1764,7 @@ mlx5dr_action_create_modify_header_hws(struct mlx5dr_action *action,
 {
 	struct mlx5dr_devx_obj *pat_obj, *arg_obj = NULL;
 	struct mlx5dr_context *ctx = action->ctx;
-	uint16_t max_mh_actions = 0;
+	uint16_t num_actions, max_mh_actions = 0;
 	int i, ret;
 
 	/* Calculate maximum number of mh actions for shared arg allocation */
@@ -1786,11 +1790,14 @@ mlx5dr_action_create_modify_header_hws(struct mlx5dr_action *action,
 			goto free_stc_and_pat;
 		}
 
+		num_actions = pattern[i].sz / MLX5DR_MODIFY_ACTION_SIZE;
 		action[i].modify_header.num_of_patterns = num_of_patterns;
 		action[i].modify_header.max_num_of_actions = max_mh_actions;
-		action[i].modify_header.num_of_actions = pattern[i].sz / MLX5DR_MODIFY_ACTION_SIZE;
+		action[i].modify_header.num_of_actions = num_actions;
+		action[i].modify_header.require_reparse =
+			mlx5dr_pat_require_reparse(pattern[i].data, num_actions);
 
-		if (action[i].modify_header.num_of_actions == 1) {
+		if (num_actions == 1) {
 			pat_obj = NULL;
 			/* Optimize single modify action to be used inline */
 			action[i].modify_header.single_action = pattern[i].data[0];
diff --git a/drivers/net/mlx5/hws/mlx5dr_action.h b/drivers/net/mlx5/hws/mlx5dr_action.h
index 328de65a1e..e56f5b59c7 100644
--- a/drivers/net/mlx5/hws/mlx5dr_action.h
+++ b/drivers/net/mlx5/hws/mlx5dr_action.h
@@ -132,6 +132,7 @@ struct mlx5dr_action {
 					uint8_t single_action_type;
 					uint8_t num_of_actions;
 					uint8_t max_num_of_actions;
+					uint8_t require_reparse;
 				} modify_header;
 				struct {
 					struct mlx5dr_devx_obj *arg_obj;
diff --git a/drivers/net/mlx5/hws/mlx5dr_pat_arg.c b/drivers/net/mlx5/hws/mlx5dr_pat_arg.c
index 349d77f296..a949844d24 100644
--- a/drivers/net/mlx5/hws/mlx5dr_pat_arg.c
+++ b/drivers/net/mlx5/hws/mlx5dr_pat_arg.c
@@ -37,6 +37,43 @@ uint32_t mlx5dr_arg_get_arg_size(uint16_t num_of_actions)
 	return BIT(mlx5dr_arg_get_arg_log_size(num_of_actions));
 }
 
+bool mlx5dr_pat_require_reparse(__be64 *actions, uint16_t num_of_actions)
+{
+	uint16_t i, field;
+	uint8_t action_id;
+
+	for (i = 0; i < num_of_actions; i++) {
+		action_id = MLX5_GET(set_action_in, &actions[i], action_type);
+
+		switch (action_id) {
+		case MLX5_MODIFICATION_TYPE_NOP:
+			field = MLX5_MODI_OUT_NONE;
+			break;
+
+		case MLX5_MODIFICATION_TYPE_SET:
+		case MLX5_MODIFICATION_TYPE_ADD:
+			field = MLX5_GET(set_action_in, &actions[i], field);
+			break;
+
+		case MLX5_MODIFICATION_TYPE_COPY:
+		case MLX5_MODIFICATION_TYPE_ADD_FIELD:
+			field = MLX5_GET(copy_action_in, &actions[i], dst_field);
+			break;
+
+		default:
+			/* Insert/Remove/Unknown actions require reparse */
+			return true;
+		}
+
+		/* Below fields can change packet structure require a reparse */
+		if (field == MLX5_MODI_OUT_ETHERTYPE ||
+		    field == MLX5_MODI_OUT_IPV6_NEXT_HDR)
+			return true;
+	}
+
+	return false;
+}
+
 /* Cache and cache element handling */
 int mlx5dr_pat_init_pattern_cache(struct mlx5dr_pattern_cache **cache)
 {
@@ -228,8 +265,8 @@ mlx5dr_pat_get_pattern(struct mlx5dr_context *ctx,
 	}
 
 	pat_obj = mlx5dr_cmd_header_modify_pattern_create(ctx->ibv_ctx,
-							      pattern_sz,
-							      (uint8_t *)pattern);
+							  pattern_sz,
+							  (uint8_t *)pattern);
 	if (!pat_obj) {
 		DR_LOG(ERR, "Failed to create pattern FW object");
 		goto out_unlock;
diff --git a/drivers/net/mlx5/hws/mlx5dr_pat_arg.h b/drivers/net/mlx5/hws/mlx5dr_pat_arg.h
index 2a38891c4d..bbe313102f 100644
--- a/drivers/net/mlx5/hws/mlx5dr_pat_arg.h
+++ b/drivers/net/mlx5/hws/mlx5dr_pat_arg.h
@@ -79,6 +79,8 @@ void mlx5dr_pat_put_pattern(struct mlx5dr_context *ctx,
 bool mlx5dr_arg_is_valid_arg_request_size(struct mlx5dr_context *ctx,
 					  uint32_t arg_size);
 
+bool mlx5dr_pat_require_reparse(__be64 *actions, uint16_t num_of_actions);
+
 void mlx5dr_arg_write(struct mlx5dr_send_engine *queue,
 		      void *comp_data,
 		      uint32_t arg_idx,
-- 
2.39.2


^ permalink raw reply	[flat|nested] 11+ messages in thread

end of thread, other threads:[~2023-10-31 12:27 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-10-31 12:25 [PATCH 00/10] net/mlx5/hws: IPSEC reparse submission Gregory Etelson
2023-10-31 12:25 ` [PATCH 01/10] net/mlx5/hws: check the rule status on rule update Gregory Etelson
2023-10-31 12:25 ` [PATCH 02/10] net/mlx5/hws: support IPsec encryption/decryption action Gregory Etelson
2023-10-31 12:25 ` [PATCH 03/10] net/mlx5/hws: support ASO IPsec action Gregory Etelson
2023-10-31 12:25 ` [PATCH 04/10] net/mlx5/hws: support reformat trailer action Gregory Etelson
2023-10-31 12:25 ` [PATCH 05/10] net/mlx5/hws: support ASO first hit action Gregory Etelson
2023-10-31 12:25 ` [PATCH 06/10] net/mlx5/hws: support insert header action Gregory Etelson
2023-10-31 12:25 ` [PATCH 07/10] net/mlx5/hws: support remove " Gregory Etelson
2023-10-31 12:25 ` [PATCH 08/10] net/mlx5/hws: allow jump to TIR over FDB Gregory Etelson
2023-10-31 12:25 ` [PATCH 09/10] net/mlx5/hws: support dynamic re-parse Gregory Etelson
2023-10-31 12:25 ` [PATCH 10/10] net/mlx5/hws: dynamic re-parse for modify header Gregory Etelson

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).