[v3] net/mlx5: support IP-in-IP tunnel

Message ID b38fcad2ae2b052b3d22d738760fab55b0ad59f9.1562752959.git.jackmin@mellanox.com (mailing list archive)
State Superseded, archived
Delegated to: Raslan Darawsheh
Headers
Series [v3] net/mlx5: support IP-in-IP tunnel |

Checks

Context Check Description
ci/checkpatch success coding style OK
ci/intel-Performance-Testing success Performance Testing PASS
ci/mellanox-Performance-Testing success Performance Testing PASS
ci/Intel-compilation success Compilation OK

Commit Message

Xiaoyu Min July 10, 2019, 10:15 a.m. UTC
  Enabled IP-in-IP tunnel type support on DV/DR flow engine.
This includes the following combination:
 - IPv4 over IPv4
 - IPv4 over IPv6
 - IPv6 over IPv4
 - IPv6 over IPv6

MLX5 NIC supports IP-in-IP tunnel via FLEX Parser so
need to make sure fw using FLEX Paser profile 0.

  mlxconfig -d <mst device> -y set FLEX_PARSER_PROFILE_ENABLE=0

Signed-off-by: Xiaoyu Min <jackmin@mellanox.com>
---
v2:
  * updated release note
v3:
  * rebased on 19.08-rc1
---
 doc/guides/nics/mlx5.rst               | 15 ++++++++++-
 doc/guides/rel_notes/release_19_08.rst |  1 +
 drivers/net/mlx5/mlx5_flow.c           | 35 ++++++++++++++++++++++++
 drivers/net/mlx5/mlx5_flow.h           |  6 ++++-
 drivers/net/mlx5/mlx5_flow_dv.c        | 37 ++++++++++++++++++++++++++
 5 files changed, 92 insertions(+), 2 deletions(-)
  

Comments

Slava Ovsiienko July 10, 2019, 2:19 p.m. UTC | #1
Hi, Xiaoyu

There is a couple of small points to note:
1) It would be good to have the testpmd flow create command sample with new tunnels in commit log.
2) is it OK: "mlx5_flow_tunnel_ip_check(items, &last_item); " ?
    It looks like a bug, should the second parameter be "&item_flags" ? (if so - please, fix all
   calls of mlx5_flow_tunnel_ip_check()) 

WBR,
Slava

> -----Original Message-----
> From: Xiaoyu Min <jackmin@mellanox.com>
> Sent: Wednesday, July 10, 2019 13:15
> To: Raslan Darawsheh <rasland@mellanox.com>; Slava Ovsiienko
> <viacheslavo@mellanox.com>; Shahaf Shuler <shahafs@mellanox.com>;
> Yongseok Koh <yskoh@mellanox.com>; John McNamara
> <john.mcnamara@intel.com>; Marko Kovacevic
> <marko.kovacevic@intel.com>
> Cc: dev@dpdk.org
> Subject: [Suspected-Phishing][PATCH v3] net/mlx5: support IP-in-IP tunnel
> 
> Enabled IP-in-IP tunnel type support on DV/DR flow engine.
> This includes the following combination:
>  - IPv4 over IPv4
>  - IPv4 over IPv6
>  - IPv6 over IPv4
>  - IPv6 over IPv6
> 
> MLX5 NIC supports IP-in-IP tunnel via FLEX Parser so need to make sure fw
> using FLEX Paser profile 0.
> 
>   mlxconfig -d <mst device> -y set FLEX_PARSER_PROFILE_ENABLE=0
> 
> Signed-off-by: Xiaoyu Min <jackmin@mellanox.com>
> ---
> v2:
>   * updated release note
> v3:
>   * rebased on 19.08-rc1
> ---
>  doc/guides/nics/mlx5.rst               | 15 ++++++++++-
>  doc/guides/rel_notes/release_19_08.rst |  1 +
>  drivers/net/mlx5/mlx5_flow.c           | 35 ++++++++++++++++++++++++
>  drivers/net/mlx5/mlx5_flow.h           |  6 ++++-
>  drivers/net/mlx5/mlx5_flow_dv.c        | 37 ++++++++++++++++++++++++++
>  5 files changed, 92 insertions(+), 2 deletions(-)
>
  
Slava Ovsiienko July 10, 2019, 2:35 p.m. UTC | #2
Regarding point 2) - it is OK, there is common flags update in the item validation loop.
So, after update point 1) - you can add my Acked-by to the patch, thanks.

WBR,
Slava

