From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from EUR03-VE1-obe.outbound.protection.outlook.com (mail-eopbgr50049.outbound.protection.outlook.com [40.107.5.49]) by dpdk.org (Postfix) with ESMTP id 5CE745398 for ; Mon, 29 Oct 2018 11:03:23 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=Mellanox.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=bBzjIJKGe0Q2dtNl94sszYWeqsgTskxyVqxNmr4u61c=; b=TAoejFhdVFqw9TBClOKNJXYLrn1S10drAFlCXTGCR1IChC60qGqrlkN/cPgzLiFs/yZXtGhJ9PF6/8BggE5EY/3ZE/RsrZ0obylgUvGro9sQXW4r2+VbJ/se0fM2xOeBnhkidMb0J1oqc8nYvAzj1Wfn/2ZY2HG3OvMZFANU6po= Received: from DB7PR05MB4426.eurprd05.prod.outlook.com (52.134.109.15) by DB7PR05MB5463.eurprd05.prod.outlook.com (20.177.192.28) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.1273.27; Mon, 29 Oct 2018 10:03:22 +0000 Received: from DB7PR05MB4426.eurprd05.prod.outlook.com ([fe80::80e:e6b:baf2:d973]) by DB7PR05MB4426.eurprd05.prod.outlook.com ([fe80::80e:e6b:baf2:d973%3]) with mapi id 15.20.1273.027; Mon, 29 Oct 2018 10:03:22 +0000 From: Shahaf Shuler To: Dekel Peled , Yongseok Koh CC: "dev@dpdk.org" , Ori Kam Thread-Topic: [dpdk-dev] [PATCH v6 6/6] net/mlx5: add raw data encap decap to Direct Verbs Thread-Index: AQHUbJ6/CQ5DkDhNeEGOek3JICkMkKU152kQ Date: Mon, 29 Oct 2018 10:03:21 +0000 Message-ID: References: <1539259967-10975-1-git-send-email-dekelp@mellanox.com> <1540498108-18358-7-git-send-email-dekelp@mellanox.com> In-Reply-To: <1540498108-18358-7-git-send-email-dekelp@mellanox.com> Accept-Language: en-US Content-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: authentication-results: spf=none (sender IP is ) smtp.mailfrom=shahafs@mellanox.com; x-originating-ip: [31.154.10.105] x-ms-publictraffictype: Email x-microsoft-exchange-diagnostics: 1; DB7PR05MB5463; 6:WZRZPzJ1AnL9+EOp9W85wgRYU3yrUFsl5/IDrVbb/7JQrjKELSOM3AcCd97QzVDU4bzz9hIYTWpckQCh1LSt7lo2sH36i4ldiY8kan1d6ot4WM2QKg/Z9W4JCLLboJ4R6k0C6T+6QS6dMrRdhUWeU4zqRNTWqlI2BOW56nHoYxunddC1Wu6FIAJbXuCiqXRtY0oAcT1hxSGpjL2rbF1drIC4kA88xJT96WjNo/VHdVtRUvy0DBzqXn4+aV2TrvEwXgDU/jZ1XKlROhdF8sBFrHTwsy08e5QEXIZCiZD9MBcQAYdpI4pJIHX1E9Uyrw5ix3UMFheDUTMt40sTuUStpssK+P35+ZmnoPxbJzwe36Hy7vyeXRxeFaZ/ewicQ7sSklQjnXgaOjczzR3G1DaHL9srMC5qMyzfyFUWiDlqYl8Eub0vHci2/9pvNPhSvAPZaNXGg041bDT7e4dcBv/xDg==; 5:18dEPd+YRBFaSoeFHrNjO4HuvH2s/oesszXeyC4l3/8q1wWD4hvdP0chHuWwxv6U1ExB++ILDv23pXnlgUPVPXvPrWvZUG0leJLgH06dwDS1PtThT+Rla5L7q0ZNkxuyvTiPuFy1TjAkVTZZfB5T9PSaQ2paLwPt92d5NxBeHMg=; 7:Fdlw1W9bhFvHD6Xum1p5kXVsA3ag1LECzyrTqfbST7xGt5cuOTGOIeKfndvhspRXcTdTDkNZFzvh32KdE6svc7wRLpI+zRlsK9JtbiW+5ykEmGYNrasMXrMoFyqH+uUf575Bd9EE/jyzlWIW4Bk20w== x-ms-exchange-antispam-srfa-diagnostics: SOS; x-ms-office365-filtering-correlation-id: d834aae5-f2ad-44d5-0ad5-08d63d85c25e x-ms-office365-filtering-ht: Tenant x-microsoft-antispam: BCL:0; PCL:0; RULEID:(7020095)(4652040)(8989299)(4534185)(4627221)(201703031133081)(201702281549075)(8990200)(5600074)(711020)(4618075)(2017052603328)(7153060)(7193020); SRVR:DB7PR05MB5463; x-ms-traffictypediagnostic: DB7PR05MB5463: x-microsoft-antispam-prvs: x-exchange-antispam-report-test: UriScan:(17755550239193); x-ms-exchange-senderadcheck: 1 x-exchange-antispam-report-cfa-test: BCL:0; PCL:0; RULEID:(8211001083)(6040522)(2401047)(5005006)(8121501046)(3231382)(944501410)(52105095)(93006095)(93001095)(10201501046)(3002001)(6055026)(148016)(149066)(150057)(6041310)(201703131423095)(201702281528075)(20161123555045)(201703061421075)(201703061406153)(20161123558120)(20161123562045)(20161123564045)(20161123560045)(201708071742011)(7699051)(76991095); SRVR:DB7PR05MB5463; BCL:0; PCL:0; RULEID:; SRVR:DB7PR05MB5463; x-forefront-prvs: 084080FC15 x-forefront-antispam-report: SFV:NSPM; SFS:(10009020)(376002)(136003)(346002)(396003)(39860400002)(366004)(199004)(189003)(229853002)(26005)(7696005)(6506007)(5250100002)(76176011)(2900100001)(186003)(55016002)(4326008)(6436002)(256004)(14454004)(14444005)(97736004)(478600001)(2906002)(81166006)(81156014)(74316002)(66066001)(575784001)(8936002)(86362001)(68736007)(110136005)(305945005)(106356001)(6246003)(9686003)(105586002)(476003)(53936002)(7736002)(54906003)(11346002)(446003)(6636002)(25786009)(6116002)(3846002)(5660300001)(4744004)(102836004)(33656002)(486006)(71190400001)(107886003)(71200400001)(316002)(99286004)(290074003); DIR:OUT; SFP:1101; SCL:1; SRVR:DB7PR05MB5463; H:DB7PR05MB4426.eurprd05.prod.outlook.com; FPR:; SPF:None; LANG:en; PTR:InfoNoRecords; A:1; MX:1; received-spf: None (protection.outlook.com: mellanox.com does not designate permitted sender hosts) x-microsoft-antispam-message-info: 2eeVlOJkyjrNEl9NkSKW1Ppy75zPCJbKW3iiAkTWktgoipmRmhUFuQ0FXmAGqwYQtsyX+q1/VRdGNsUpCtuuAQnB3vlPE9f5pbCruuKEdsQTACau6vaPrcKOOaJD0FQDwUzJcjWK9tokstqEyqWPw4urmVDqvUuBD20BE7BYN+7Vc9WFssgXR2oj/IQUOYbKO2PDFHR3u5ZGNzk2OegQ38nDfC5BAA5DtX+GYhO+fTR6gIQT6oq30tZAf5hP89LijCFK+j+iMjhJjM1cghIyurkQDdXByEKqBxwMVCwrk9JC1lXhiJvFq0Uewlo/KVkXvepazHNRApToZBMYCBx5PjKuRDSAZeRyND9uj6Cqkho= spamdiagnosticoutput: 1:99 spamdiagnosticmetadata: NSPM Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 X-OriginatorOrg: Mellanox.com X-MS-Exchange-CrossTenant-Network-Message-Id: d834aae5-f2ad-44d5-0ad5-08d63d85c25e X-MS-Exchange-CrossTenant-originalarrivaltime: 29 Oct 2018 10:03:21.9130 (UTC) X-MS-Exchange-CrossTenant-fromentityheader: Hosted X-MS-Exchange-CrossTenant-id: a652971c-7d2e-4d9b-a6a4-d149256f461b X-MS-Exchange-Transport-CrossTenantHeadersStamped: DB7PR05MB5463 Subject: Re: [dpdk-dev] [PATCH v6 6/6] net/mlx5: add raw data encap decap to Direct Verbs X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 29 Oct 2018 10:03:23 -0000 Thursday, October 25, 2018 11:08 PM, Dekel Peled: > Subject: [dpdk-dev] [PATCH v6 6/6] net/mlx5: add raw data encap decap to > Direct Verbs >=20 > This patch implements the encap and decap actions, using raw data, in DV > flow for MLX5 PMD. >=20 > Signed-off-by: Dekel Peled > --- > drivers/net/mlx5/mlx5_flow.h | 12 ++- > drivers/net/mlx5/mlx5_flow_dv.c | 227 > ++++++++++++++++++++++++++++++++++++++-- > 2 files changed, 224 insertions(+), 15 deletions(-) >=20 > diff --git a/drivers/net/mlx5/mlx5_flow.h b/drivers/net/mlx5/mlx5_flow.h > index 2d73a05..92ba111 100644 > --- a/drivers/net/mlx5/mlx5_flow.h > +++ b/drivers/net/mlx5/mlx5_flow.h > @@ -96,15 +96,19 @@ > #define MLX5_FLOW_ACTION_VXLAN_DECAP (1u << 23) #define > MLX5_FLOW_ACTION_NVGRE_ENCAP (1u << 24) #define > MLX5_FLOW_ACTION_NVGRE_DECAP (1u << 25) > +#define MLX5_FLOW_ACTION_RAW_ENCAP (1u << 26) #define > +MLX5_FLOW_ACTION_RAW_DECAP (1u << 27) >=20 > #define MLX5_FLOW_FATE_ACTIONS \ > (MLX5_FLOW_ACTION_DROP | MLX5_FLOW_ACTION_QUEUE | > MLX5_FLOW_ACTION_RSS) >=20 > -#define MLX5_FLOW_ENCAP_ACTIONS \ > - (MLX5_FLOW_ACTION_VXLAN_ENCAP | > MLX5_FLOW_ACTION_NVGRE_ENCAP) > +#define MLX5_FLOW_ENCAP_ACTIONS > (MLX5_FLOW_ACTION_VXLAN_ENCAP | \ > + MLX5_FLOW_ACTION_NVGRE_ENCAP | \ > + MLX5_FLOW_ACTION_RAW_ENCAP) >=20 > -#define MLX5_FLOW_DECAP_ACTIONS \ > - (MLX5_FLOW_ACTION_VXLAN_DECAP | > MLX5_FLOW_ACTION_NVGRE_DECAP) > +#define MLX5_FLOW_DECAP_ACTIONS > (MLX5_FLOW_ACTION_VXLAN_DECAP | \ > + MLX5_FLOW_ACTION_NVGRE_DECAP | \ > + MLX5_FLOW_ACTION_RAW_DECAP) >=20 > #ifndef IPPROTO_MPLS > #define IPPROTO_MPLS 137 > diff --git a/drivers/net/mlx5/mlx5_flow_dv.c > b/drivers/net/mlx5/mlx5_flow_dv.c index d7d0c6b..ca75645 100644 > --- a/drivers/net/mlx5/mlx5_flow_dv.c > +++ b/drivers/net/mlx5/mlx5_flow_dv.c > @@ -186,6 +186,82 @@ > } >=20 > /** > + * Validate the raw encap action. > + * > + * @param[in] action_flags > + * Holds the actions detected until now. > + * @param[in] action > + * Pointer to the encap action. > + * @param[in] attr > + * Pointer to flow attributes > + * @param[out] error > + * Pointer to error structure. > + * > + * @return > + * 0 on success, a negative errno value otherwise and rte_errno is set= . > + */ > +static int > +flow_dv_validate_action_raw_encap(uint64_t action_flags, > + const struct rte_flow_action *action, > + const struct rte_flow_attr *attr, > + struct rte_flow_error *error) > +{ > + if (!(action->conf)) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > action, > + "configuration cannot be null"); > + if (action_flags & MLX5_FLOW_ACTION_DROP) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > NULL, > + "can't drop and encap in same > flow"); > + if (action_flags & MLX5_FLOW_ENCAP_ACTIONS) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > NULL, > + "can only have a single encap" > + " action in a flow"); > + /* encap without preceding decap is not supported for ingress */ > + if (attr->ingress && !(action_flags & > MLX5_FLOW_ACTION_RAW_DECAP)) > + return rte_flow_error_set(error, ENOTSUP, > + > RTE_FLOW_ERROR_TYPE_ATTR_INGRESS, > + NULL, > + "encap action not supported for " > + "ingress"); The error message doesn't seems informative enough.=20 > + return 0; > +} > + > +/** > + * Validate the raw decap action. > + * > + * @param[in] action_flags > + * Holds the actions detected until now. > + * @param[out] error > + * Pointer to error structure. > + * > + * @return > + * 0 on success, a negative errno value otherwise and rte_errno is set= . > + */ > +static int > +flow_dv_validate_action_raw_decap(uint64_t action_flags, > + struct rte_flow_error *error) > +{ > + if (action_flags & MLX5_FLOW_ACTION_DROP) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > NULL, > + "can't drop and decap in same > flow"); > + if (action_flags & MLX5_FLOW_ENCAP_ACTIONS) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > NULL, > + "can't have encap action before" > + " decap action"); > + if (action_flags & MLX5_FLOW_DECAP_ACTIONS) > + return rte_flow_error_set(error, EINVAL, > + RTE_FLOW_ERROR_TYPE_ACTION, > NULL, > + "can only have a single decap" > + " action in a flow"); Just like you don't allow to do only encap w/o decap on ingress, on egress = we cannot do only decap w/o a subsequent encap.=20 > + return 0; > +} > + > +/** > * Get the size of specific rte_flow_item_type > * > * @param[in] item_type > @@ -396,6 +472,7 @@ > /** > * Convert L2 encap action to DV specification. > * Used for VXLAN and NVGRE encap actions. > + * Also used for raw encap action without preceding decap. > * > * @param[in] dev > * Pointer to rte_eth_dev structure. > @@ -414,23 +491,34 @@ > { > struct ibv_flow_action *verbs_action =3D NULL; > const struct rte_flow_item *encap_data; > + const struct rte_flow_action_raw_encap *raw_encap_data; This one can be declared inside the if statement=20 > struct priv *priv =3D dev->data->dev_private; > uint8_t buf[MLX5_ENCAP_MAX_LEN]; > + uint8_t *buf_ptr =3D buf; Why you need this buf_ptr? Compilation issue with the fixed sized array of = buf? =20 > size_t size =3D 0; > int convert_result =3D 0; >=20 > - if (action->type =3D=3D RTE_FLOW_ACTION_TYPE_VXLAN_ENCAP) > - encap_data =3D ((const struct rte_flow_action_vxlan_encap *) > + if (action->type =3D=3D RTE_FLOW_ACTION_TYPE_RAW_ENCAP) { > + raw_encap_data =3D > + (const struct rte_flow_action_raw_encap *)action- > >conf; > + buf_ptr =3D raw_encap_data->data; > + size =3D raw_encap_data->size; > + } else { > + if (action->type =3D=3D > RTE_FLOW_ACTION_TYPE_VXLAN_ENCAP) > + encap_data =3D > + ((const struct rte_flow_action_vxlan_encap > *) > action->conf)->definition; > - else > - encap_data =3D ((const struct rte_flow_action_nvgre_encap *) > + else > + encap_data =3D > + ((const struct rte_flow_action_nvgre_encap > *) > action->conf)->definition; > - convert_result =3D flow_dv_convert_encap_data(encap_data, buf, > - &size, error); > - if (convert_result) > - return NULL; > + convert_result =3D flow_dv_convert_encap_data(encap_data, > buf, > + &size, error); > + if (convert_result) > + return NULL; > + } > verbs_action =3D mlx5_glue- > >dv_create_flow_action_packet_reformat > - (priv->ctx, size, (size ? buf : NULL), > + (priv->ctx, size, (size ? buf_ptr : NULL), >=20 > MLX5DV_FLOW_ACTION_PACKET_REFORMAT_TYPE_L2_TO_L2_TUNNEL, > MLX5DV_FLOW_TABLE_TYPE_NIC_TX); > if (!verbs_action) > @@ -472,6 +560,50 @@ > } >=20 > /** > + * Convert raw decap/encap (L3 tunnel) action to DV specification. > + * > + * @param[in] dev > + * Pointer to rte_eth_dev structure. > + * @param[in] action > + * Pointer to action structure. > + * @param[in] attr > + * Pointer to the flow attributes. > + * @param[out] error > + * Pointer to the error structure. > + * > + * @return > + * Pointer to action on success, NULL otherwise and rte_errno is set. > + */ > +static struct ibv_flow_action * > +flow_dv_create_action_raw_encap(struct rte_eth_dev *dev, I would call it flow_dv_create_action_packet_reformat, as this is the only = case this function is being called.=20 For raw_encap only you will use the l2_encap function.=20 > + const struct rte_flow_action *action, > + const struct rte_flow_attr *attr, > + struct rte_flow_error *error) > +{ > + struct ibv_flow_action *verbs_action =3D NULL; > + const struct rte_flow_action_raw_encap *encap_data; > + struct priv *priv =3D dev->data->dev_private; > + enum mlx5dv_flow_action_packet_reformat_type reformat_type; > + enum mlx5dv_flow_table_type ft_type; > + > + encap_data =3D (const struct rte_flow_action_raw_encap *)action- > >conf; > + reformat_type =3D attr->egress ? > + > MLX5DV_FLOW_ACTION_PACKET_REFORMAT_TYPE_L2_TO_L3_TU > NNEL : > + > MLX5DV_FLOW_ACTION_PACKET_REFORMAT_TYPE_L3_TUNNEL_T > O_L2; > + ft_type =3D attr->egress ? > + MLX5DV_FLOW_TABLE_TYPE_NIC_TX : > + MLX5DV_FLOW_TABLE_TYPE_NIC_RX; > + verbs_action =3D mlx5_glue- > >dv_create_flow_action_packet_reformat > + (priv->ctx, encap_data->size, > + (encap_data->size ? encap_data->data : > NULL), > + reformat_type, ft_type); > + if (!verbs_action) > + rte_flow_error_set(error, EINVAL, > RTE_FLOW_ERROR_TYPE_ACTION, > + NULL, "cannot create encap action"); > + return verbs_action; > +} > + > +/** > * Verify the @p attributes will be correctly understood by the NIC and = store > * them in the @p flow if everything is correct. > * > @@ -726,7 +858,6 @@ >=20 > RTE_FLOW_ACTION_TYPE_VXLAN_ENCAP ? >=20 > MLX5_FLOW_ACTION_VXLAN_ENCAP : >=20 > MLX5_FLOW_ACTION_NVGRE_ENCAP; > - > ++actions_n; > break; > case RTE_FLOW_ACTION_TYPE_VXLAN_DECAP: > @@ -740,7 +871,23 @@ >=20 > RTE_FLOW_ACTION_TYPE_VXLAN_DECAP ? >=20 > MLX5_FLOW_ACTION_VXLAN_DECAP : >=20 > MLX5_FLOW_ACTION_NVGRE_DECAP; > - > + ++actions_n; > + break; > + case RTE_FLOW_ACTION_TYPE_RAW_ENCAP: > + ret =3D > flow_dv_validate_action_raw_encap(action_flags, > + actions, attr, > + error); > + if (ret < 0) > + return ret; > + action_flags |=3D MLX5_FLOW_ACTION_RAW_ENCAP; > + ++actions_n; > + break; > + case RTE_FLOW_ACTION_TYPE_RAW_DECAP: > + ret =3D > flow_dv_validate_action_raw_decap(action_flags, > + error); > + if (ret < 0) > + return ret; > + action_flags |=3D MLX5_FLOW_ACTION_RAW_DECAP; > ++actions_n; > break; > default: > @@ -1550,6 +1697,64 @@ > MLX5_FLOW_ACTION_NVGRE_DECAP; > actions_n++; > break; > + case RTE_FLOW_ACTION_TYPE_RAW_ENCAP: > + /* Handle encap action with preceding decap */ > + if (flow->actions & MLX5_FLOW_ACTION_RAW_DECAP) { > + dev_flow->dv.actions[actions_n].type =3D > + > MLX5DV_FLOW_ACTION_IBV_FLOW_ACTION; > + dev_flow->dv.actions[actions_n].action =3D > + flow_dv_create_action_raw_encap > + (dev, action, > + attr, error); > + if (!(dev_flow->dv.actions[actions_n].action)) > + return -rte_errno; > + dev_flow->dv.verbs_action =3D > + dev_flow->dv.actions[actions_n].action; > + } else { > + /* Handle encap action without preceding decap */ > + dev_flow->dv.actions[actions_n].type =3D > + > MLX5DV_FLOW_ACTION_IBV_FLOW_ACTION; > + dev_flow->dv.actions[actions_n].action =3D > + flow_dv_create_action_l2_encap > + (dev, action, error); > + if (!(dev_flow->dv.actions[actions_n].action)) > + return -rte_errno; > + dev_flow->dv.verbs_action =3D > + dev_flow->dv.actions[actions_n].action; > + } > + flow->actions |=3D MLX5_FLOW_ACTION_RAW_ENCAP; > + actions_n++; > + break; > + case RTE_FLOW_ACTION_TYPE_RAW_DECAP: > + /* Check if this decap action is followed by encap. */ > + for (; action->type !=3D RTE_FLOW_ACTION_TYPE_END && > + action->type !=3D RTE_FLOW_ACTION_TYPE_RAW_ENCAP; > + action++) { > + } > + /* Handle decap action only if it isn't followed by encap */ > + if (action->type !=3D RTE_FLOW_ACTION_TYPE_RAW_ENCAP) { > + /* on egress, decap without following encap is error. > */ > + if (attr->egress) > + return rte_flow_error_set > + (error, ENOTSUP, > + > RTE_FLOW_ERROR_TYPE_ATTR_EGRESS, > + NULL, > + "decap action not supported for " > + "egress"); This check should have been performed on the validate stage.=20 > + dev_flow->dv.actions[actions_n].type =3D > + > MLX5DV_FLOW_ACTION_IBV_FLOW_ACTION; > + dev_flow->dv.actions[actions_n].action =3D > + flow_dv_create_action_l2_decap > + (dev, action, error); > + if (!(dev_flow->dv.actions[actions_n].action)) > + return -rte_errno; > + dev_flow->dv.verbs_action =3D > + dev_flow->dv.actions[actions_n].action; > + actions_n++; > + } > + /* If decap is followed by encap, handle it at encap case. */ > + flow->actions |=3D MLX5_FLOW_ACTION_RAW_DECAP; > + break; > default: > break; > } > -- > 1.8.3.1