> -----Original Message-----
> From: dev <dev-bounces@dpdk.org> On Behalf Of Slava Ovsiienko
> Sent: Wednesday, July 10, 2019 17:20
> To: Jack Min <jackmin@mellanox.com>; Raslan Darawsheh
> <rasland@mellanox.com>; Shahaf Shuler <shahafs@mellanox.com>;
> Yongseok Koh <yskoh@mellanox.com>; John McNamara
> <john.mcnamara@intel.com>; Marko Kovacevic
> <marko.kovacevic@intel.com>
> Cc: dev@dpdk.org
> Subject: Re: [dpdk-dev] [Suspected-Phishing][PATCH v3] net/mlx5: support
> IP-in-IP tunnel
> 
> Hi, Xiaoyu
> 
> There is a couple of small points to note:
> 1) It would be good to have the testpmd flow create command sample with
> new tunnels in commit log.
> 2) is it OK: "mlx5_flow_tunnel_ip_check(items, &last_item); " ?
>     It looks like a bug, should the second parameter be "&item_flags" ? (if so -
> please, fix all
>    calls of mlx5_flow_tunnel_ip_check())
> 
> WBR,
> Slava
> 
> > -----Original Message-----
> > From: Xiaoyu Min <jackmin@mellanox.com>
> > Sent: Wednesday, July 10, 2019 13:15
> > To: Raslan Darawsheh <rasland@mellanox.com>; Slava Ovsiienko
> > <viacheslavo@mellanox.com>; Shahaf Shuler <shahafs@mellanox.com>;
> > Yongseok Koh <yskoh@mellanox.com>; John McNamara
> > <john.mcnamara@intel.com>; Marko Kovacevic
> <marko.kovacevic@intel.com>
> > Cc: dev@dpdk.org
> > Subject: [Suspected-Phishing][PATCH v3] net/mlx5: support IP-in-IP
> > tunnel
> >
> > Enabled IP-in-IP tunnel type support on DV/DR flow engine.
> > This includes the following combination:
> >  - IPv4 over IPv4
> >  - IPv4 over IPv6
> >  - IPv6 over IPv4
> >  - IPv6 over IPv6
> >
> > MLX5 NIC supports IP-in-IP tunnel via FLEX Parser so need to make sure
> > fw using FLEX Paser profile 0.
> >
> >   mlxconfig -d <mst device> -y set FLEX_PARSER_PROFILE_ENABLE=0
> >
> > Signed-off-by: Xiaoyu Min <jackmin@mellanox.com>
> > ---
> > v2:
> >   * updated release note
> > v3:
> >   * rebased on 19.08-rc1
> > ---
> >  doc/guides/nics/mlx5.rst               | 15 ++++++++++-
> >  doc/guides/rel_notes/release_19_08.rst |  1 +
> >  drivers/net/mlx5/mlx5_flow.c           | 35 ++++++++++++++++++++++++
> >  drivers/net/mlx5/mlx5_flow.h           |  6 ++++-
> >  drivers/net/mlx5/mlx5_flow_dv.c        | 37 ++++++++++++++++++++++++++
> >  5 files changed, 92 insertions(+), 2 deletions(-)
> >
  
Xiaoyu Min July 10, 2019, 2:40 p.m. UTC | #3
On Wed, 19-07-10, 22:35, Slava Ovsiienko wrote:
> Regarding point 2) - it is OK, there is common flags update in the item validation loop.
> So, after update point 1) - you can add my Acked-by to the patch, thanks.
Great! thank you~
I'll update it soon.

> 
> WBR,
> Slava
> 
> > -----Original Message-----
> > From: dev <dev-bounces@dpdk.org> On Behalf Of Slava Ovsiienko
> > Sent: Wednesday, July 10, 2019 17:20
> > To: Jack Min <jackmin@mellanox.com>; Raslan Darawsheh
> > <rasland@mellanox.com>; Shahaf Shuler <shahafs@mellanox.com>;
> > Yongseok Koh <yskoh@mellanox.com>; John McNamara
> > <john.mcnamara@intel.com>; Marko Kovacevic
> > <marko.kovacevic@intel.com>
> > Cc: dev@dpdk.org
> > Subject: Re: [dpdk-dev] [Suspected-Phishing][PATCH v3] net/mlx5: support
> > IP-in-IP tunnel
> > 
> > Hi, Xiaoyu
> > 
> > There is a couple of small points to note:
> > 1) It would be good to have the testpmd flow create command sample with
> > new tunnels in commit log.
> > 2) is it OK: "mlx5_flow_tunnel_ip_check(items, &last_item); " ?
> >     It looks like a bug, should the second parameter be "&item_flags" ? (if so -
> > please, fix all
> >    calls of mlx5_flow_tunnel_ip_check())
> > 
> > WBR,
> > Slava
> > 
> > > -----Original Message-----
> > > From: Xiaoyu Min <jackmin@mellanox.com>
> > > Sent: Wednesday, July 10, 2019 13:15
> > > To: Raslan Darawsheh <rasland@mellanox.com>; Slava Ovsiienko
> > > <viacheslavo@mellanox.com>; Shahaf Shuler <shahafs@mellanox.com>;
> > > Yongseok Koh <yskoh@mellanox.com>; John McNamara
> > > <john.mcnamara@intel.com>; Marko Kovacevic
> > <marko.kovacevic@intel.com>
> > > Cc: dev@dpdk.org
> > > Subject: [Suspected-Phishing][PATCH v3] net/mlx5: support IP-in-IP
> > > tunnel
> > >
> > > Enabled IP-in-IP tunnel type support on DV/DR flow engine.
> > > This includes the following combination:
> > >  - IPv4 over IPv4
> > >  - IPv4 over IPv6
> > >  - IPv6 over IPv4
> > >  - IPv6 over IPv6
> > >
> > > MLX5 NIC supports IP-in-IP tunnel via FLEX Parser so need to make sure
> > > fw using FLEX Paser profile 0.
> > >
> > >   mlxconfig -d <mst device> -y set FLEX_PARSER_PROFILE_ENABLE=0
> > >
> > > Signed-off-by: Xiaoyu Min <jackmin@mellanox.com>
> > > ---
> > > v2:
> > >   * updated release note
> > > v3:
> > >   * rebased on 19.08-rc1
> > > ---
> > >  doc/guides/nics/mlx5.rst               | 15 ++++++++++-
> > >  doc/guides/rel_notes/release_19_08.rst |  1 +
> > >  drivers/net/mlx5/mlx5_flow.c           | 35 ++++++++++++++++++++++++
> > >  drivers/net/mlx5/mlx5_flow.h           |  6 ++++-
> > >  drivers/net/mlx5/mlx5_flow_dv.c        | 37 ++++++++++++++++++++++++++
> > >  5 files changed, 92 insertions(+), 2 deletions(-)
> > >
  

Patch

diff --git a/doc/guides/nics/mlx5.rst b/doc/guides/nics/mlx5.rst
index 20cbba7ace..16aa390380 100644
--- a/doc/guides/nics/mlx5.rst
+++ b/doc/guides/nics/mlx5.rst
@@ -76,7 +76,7 @@  Features
 - RX interrupts.
 - Statistics query including Basic, Extended and per queue.
 - Rx HW timestamp.
-- Tunnel types: VXLAN, L3 VXLAN, VXLAN-GPE, GRE, MPLSoGRE, MPLSoUDP.
+- Tunnel types: VXLAN, L3 VXLAN, VXLAN-GPE, GRE, MPLSoGRE, MPLSoUDP, IP-in-IP.
 - Tunnel HW offloads: packet type, inner/outer RSS, IP and UDP checksum verification.
 - NIC HW offloads: encapsulation (vxlan, gre, mplsoudp, mplsogre), NAT, routing, TTL
   increment/decrement, count, drop, mark. For details please see :ref:`Supported hardware offloads using rte_flow API`.
@@ -540,6 +540,19 @@  Firmware configuration
      mlxconfig -d <mst device> query | grep FLEX_PARSER_PROFILE_ENABLE
      FLEX_PARSER_PROFILE_ENABLE         2
 
+- IP-in-IP tunnel enable
+
+   .. code-block:: console
+
+     mlxconfig -d <mst device> set FLEX_PARSER_PROFILE_ENABLE=0
+
+  Verify configurations are set:
+
+   .. code-block:: console
+
+     mlxconfig -d <mst device> query | grep FLEX_PARSER_PROFILE_ENABLE
+     FLEX_PARSER_PROFILE_ENABLE          0
+
 Prerequisites
 -------------
 
diff --git a/doc/guides/rel_notes/release_19_08.rst b/doc/guides/rel_notes/release_19_08.rst
index 27d5915bed..a9ec6adb69 100644
--- a/doc/guides/rel_notes/release_19_08.rst
+++ b/doc/guides/rel_notes/release_19_08.rst
@@ -112,6 +112,7 @@  New Features
   * Updated the packet header modification feature. Added support of TCP header
     sequence number and acknowledgment number modification.
   * Added support for match on ICMP/ICMP6 code and type.
+  * Added support for IP-in-IP tunnel.
 
 * **Updated Solarflare network PMD.**
 
diff --git a/drivers/net/mlx5/mlx5_flow.c b/drivers/net/mlx5/mlx5_flow.c
index 534cd9338e..005a1a69a7 100644
--- a/drivers/net/mlx5/mlx5_flow.c
+++ b/drivers/net/mlx5/mlx5_flow.c
@@ -1282,6 +1282,7 @@  mlx5_flow_validate_item_ipv4(const struct rte_flow_item *item,
 			     struct rte_flow_error *error)
 {
 	const struct rte_flow_item_ipv4 *mask = item->mask;
+	const struct rte_flow_item_ipv4 *spec = item->spec;
 	const struct rte_flow_item_ipv4 nic_mask = {
 		.hdr = {
 			.src_addr = RTE_BE32(0xffffffff),
@@ -1296,7 +1297,24 @@  mlx5_flow_validate_item_ipv4(const struct rte_flow_item *item,
 	const uint64_t l4m = tunnel ? MLX5_FLOW_LAYER_INNER_L4 :
 				      MLX5_FLOW_LAYER_OUTER_L4;
 	int ret;
+	uint8_t next_proto = 0xFF;
 
+	if (item_flags & MLX5_FLOW_LAYER_IPIP) {
+		if (mask && spec)
+			next_proto = mask->hdr.next_proto_id &
+				     spec->hdr.next_proto_id;
+		if (next_proto == IPPROTO_IPIP || next_proto == IPPROTO_IPV6)
+			return rte_flow_error_set(error, EINVAL,
+						  RTE_FLOW_ERROR_TYPE_ITEM,
+						  item,
+						  "multiple tunnel "
+						  "not supported");
+	}
+	if (item_flags & MLX5_FLOW_LAYER_IPV6_ENCAP)
+		return rte_flow_error_set(error, EINVAL,
+					  RTE_FLOW_ERROR_TYPE_ITEM, item,
+					  "wrong tunnel type - IPv6 specified "
+					  "but IPv4 item provided");
 	if (item_flags & l3m)
 		return rte_flow_error_set(error, ENOTSUP,
 					  RTE_FLOW_ERROR_TYPE_ITEM, item,
@@ -1346,6 +1364,7 @@  mlx5_flow_validate_item_ipv6(const struct rte_flow_item *item,
 			     struct rte_flow_error *error)
 {
 	const struct rte_flow_item_ipv6 *mask = item->mask;
+	const struct rte_flow_item_ipv6 *spec = item->spec;
 	const struct rte_flow_item_ipv6 nic_mask = {
 		.hdr = {
 			.src_addr =
@@ -1365,7 +1384,23 @@  mlx5_flow_validate_item_ipv6(const struct rte_flow_item *item,
 	const uint64_t l4m = tunnel ? MLX5_FLOW_LAYER_INNER_L4 :
 				      MLX5_FLOW_LAYER_OUTER_L4;
 	int ret;
+	uint8_t next_proto = 0xFF;
 
+	if (item_flags & MLX5_FLOW_LAYER_IPV6_ENCAP) {
+		if (mask && spec)
+			next_proto = mask->hdr.proto & spec->hdr.proto;
+		if (next_proto == IPPROTO_IPIP || next_proto == IPPROTO_IPV6)
+			return rte_flow_error_set(error, EINVAL,
+						  RTE_FLOW_ERROR_TYPE_ITEM,
+						  item,
+						  "multiple tunnel "
+						  "not supported");
+	}
+	if (item_flags & MLX5_FLOW_LAYER_IPIP)
+		return rte_flow_error_set(error, EINVAL,
+					  RTE_FLOW_ERROR_TYPE_ITEM, item,
+					  "wrong tunnel type - IPv4 specified "
+					  "but IPv6 item provided");
 	if (item_flags & l3m)
 		return rte_flow_error_set(error, ENOTSUP,
 					  RTE_FLOW_ERROR_TYPE_ITEM, item,
diff --git a/drivers/net/mlx5/mlx5_flow.h b/drivers/net/mlx5/mlx5_flow.h
index 3d7fcf706e..ef430d6d44 100644
--- a/drivers/net/mlx5/mlx5_flow.h
+++ b/drivers/net/mlx5/mlx5_flow.h
@@ -54,6 +54,9 @@ 
 #define MLX5_FLOW_LAYER_ICMP (1u << 18)
 #define MLX5_FLOW_LAYER_ICMP6 (1u << 19)
 
+#define MLX5_FLOW_LAYER_IPIP (1u << 20)
+#define MLX5_FLOW_LAYER_IPV6_ENCAP (1u << 21)
+
 /* Outer Masks. */
 #define MLX5_FLOW_LAYER_OUTER_L3 \
 	(MLX5_FLOW_LAYER_OUTER_L3_IPV4 | MLX5_FLOW_LAYER_OUTER_L3_IPV6)
@@ -66,7 +69,8 @@ 
 /* Tunnel Masks. */
 #define MLX5_FLOW_LAYER_TUNNEL \
 	(MLX5_FLOW_LAYER_VXLAN | MLX5_FLOW_LAYER_VXLAN_GPE | \
-	 MLX5_FLOW_LAYER_GRE | MLX5_FLOW_LAYER_MPLS)
+	 MLX5_FLOW_LAYER_GRE | MLX5_FLOW_LAYER_MPLS | \
+	 MLX5_FLOW_LAYER_IPIP | MLX5_FLOW_LAYER_IPV6_ENCAP)
 
 /* Inner Masks. */
 #define MLX5_FLOW_LAYER_INNER_L3 \
diff --git a/drivers/net/mlx5/mlx5_flow_dv.c b/drivers/net/mlx5/mlx5_flow_dv.c
index 9cc09e73c9..54c1b9f2e1 100644
--- a/drivers/net/mlx5/mlx5_flow_dv.c
+++ b/drivers/net/mlx5/mlx5_flow_dv.c
@@ -141,6 +141,39 @@  struct field_modify_info modify_tcp[] = {
 	{0, 0, 0},
 };
 
+static void
+mlx5_flow_tunnel_ip_check(const struct rte_flow_item *item, uint64_t *flags)
+{
+	uint8_t next_protocol = 0xFF;
+
+	if (item->mask != NULL) {
+		switch (item->type) {
+		case RTE_FLOW_ITEM_TYPE_IPV4:
+			next_protocol =
+				((const struct rte_flow_item_ipv4 *)
+				 (item->spec))->hdr.next_proto_id;
+			next_protocol &=
+				((const struct rte_flow_item_ipv4 *)
+				 (item->mask))->hdr.next_proto_id;
+			break;
+		case RTE_FLOW_ITEM_TYPE_IPV6:
+			next_protocol =
+				((const struct rte_flow_item_ipv6 *)
+				 (item->spec))->hdr.proto;
+			next_protocol &=
+				((const struct rte_flow_item_ipv6 *)
+				 (item->mask))->hdr.proto;
+			break;
+		default:
+			break;
+		}
+	}
+	if (next_protocol == IPPROTO_IPIP)
+		*flags |= MLX5_FLOW_LAYER_IPIP;
+	if (next_protocol == IPPROTO_IPV6)
+		*flags |= MLX5_FLOW_LAYER_IPV6_ENCAP;
+}
+
 /**
  * Acquire the synchronizing object to protect multithreaded access
  * to shared dv context. Lock occurs only if context is actually
@@ -2355,6 +2388,7 @@  flow_dv_validate(struct rte_eth_dev *dev, const struct rte_flow_attr *attr,
 				/* Reset for inner layer. */
 				next_protocol = 0xff;
 			}
+			mlx5_flow_tunnel_ip_check(items, &last_item);
 			break;
 		case RTE_FLOW_ITEM_TYPE_IPV6:
 			ret = mlx5_flow_validate_item_ipv6(items, item_flags,
@@ -2376,6 +2410,7 @@  flow_dv_validate(struct rte_eth_dev *dev, const struct rte_flow_attr *attr,
 				/* Reset for inner layer. */
 				next_protocol = 0xff;
 			}
+			mlx5_flow_tunnel_ip_check(items, &last_item);
 			break;
 		case RTE_FLOW_ITEM_TYPE_TCP:
 			ret = mlx5_flow_validate_item_tcp
@@ -4348,6 +4383,7 @@  flow_dv_translate(struct rte_eth_dev *dev,
 					 MLX5_IPV4_IBV_RX_HASH);
 			last_item = tunnel ? MLX5_FLOW_LAYER_INNER_L3_IPV4 :
 					     MLX5_FLOW_LAYER_OUTER_L3_IPV4;
+			mlx5_flow_tunnel_ip_check(items, &last_item);
 			break;
 		case RTE_FLOW_ITEM_TYPE_IPV6:
 			flow_dv_translate_item_ipv6(match_mask, match_value,
@@ -4360,6 +4396,7 @@  flow_dv_translate(struct rte_eth_dev *dev,
 					 MLX5_IPV6_IBV_RX_HASH);
 			last_item = tunnel ? MLX5_FLOW_LAYER_INNER_L3_IPV6 :
 					     MLX5_FLOW_LAYER_OUTER_L3_IPV6;
+			mlx5_flow_tunnel_ip_check(items, &last_item);
 			break;
 		case RTE_FLOW_ITEM_TYPE_TCP:
 			flow_dv_translate_item_tcp(match_mask, match_value,