DPDK patches and discussions
 help / color / Atom feed
* [dpdk-dev] [PATCH v1 0/3] Add GENEVE protocol parsing to testpmd
@ 2020-07-29  8:29 Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                   ` (2 more replies)
  0 siblings, 3 replies; 50+ messages in thread
From: Ophir Munk @ 2020-07-29  8:29 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Thomas Monjalon
  Cc: Ophir Munk

This patchset adds GENEVE parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd,
Ethernet-0x6558) based on IETF draft-ietf-nvo3-geneve-09.

v1:
Initial version

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: reduce tunnel parsing code duplication

 app/test-pmd/csumonly.c     | 120 ++++++++++++++++++++++++++++----------------
 app/test-pmd/parameters.c   |  13 ++++-
 app/test-pmd/testpmd.h      |   1 +
 lib/librte_net/Makefile     |   2 +-
 lib/librte_net/meson.build  |   3 +-
 lib/librte_net/rte_geneve.h |  72 ++++++++++++++++++++++++++
 lib/librte_net/rte_vxlan.h  |   1 +
 7 files changed, 167 insertions(+), 45 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v1 1/3] app/testpmd: add GENEVE parsing
  2020-07-29  8:29 [dpdk-dev] [PATCH v1 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-07-29  8:29 ` Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-07-29  8:29 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Thomas Monjalon
  Cc: Ophir Munk

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/Makefile     |  2 +-
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++
 5 files changed, 145 insertions(+), 3 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 0a96b24..5f29868 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_GENEVE_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -873,9 +933,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index 25a12b1..a60e009 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -456,6 +456,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/Makefile b/lib/librte_net/Makefile
index 9830e77..9fe99af 100644
--- a/lib/librte_net/Makefile
+++ b/lib/librte_net/Makefile
@@ -20,6 +20,6 @@ SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_sctp.h rte_icmp.h rte_arp.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ether.h rte_gre.h rte_net.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_net_crc.h rte_mpls.h rte_higig.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_gtp.h rte_vxlan.h
-SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ecpri.h
+SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ecpri.h rte_geneve.h
 
 include $(RTE_SDK)/mk/rte.lib.mk
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..a1b69c7
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+
+#include <stdint.h>
+
+#include <rte_udp.h>
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on reciept).
+ * More-bits (optinal) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t oam:1;		/**< Control packet (1). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+#else
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t oam:1;		/**< Control packet (1). */
+#endif
+	rte_be16_t proto;	/**< Protocol type (16). */
+	uint8_t vni[3];		/**< Virtual network identifier (24). */
+	uint8_t rsvd2;		/**< Reserved (8). */
+	char	opts[0];	/**<Variable length options. */
+} __rte_packed;
+
+/* GENEVE next protocol types */
+#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol. */
+#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol. */
+#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v1 2/3] app/testpmd: enable configuring GENEVE port
  2020-07-29  8:29 [dpdk-dev] [PATCH v1 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-07-29  8:29 ` Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-07-29  8:29 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Thomas Monjalon
  Cc: Ophir Munk

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 7cb0e3d..0d135b0 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,7 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
 	       "--txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= ]\n",
+	       "--vxlan-gpe-port= ] "
+	       "--geneve-port= ]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -199,6 +200,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -664,6 +666,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1298,6 +1301,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
-- 
2.8.4


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

* [dpdk-dev] [PATCH v1 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-07-29  8:29 [dpdk-dev] [PATCH v1 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-07-29  8:29 ` Ophir Munk
  2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-07-29  8:29 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Thomas Monjalon
  Cc: Ophir Munk

This is a cleanup commit. It assembles all tunnel outer updates into one
function call to avoid code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
 lib/librte_net/rte_vxlan.h |  1 +
 2 files changed, 21 insertions(+), 52 deletions(-)

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 5f29868..3a0e46e 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -257,11 +264,7 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +294,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +304,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +314,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +326,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +392,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +401,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +410,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd
  2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
@ 2020-08-27  7:02   ` Ophir Munk
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                       ` (3 more replies)
  0 siblings, 4 replies; 50+ messages in thread
From: Ophir Munk @ 2020-08-27  7:02 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

This patchset adds GENEVE parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd,
Ethernet-0x6558) based on IETF draft-ietf-nvo3-geneve-09.

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: reduce tunnel parsing code duplication

 app/test-pmd/csumonly.c     | 120 ++++++++++++++++++++++++++++----------------
 app/test-pmd/parameters.c   |  13 ++++-
 app/test-pmd/testpmd.h      |   1 +
 lib/librte_net/Makefile     |   2 +-
 lib/librte_net/meson.build  |   3 +-
 lib/librte_net/rte_geneve.h |  72 ++++++++++++++++++++++++++
 lib/librte_net/rte_vxlan.h  |   1 +
 7 files changed, 167 insertions(+), 45 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing
  2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-08-27  7:02     ` Ophir Munk
  2020-09-14 17:27       ` Ferruh Yigit
  2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
                       ` (2 subsequent siblings)
  3 siblings, 2 replies; 50+ messages in thread
From: Ophir Munk @ 2020-08-27  7:02 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/Makefile     |  2 +-
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++
 5 files changed, 145 insertions(+), 3 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 0a96b24..5f29868 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_GENEVE_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -873,9 +933,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index 25a12b1..a60e009 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -456,6 +456,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/Makefile b/lib/librte_net/Makefile
index 9830e77..9fe99af 100644
--- a/lib/librte_net/Makefile
+++ b/lib/librte_net/Makefile
@@ -20,6 +20,6 @@ SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_sctp.h rte_icmp.h rte_arp.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ether.h rte_gre.h rte_net.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_net_crc.h rte_mpls.h rte_higig.h
 SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_gtp.h rte_vxlan.h
-SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ecpri.h
+SYMLINK-$(CONFIG_RTE_LIBRTE_NET)-include += rte_ecpri.h rte_geneve.h
 
 include $(RTE_SDK)/mk/rte.lib.mk
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..a7101c8
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+
+#include <stdint.h>
+
+#include <rte_udp.h>
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on reciept).
+ * More-bits (optinal) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t oam:1;		/**< Control packet (1). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+#else
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t oam:1;		/**< Control packet (1). */
+#endif
+	rte_be16_t proto;	/**< Protocol type (16). */
+	uint8_t vni[3];		/**< Virtual network identifier (24). */
+	uint8_t rsvd2;		/**< Reserved (8). */
+	uint8_t opts[];		/**<Variable length options. */
+} __rte_packed;
+
+/* GENEVE next protocol types */
+#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol. */
+#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol. */
+#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-08-27  7:02     ` Ophir Munk
  2020-09-14 17:31       ` Ferruh Yigit
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2020-08-31  6:40     ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  3 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-08-27  7:02 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 7cb0e3d..0d135b0 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,7 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
 	       "--txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= ]\n",
+	       "--vxlan-gpe-port= ] "
+	       "--geneve-port= ]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -199,6 +200,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -664,6 +666,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1298,6 +1301,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
-- 
2.8.4


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

* [dpdk-dev] [PATCH v2 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-08-27  7:02     ` Ophir Munk
  2020-08-31  6:40     ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-08-27  7:02 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit. It assembles all tunnel outer updates into one
function call to avoid code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
 lib/librte_net/rte_vxlan.h |  1 +
 2 files changed, 21 insertions(+), 52 deletions(-)

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 5f29868..3a0e46e 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -257,11 +264,7 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +294,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +304,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +314,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +326,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +392,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +401,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +410,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd
  2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
                       ` (2 preceding siblings ...)
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
@ 2020-08-31  6:40     ` Ophir Munk
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-08-31  6:40 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

Hello Wenzhou, Beilei, Bernard,
I saw no comments regarding v1 or v2 of this patch set.
Please let me know if you have any question. Otherwise - can it be merged?

Regards,
Ophir

> -----Original Message-----
> From: Ophir Munk <ophirmu@nvidia.com>
> Sent: Thursday, August 27, 2020 10:03 AM
> To: dev@dpdk.org; Wenzhuo Lu <wenzhuo.lu@intel.com>; Beilei Xing
> <beilei.xing@intel.com>; Bernard Iremonger
> <bernard.iremonger@intel.com>
> Cc: Ophir Munk <ophirmu@mellanox.com>
> Subject: [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd
> 
> This patchset adds GENEVE parsing of inner protocols (IPv4-0x0800, IPv6-
> 0x86dd,
> Ethernet-0x6558) based on IETF draft-ietf-nvo3-geneve-09.
> 
> v1:
> Initial version
> v2:
> Rebased + Minor update in protocol options field:
> char opts[0] ===> uint8_t opts[]
> 
> Ophir Munk (3):
>   app/testpmd: add GENEVE parsing
>   app/testpmd: enable configuring GENEVE port
>   app/testpmd: reduce tunnel parsing code duplication
> 
>  app/test-pmd/csumonly.c     | 120 ++++++++++++++++++++++++++++---------
> -------
>  app/test-pmd/parameters.c   |  13 ++++-
>  app/test-pmd/testpmd.h      |   1 +
>  lib/librte_net/Makefile     |   2 +-
>  lib/librte_net/meson.build  |   3 +-
>  lib/librte_net/rte_geneve.h |  72 ++++++++++++++++++++++++++
>  lib/librte_net/rte_vxlan.h  |   1 +
>  7 files changed, 167 insertions(+), 45 deletions(-)  create mode 100644
> lib/librte_net/rte_geneve.h
> 
> --
> 2.8.4


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

* Re: [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-14 17:27       ` Ferruh Yigit
  2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  1 sibling, 0 replies; 50+ messages in thread
From: Ferruh Yigit @ 2020-09-14 17:27 UTC (permalink / raw)
  To: Ophir Munk, Wenzhuo Lu, Beilei Xing, Bernard Iremonger
  Cc: Ophir Munk, dev, Olivier Matz

On 8/27/2020 8:02 AM, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> GENEVE is a widely used tunneling protocol in modern Virtualized
> Networks. testpmd already supports parsing of several tunneling
> protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
> parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
> based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
> flexible than the other protocols.  In terms of protocol format GENEVE
> header has a variable length options as opposed to other tunneling
> protocols which have a fixed header size.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>  app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
>  app/test-pmd/testpmd.h      |  1 +
>  lib/librte_net/Makefile     |  2 +-
>  lib/librte_net/meson.build  |  3 +-
>  lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++


cc'ed Oliver for the 'rte_geneve.h' part.


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

* Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-09-14 17:31       ` Ferruh Yigit
  2020-09-15  8:46         ` Ophir Munk
  0 siblings, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-09-14 17:31 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger; +Cc: Ophir Munk

On 8/27/2020 8:02 AM, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> IANA has assigned port 6081 as the fixed well-known destination port for
> GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
> implementations make this configurable.  This commit enables specifying
> any positive UDP destination port number for GENEVE.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>  app/test-pmd/parameters.c | 13 ++++++++++++-
>  1 file changed, 12 insertions(+), 1 deletion(-)
> 
> diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
> index 7cb0e3d..0d135b0 100644
> --- a/app/test-pmd/parameters.c
> +++ b/app/test-pmd/parameters.c
> @@ -70,7 +70,8 @@ usage(char* progname)
>  	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
>  	       "--txpt= | --txht= | --txwt= | --txfreet= | "
>  	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
> -	       "--vxlan-gpe-port= ]\n",
> +	       "--vxlan-gpe-port= ] "
> +	       "--geneve-port= ]\n",
>  	       progname);

Hi Ophir,

Is there a command line to update the geneve port?

I can see there are some parameter for other tunneling too, but do you
find providing parameter useful? I think command line better since it is
more flexible, what do you think?

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

* Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-14 17:31       ` Ferruh Yigit
@ 2020-09-15  8:46         ` Ophir Munk
  2020-09-15 11:07           ` Ferruh Yigit
  0 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-09-15  8:46 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger
  Cc: Ophir Munk, Raslan Darawsheh

Hi Ferruh,
I don't think that having the flexibility to specify the Geneve protocol in the command line will have an added value.
The reason is that any Geneve setup has a fixed protocol number for the duration of the test lifetime (fixed and synched by all the peers in the lab). The protocol number is not dynamic.
So even if we could specify the protocol in the command line - it would be a onetime setting after testpmd startup. Therefore, it is simpler to have it as parameter only.

Regards,
Ophir 

> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> Sent: Monday, September 14, 2020 8:31 PM
> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
> <wenzhuo.lu@intel.com>; Beilei Xing <beilei.xing@intel.com>; Bernard
> Iremonger <bernard.iremonger@intel.com>
> Cc: Ophir Munk <ophirmu@mellanox.com>
> Subject: Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring
> GENEVE port
> 
> On 8/27/2020 8:02 AM, Ophir Munk wrote:
> > From: Ophir Munk <ophirmu@mellanox.com>
> >
> > IANA has assigned port 6081 as the fixed well-known destination port
> > for GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
> > implementations make this configurable.  This commit enables
> > specifying any positive UDP destination port number for GENEVE.
> >
> > Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> > ---
> >  app/test-pmd/parameters.c | 13 ++++++++++++-
> >  1 file changed, 12 insertions(+), 1 deletion(-)
> >
> > diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
> > index 7cb0e3d..0d135b0 100644
> > --- a/app/test-pmd/parameters.c
> > +++ b/app/test-pmd/parameters.c
> > @@ -70,7 +70,8 @@ usage(char* progname)
> >  	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
> >  	       "--txpt= | --txht= | --txwt= | --txfreet= | "
> >  	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
> > -	       "--vxlan-gpe-port= ]\n",
> > +	       "--vxlan-gpe-port= ] "
> > +	       "--geneve-port= ]\n",
> >  	       progname);
> 
> Hi Ophir,
> 
> Is there a command line to update the geneve port?
> 
> I can see there are some parameter for other tunneling too, but do you find
> providing parameter useful? I think command line better since it is more
> flexible, what do you think?

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

* Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-15  8:46         ` Ophir Munk
@ 2020-09-15 11:07           ` Ferruh Yigit
  2020-09-15 12:59             ` Ophir Munk
  0 siblings, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-09-15 11:07 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger
  Cc: Ophir Munk, Raslan Darawsheh

On 9/15/2020 9:46 AM, Ophir Munk wrote:
> Hi Ferruh,
> I don't think that having the flexibility to specify the Geneve protocol in the command line will have an added value.
> The reason is that any Geneve setup has a fixed protocol number for the duration of the test lifetime (fixed and synched by all the peers in the lab). The protocol number is not dynamic.
> So even if we could specify the protocol in the command line - it would be a onetime setting after testpmd startup. Therefore, it is simpler to have it as parameter only.
> 

OK, if you think there is a value.

Overall, not specific to this patch, it bothers me not having any
guideline what to add as a parameter, and not able to say what is
implemented as parameter without searching for it ...

> Regards,
> Ophir 
> 
>> -----Original Message-----
>> From: Ferruh Yigit <ferruh.yigit@intel.com>
>> Sent: Monday, September 14, 2020 8:31 PM
>> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
>> <wenzhuo.lu@intel.com>; Beilei Xing <beilei.xing@intel.com>; Bernard
>> Iremonger <bernard.iremonger@intel.com>
>> Cc: Ophir Munk <ophirmu@mellanox.com>
>> Subject: Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring
>> GENEVE port
>>
>> On 8/27/2020 8:02 AM, Ophir Munk wrote:
>>> From: Ophir Munk <ophirmu@mellanox.com>
>>>
>>> IANA has assigned port 6081 as the fixed well-known destination port
>>> for GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
>>> implementations make this configurable.  This commit enables
>>> specifying any positive UDP destination port number for GENEVE.
>>>
>>> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
>>> ---
>>>  app/test-pmd/parameters.c | 13 ++++++++++++-
>>>  1 file changed, 12 insertions(+), 1 deletion(-)
>>>
>>> diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
>>> index 7cb0e3d..0d135b0 100644
>>> --- a/app/test-pmd/parameters.c
>>> +++ b/app/test-pmd/parameters.c
>>> @@ -70,7 +70,8 @@ usage(char* progname)
>>>  	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
>>>  	       "--txpt= | --txht= | --txwt= | --txfreet= | "
>>>  	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
>>> -	       "--vxlan-gpe-port= ]\n",
>>> +	       "--vxlan-gpe-port= ] "
>>> +	       "--geneve-port= ]\n",
>>>  	       progname);
>>
>> Hi Ophir,
>>
>> Is there a command line to update the geneve port?
>>
>> I can see there are some parameter for other tunneling too, but do you find
>> providing parameter useful? I think command line better since it is more
>> flexible, what do you think?


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

* [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd
  2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-14 17:27       ` Ferruh Yigit
@ 2020-09-15 12:53       ` Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                           ` (2 more replies)
  1 sibling, 3 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 12:53 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit; +Cc: Ophir Munk

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]
v3:
Rebase
document "geneve-port=N" parameter

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: reduce tunnel parsing code duplication

 app/test-pmd/csumonly.c               | 120 ++++++++++++++++++++++------------
 app/test-pmd/parameters.c             |  14 +++-
 app/test-pmd/testpmd.h                |   1 +
 doc/guides/testpmd_app_ug/run_app.rst |   5 ++
 lib/librte_net/meson.build            |   3 +-
 lib/librte_net/rte_geneve.h           |  72 ++++++++++++++++++++
 lib/librte_net/rte_vxlan.h            |   1 +
 7 files changed, 171 insertions(+), 45 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing
  2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-09-15 12:53         ` Ophir Munk
  2020-09-15 13:17           ` [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 12:53 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 144 insertions(+), 2 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 7ece398..eb87b9b 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_GENEVE_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index a8ae5cc..f405d4e 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..a7101c8
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+
+#include <stdint.h>
+
+#include <rte_udp.h>
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on reciept).
+ * More-bits (optinal) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t oam:1;		/**< Control packet (1). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+#else
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t oam:1;		/**< Control packet (1). */
+#endif
+	rte_be16_t proto;	/**< Protocol type (16). */
+	uint8_t vni[3];		/**< Virtual network identifier (24). */
+	uint8_t rsvd2;		/**< Reserved (8). */
+	uint8_t opts[];		/**<Variable length options. */
+} __rte_packed;
+
+/* GENEVE next protocol types */
+#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol. */
+#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol. */
+#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v3 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-15 12:53         ` Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 12:53 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c             | 14 ++++++++++++--
 doc/guides/testpmd_app_ug/run_app.rst |  5 +++++
 2 files changed, 17 insertions(+), 2 deletions(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 7845153..25e2935 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,8 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
 	       "--txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= | --record-core-cycles | "
-	       "--record-burst-stats]\n",
+	       "--vxlan-gpe-port= | --geneve-port= | "
+	       "--record-core-cycles | --record-burst-stats]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -200,6 +200,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -667,6 +668,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1303,6 +1305,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
diff --git a/doc/guides/testpmd_app_ug/run_app.rst b/doc/guides/testpmd_app_ug/run_app.rst
index e2539f6..dbd22f1 100644
--- a/doc/guides/testpmd_app_ug/run_app.rst
+++ b/doc/guides/testpmd_app_ug/run_app.rst
@@ -426,6 +426,11 @@ The command line options are:
     Set the UDP port number of tunnel VXLAN-GPE to N.
     The default value is 4790.
 
+*   ``--geneve-port=N``
+
+    Set the UDP port number of tunnel GENEVE to N.
+    The default value is 6081.
+
 *   ``--mlockall``
 
     Enable locking all memory.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v3 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-09-15 12:53         ` Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 12:53 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit. It assembles all tunnel outer updates into one
function call to avoid code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
 lib/librte_net/rte_vxlan.h |  1 +
 2 files changed, 21 insertions(+), 52 deletions(-)

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index eb87b9b..6f24a14 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -257,11 +264,7 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +294,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +304,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +314,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +326,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +392,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +401,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +410,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-15 11:07           ` Ferruh Yigit
@ 2020-09-15 12:59             ` Ophir Munk
  2020-09-15 13:19               ` Ophir Munk
  0 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 12:59 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger
  Cc: Ophir Munk, Raslan Darawsheh

Hi Ferruh,
I added to documentation the new parameter "--geneve-port=N" (second patch in the series).
I also rebased the series and sent v3.

Regards,
Ophir

> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> > I don't think that having the flexibility to specify the Geneve protocol in the
> command line will have an added value.
> > The reason is that any Geneve setup has a fixed protocol number for the
> duration of the test lifetime (fixed and synched by all the peers in the lab).
> The protocol number is not dynamic.
> > So even if we could specify the protocol in the command line - it would be
> a onetime setting after testpmd startup. Therefore, it is simpler to have it as
> parameter only.
> >
> 
> Overall, not specific to this patch, it bothers me not having any guideline
> what to add as a parameter, and not able to say what is implemented as
> parameter without searching for it ...
> 
> > Regards,
> > Ophir
> >


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

* [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd
  2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-15 13:17           ` Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                               ` (2 more replies)
  0 siblings, 3 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit; +Cc: Ophir Munk

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]
v3:
Rebase
document "geneve-port=N" parameter
v4:
Mispelling corrections

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: reduce tunnel parsing code duplication

 app/test-pmd/csumonly.c               | 120 ++++++++++++++++++++++------------
 app/test-pmd/parameters.c             |  14 +++-
 app/test-pmd/testpmd.h                |   1 +
 doc/guides/testpmd_app_ug/run_app.rst |   5 ++
 lib/librte_net/meson.build            |   3 +-
 lib/librte_net/rte_geneve.h           |  72 ++++++++++++++++++++
 lib/librte_net/rte_vxlan.h            |   1 +
 7 files changed, 171 insertions(+), 45 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing
  2020-09-15 13:17           ` [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-09-15 13:17             ` Ophir Munk
  2020-09-15 13:56               ` Ophir Munk
                                 ` (2 more replies)
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 3 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 144 insertions(+), 2 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 7ece398..eb87b9b 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_GENEVE_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index a8ae5cc..f405d4e 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..d50f5b3
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+
+#include <stdint.h>
+
+#include <rte_udp.h>
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protocol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
+ * More-bits (optional) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t oam:1;		/**< Control packet (1). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+#else
+	uint8_t opt_len:6;	/**< Options length (6). */
+	uint8_t ver:2;		/**< Version (2).  */
+	uint8_t rsvd1:6;	/**< Reserved (6). */
+	uint8_t critical:1;	/**< Critical packet (1). */
+	uint8_t oam:1;		/**< Control packet (1). */
+#endif
+	rte_be16_t proto;	/**< Protocol type (16). */
+	uint8_t vni[3];		/**< Virtual network identifier (24). */
+	uint8_t rsvd2;		/**< Reserved (8). */
+	uint8_t opts[];		/**<Variable length options. */
+} __rte_packed;
+
+/* GENEVE next protocol types */
+#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol. */
+#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol. */
+#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v4 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-15 13:17           ` [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-15 13:17             ` Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c             | 14 ++++++++++++--
 doc/guides/testpmd_app_ug/run_app.rst |  5 +++++
 2 files changed, 17 insertions(+), 2 deletions(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 7845153..25e2935 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,8 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
 	       "--txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= | --record-core-cycles | "
-	       "--record-burst-stats]\n",
+	       "--vxlan-gpe-port= | --geneve-port= | "
+	       "--record-core-cycles | --record-burst-stats]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -200,6 +200,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -667,6 +668,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1303,6 +1305,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
diff --git a/doc/guides/testpmd_app_ug/run_app.rst b/doc/guides/testpmd_app_ug/run_app.rst
index e2539f6..dbd22f1 100644
--- a/doc/guides/testpmd_app_ug/run_app.rst
+++ b/doc/guides/testpmd_app_ug/run_app.rst
@@ -426,6 +426,11 @@ The command line options are:
     Set the UDP port number of tunnel VXLAN-GPE to N.
     The default value is 4790.
 
+*   ``--geneve-port=N``
+
+    Set the UDP port number of tunnel GENEVE to N.
+    The default value is 6081.
+
 *   ``--mlockall``
 
     Enable locking all memory.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v4 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-09-15 13:17           ` [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-09-15 13:17             ` Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit. It assembles all tunnel outer updates into one
function call to avoid code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
 lib/librte_net/rte_vxlan.h |  1 +
 2 files changed, 21 insertions(+), 52 deletions(-)

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index eb87b9b..6f24a14 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -257,11 +264,7 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +294,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +304,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +314,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +326,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +392,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +401,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +410,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-15 12:59             ` Ophir Munk
@ 2020-09-15 13:19               ` Ophir Munk
  0 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:19 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger
  Cc: Ophir Munk, Raslan Darawsheh

Hi,
V4 sent with misspelling corrections.

Regards,
Ophir

> -----Original Message-----
> From: Ophir Munk
> Sent: Tuesday, September 15, 2020 3:59 PM
> To: Ferruh Yigit <ferruh.yigit@intel.com>; dev@dpdk.org; Wenzhuo Lu
> <wenzhuo.lu@intel.com>; Beilei Xing <beilei.xing@intel.com>; Bernard
> Iremonger <bernard.iremonger@intel.com>
> Cc: Ophir Munk <ophirmu@mellanox.com>; Raslan Darawsheh
> <rasland@nvidia.com>
> Subject: RE: [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring
> GENEVE port
> 
> Hi Ferruh,
> I added to documentation the new parameter "--geneve-port=N" (second
> patch in the series).
> I also rebased the series and sent v3.
> 
> Regards,
> Ophir

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

* Re: [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-15 13:56               ` Ophir Munk
  2020-09-17 12:23               ` Olivier Matz
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-15 13:56 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Ferruh Yigit, olivier.matz
  Cc: Ophir Munk

Adding Olivier who is the maintainer of the Network headers (lib/librte_net/rte_geneve.h).

> -----Original Message-----
> From: Ophir Munk <ophirmu@nvidia.com>
> Sent: Tuesday, September 15, 2020 4:17 PM
> To: dev@dpdk.org; Wenzhuo Lu <wenzhuo.lu@intel.com>; Beilei Xing
> <beilei.xing@intel.com>; Bernard Iremonger
> <bernard.iremonger@intel.com>; Ferruh Yigit <ferruh.yigit@intel.com>
> Cc: Ophir Munk <ophirmu@nvidia.com>; Ophir Munk
> <ophirmu@mellanox.com>
> Subject: [PATCH v4 1/3] app/testpmd: add GENEVE parsing
> 
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> GENEVE is a widely used tunneling protocol in modern Virtualized Networks.
> testpmd already supports parsing of several tunneling protocols including
> VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE parsing of inner
> protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558) based on IETF draft-
> ietf-nvo3-geneve-09. GENEVE is considered more flexible than the other
> protocols.  In terms of protocol format GENEVE header has a variable length
> options as opposed to other tunneling protocols which have a fixed header
> size.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>  app/test-pmd/csumonly.c     | 70
> ++++++++++++++++++++++++++++++++++++++++++-
>  app/test-pmd/testpmd.h      |  1 +
>  lib/librte_net/meson.build  |  3 +-
>  lib/librte_net/rte_geneve.h | 72
> +++++++++++++++++++++++++++++++++++++++++++++
>  4 files changed, 144 insertions(+), 2 deletions(-)  create mode 100644
> lib/librte_net/rte_geneve.h
> 
> diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c index
> 7ece398..eb87b9b 100644
> --- a/app/test-pmd/csumonly.c
> +++ b/app/test-pmd/csumonly.c
> @@ -43,6 +43,7 @@
>  #include <rte_flow.h>
>  #include <rte_gro.h>
>  #include <rte_gso.h>
> +#include <rte_geneve.h>
> 
>  #include "testpmd.h"
> 
> @@ -63,6 +64,7 @@
>  #endif
> 
>  uint16_t vxlan_gpe_udp_port = 4790;
> +uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
> 
>  /* structure that caches offload info for the current packet */  struct
> testpmd_offload_info { @@ -333,6 +335,64 @@ parse_vxlan_gpe(struct
> rte_udp_hdr *udp_hdr,
>  	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;  }
> 
> +/* Fill in outer layers length */
> +static void
> +update_tunnel_outer(struct testpmd_offload_info *info) {
> +	info->is_tunnel = 1;
> +	info->outer_ethertype = info->ethertype;
> +	info->outer_l2_len = info->l2_len;
> +	info->outer_l3_len = info->l3_len;
> +	info->outer_l4_proto = info->l4_proto; }
> +
> +/* Parse a geneve header */
> +static void
> +parse_geneve(struct rte_udp_hdr *udp_hdr,
> +	    struct testpmd_offload_info *info) {
> +	struct rte_ether_hdr *eth_hdr;
> +	struct rte_ipv4_hdr *ipv4_hdr;
> +	struct rte_ipv6_hdr *ipv6_hdr;
> +	struct rte_geneve_hdr *geneve_hdr;
> +	uint16_t geneve_len;
> +
> +	/* Check udp destination port. */
> +	if (udp_hdr->dst_port != _htons(geneve_udp_port))
> +		return;
> +
> +	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
> +				sizeof(struct rte_udp_hdr));
> +	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len *
> 4;
> +	if (!geneve_hdr->proto || geneve_hdr->proto ==
> +	    _htons(RTE_GENEVE_TYPE_IPV4)) {
> +		update_tunnel_outer(info);
> +		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
> +			   geneve_len);
> +		parse_ipv4(ipv4_hdr, info);
> +		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
> +		info->l2_len = 0;
> +	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_IPV6)) {
> +		update_tunnel_outer(info);
> +		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
> +			   geneve_len);
> +		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
> +		parse_ipv6(ipv6_hdr, info);
> +		info->l2_len = 0;
> +
> +	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
> +		update_tunnel_outer(info);
> +		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
> +			  geneve_len);
> +		parse_ethernet(eth_hdr, info);
> +	} else
> +		return;
> +
> +	info->l2_len +=
> +		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
> +		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4); }
> +
>  /* Parse a gre header */
>  static void
>  parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info
> *info) @@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct
> fwd_stream *fs)
>  				}
>  				parse_vxlan(udp_hdr, &info,
>  					    m->packet_type);
> -				if (info.is_tunnel)
> +				if (info.is_tunnel) {
>  					tx_ol_flags |=
>  						PKT_TX_TUNNEL_VXLAN;
> +					goto tunnel_update;
> +				}
> +				parse_geneve(udp_hdr, &info);
> +				if (info.is_tunnel) {
> +					tx_ol_flags |=
> +						PKT_TX_TUNNEL_GENEVE;
> +					goto tunnel_update;
> +				}
>  			} else if (info.l4_proto == IPPROTO_GRE) {
>  				struct simple_gre_hdr *gre_hdr;
> 
> diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h index
> a8ae5cc..f405d4e 100644
> --- a/app/test-pmd/testpmd.h
> +++ b/app/test-pmd/testpmd.h
> @@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;  extern struct
> fwd_stream **fwd_streams;
> 
>  extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE.
> */
> +extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
> 
>  extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet
> addresses. */  extern struct rte_ether_addr
> peer_eth_addrs[RTE_MAX_ETHPORTS]; diff --git
> a/lib/librte_net/meson.build b/lib/librte_net/meson.build index
> 24ed825..52d3a97 100644
> --- a/lib/librte_net/meson.build
> +++ b/lib/librte_net/meson.build
> @@ -16,7 +16,8 @@ headers = files('rte_ip.h',
>  	'rte_net_crc.h',
>  	'rte_mpls.h',
>  	'rte_higig.h',
> -	'rte_ecpri.h')
> +	'rte_ecpri.h',
> +	'rte_geneve.h')
> 
>  sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')  deps +=
> ['mbuf'] diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
> new file mode 100644 index 0000000..d50f5b3
> --- /dev/null
> +++ b/lib/librte_net/rte_geneve.h
> @@ -0,0 +1,72 @@
> +/* SPDX-License-Identifier: BSD-3-Clause
> + * Copyright 2020 Mellanox Technologies, Ltd  */
> +
> +#ifndef _RTE_GENEVE_H_
> +#define _RTE_GENEVE_H_
> +
> +/**
> + * @file
> + *
> + * GENEVE-related definitions
> + */
> +
> +#include <stdint.h>
> +
> +#include <rte_udp.h>
> +
> +
> +#ifdef __cplusplus
> +extern "C" {
> +#endif
> +
> +/** GENEVE default port. */
> +#define RTE_GENEVE_DEFAULT_PORT 6081
> +
> +/**
> + * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
> + * Contains:
> + * 2-bits version (must be 0).
> + * 6-bits option length in four byte multiples, not including the eight
> + *	bytes of the fixed tunnel header.
> + * 1-bit control packet.
> + * 1-bit critical options in packet.
> + * 6-bits reserved
> + * 16-bits Protocol Type. The protocol data unit after the Geneve header
> + *	following the EtherType convention. Ethernet itself is represented by
> + *	the value 0x6558.
> + * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
> + * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
> + * More-bits (optional) variable length options.
> + */
> +__extension__
> +struct rte_geneve_hdr {
> +#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
> +	uint8_t ver:2;		/**< Version (2).  */
> +	uint8_t opt_len:6;	/**< Options length (6). */
> +	uint8_t oam:1;		/**< Control packet (1). */
> +	uint8_t critical:1;	/**< Critical packet (1). */
> +	uint8_t rsvd1:6;	/**< Reserved (6). */
> +#else
> +	uint8_t opt_len:6;	/**< Options length (6). */
> +	uint8_t ver:2;		/**< Version (2).  */
> +	uint8_t rsvd1:6;	/**< Reserved (6). */
> +	uint8_t critical:1;	/**< Critical packet (1). */
> +	uint8_t oam:1;		/**< Control packet (1). */
> +#endif
> +	rte_be16_t proto;	/**< Protocol type (16). */
> +	uint8_t vni[3];		/**< Virtual network identifier (24). */
> +	uint8_t rsvd2;		/**< Reserved (8). */
> +	uint8_t opts[];		/**<Variable length options. */
> +} __rte_packed;
> +
> +/* GENEVE next protocol types */
> +#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol.
> */
> +#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol.
> */
> +#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet
> Protocol. */
> +
> +#ifdef __cplusplus
> +}
> +#endif
> +
> +#endif /* RTE_GENEVE_H_ */
> --
> 2.8.4


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

* Re: [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-15 13:56               ` Ophir Munk
@ 2020-09-17 12:23               ` Olivier Matz
  2020-09-18 14:21                 ` Ophir Munk
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2 siblings, 1 reply; 50+ messages in thread
From: Olivier Matz @ 2020-09-17 12:23 UTC (permalink / raw)
  To: Ophir Munk
  Cc: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Ophir Munk

Hi Ophir,

Please find some comments below.

On Tue, Sep 15, 2020 at 01:17:15PM +0000, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> GENEVE is a widely used tunneling protocol in modern Virtualized
> Networks. testpmd already supports parsing of several tunneling
> protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
> parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
> based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
> flexible than the other protocols.  In terms of protocol format GENEVE
> header has a variable length options as opposed to other tunneling
> protocols which have a fixed header size.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>


>  app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++-
>  app/test-pmd/testpmd.h      |  1 +
>  lib/librte_net/meson.build  |  3 +-
>  lib/librte_net/rte_geneve.h | 72 +++++++++++++++++++++++++++++++++++++++++++++
>  4 files changed, 144 insertions(+), 2 deletions(-)
>  create mode 100644 lib/librte_net/rte_geneve.h

An entry could be added in doc/api/doxy-api-index.md. Some more protocols
are missing, I'll send a patch to add them.

> --- /dev/null
> +++ b/lib/librte_net/rte_geneve.h
> @@ -0,0 +1,72 @@
> +/* SPDX-License-Identifier: BSD-3-Clause
> + * Copyright 2020 Mellanox Technologies, Ltd
> + */
> +
> +#ifndef _RTE_GENEVE_H_
> +#define _RTE_GENEVE_H_
> +
> +/**
> + * @file
> + *
> + * GENEVE-related definitions
> + */
> +
> +#include <stdint.h>
> +
> +#include <rte_udp.h>

Is this include needed? Maybe it comes from a copy/paste of VXLAN?

> +
> +
> +#ifdef __cplusplus
> +extern "C" {
> +#endif
> +
> +/** GENEVE default port. */
> +#define RTE_GENEVE_DEFAULT_PORT 6081
> +
> +/**
> + * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
> + * Contains:
> + * 2-bits version (must be 0).
> + * 6-bits option length in four byte multiples, not including the eight
> + *	bytes of the fixed tunnel header.
> + * 1-bit control packet.
> + * 1-bit critical options in packet.
> + * 6-bits reserved
> + * 16-bits Protocol Type. The protocol data unit after the Geneve header
> + *	following the EtherType convention. Ethernet itself is represented by
> + *	the value 0x6558.
> + * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
> + * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
> + * More-bits (optional) variable length options.
> + */
> +__extension__
> +struct rte_geneve_hdr {
> +#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
> +	uint8_t ver:2;		/**< Version (2).  */

Isn't the (2) in the comment redundant with the :2 in the type?
Here is how bitfield look like in doxygen documentation:
https://doc.dpdk.org/api/structrte__flow__attr.html#ae4d19341d5298a2bc61f9eb941b1179c

It's true that the field documentation miss the number of bits.
So if you feel it's needed, I prefer something more explicit like "(2 bits)"
instead of just "(2)".

By the way, there are 2 spaces at the end of the comment.

> +	uint8_t opt_len:6;	/**< Options length (6). */
> +	uint8_t oam:1;		/**< Control packet (1). */
> +	uint8_t critical:1;	/**< Critical packet (1). */
> +	uint8_t rsvd1:6;	/**< Reserved (6). */

"reserved" instead of "rsvd"?

The Internet-Draft says "Rsvd" for this one, but "Reserved" for the other.

> +#else
> +	uint8_t opt_len:6;	/**< Options length (6). */
> +	uint8_t ver:2;		/**< Version (2).  */
> +	uint8_t rsvd1:6;	/**< Reserved (6). */
> +	uint8_t critical:1;	/**< Critical packet (1). */
> +	uint8_t oam:1;		/**< Control packet (1). */
> +#endif
> +	rte_be16_t proto;	/**< Protocol type (16). */
> +	uint8_t vni[3];		/**< Virtual network identifier (24). */
> +	uint8_t rsvd2;		/**< Reserved (8). */

vni is an identifier, so I wonder if it would make sense to have
it as an integer instead of an array of uint8. Something like this:

	#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
		uint32_t vni:24;
		uint32_t reserved2:8;
	#else
		uint32_t vni:24;
		uint32_t reserved2:8;
	#endif

> +	uint8_t opts[];		/**<Variable length options. */

Since the option length is a multiple of four-bytes, would uint32_t[]
make more sense here?

Missing a space after "<".

> +} __rte_packed;
> +
> +/* GENEVE next protocol types */
> +#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol. */
> +#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol. */
> +#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet Protocol. */

From what I understand in the draft, I think only RTE_GENEVE_TYPE_ETH
is needed.

   Protocol Type (16 bits):  The type of the protocol data unit
   appearing after the Geneve header.  This follows the EtherType
   [ETYPES] convention; with Ethernet itself being represented by the
   value 0x6558.

Shouldn't we use RTE_ETHER_TYPE_* instead of redefining them here?

0x6558 is RTE_ETHER_TYPE_TEB (Transparent Ethernet Bridging) and is
also used in case of NVGRE.


Regards,
Olivier

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

* [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd
  2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-15 13:56               ` Ophir Munk
  2020-09-17 12:23               ` Olivier Matz
@ 2020-09-18 14:17               ` Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                                   ` (3 more replies)
  2 siblings, 4 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-18 14:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Olivier Matz
  Cc: Ophir Munk

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]
v3:
Rebase
document "geneve-port=N" parameter
v4:
Mispelling corrections
v5:
Rebase + Updates following review
http://patches.dpdk.org/patch/77734/

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: reduce tunnel parsing code duplication

 app/test-pmd/csumonly.c               | 120 ++++++++++++++++++++++------------
 app/test-pmd/parameters.c             |  14 +++-
 app/test-pmd/testpmd.h                |   1 +
 doc/guides/testpmd_app_ug/run_app.rst |   5 ++
 lib/librte_net/meson.build            |   3 +-
 lib/librte_net/rte_geneve.h           |  66 +++++++++++++++++++
 lib/librte_net/rte_vxlan.h            |   1 +
 7 files changed, 165 insertions(+), 45 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-09-18 14:17                 ` Ophir Munk
  2020-10-06 14:30                   ` Ferruh Yigit
  2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
                                   ` (2 subsequent siblings)
  3 siblings, 2 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-18 14:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Olivier Matz
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 66 ++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 138 insertions(+), 2 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 7ece398..a9f33c6 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_ETHER_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index f139fe7..bd08a64 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..bb67724
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,66 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+#include <stdint.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protocol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
+ * More-bits (optional) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version. */
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t oam:1;		/**< Control packet. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t reserved1:6;	/**< Reserved. */
+#else
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t ver:2;		/**< Version. */
+	uint8_t reserved1:6;	/**< Reserved. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t oam:1;		/**< Control packet. */
+#endif
+	rte_be16_t proto;	/**< Protocol type. */
+	uint8_t vni[3];		/**< Virtual network identifier. */
+	uint8_t reserved2;	/**< Reserved. */
+	uint32_t opts[];	/**< Variable length options. */
+} __rte_packed;
+
+/* GENEVE ETH next protocol types */
+#define RTE_GENEVE_TYPE_ETH	0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v5 2/3] app/testpmd: enable configuring GENEVE port
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-09-18 14:17                 ` Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
  2020-10-06 14:58                 ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-18 14:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Olivier Matz
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c             | 14 ++++++++++++--
 doc/guides/testpmd_app_ug/run_app.rst |  5 +++++
 2 files changed, 17 insertions(+), 2 deletions(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 8c2aa13..d10397c 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,8 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= | --rxfreet= | "
 	       "--txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= | --record-core-cycles | "
-	       "--record-burst-stats]\n",
+	       "--vxlan-gpe-port= | --geneve-port= | "
+	       "--record-core-cycles | --record-burst-stats]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -200,6 +200,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -667,6 +668,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1303,6 +1305,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
diff --git a/doc/guides/testpmd_app_ug/run_app.rst b/doc/guides/testpmd_app_ug/run_app.rst
index e2539f6..dbd22f1 100644
--- a/doc/guides/testpmd_app_ug/run_app.rst
+++ b/doc/guides/testpmd_app_ug/run_app.rst
@@ -426,6 +426,11 @@ The command line options are:
     Set the UDP port number of tunnel VXLAN-GPE to N.
     The default value is 4790.
 
+*   ``--geneve-port=N``
+
+    Set the UDP port number of tunnel GENEVE to N.
+    The default value is 6081.
+
 *   ``--mlockall``
 
     Enable locking all memory.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-09-18 14:17                 ` Ophir Munk
  2020-10-06 14:30                   ` Ferruh Yigit
  2020-10-06 14:58                 ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
  3 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-09-18 14:17 UTC (permalink / raw)
  To: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Olivier Matz
  Cc: Ophir Munk, Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit. It assembles all tunnel outer updates into one
function call to avoid code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
 lib/librte_net/rte_vxlan.h |  1 +
 2 files changed, 21 insertions(+), 52 deletions(-)

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index a9f33c6..7f9bfa6 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -257,11 +264,7 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +294,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +304,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +314,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +326,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +392,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +401,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +410,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing
  2020-09-17 12:23               ` Olivier Matz
@ 2020-09-18 14:21                 ` Ophir Munk
  0 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-09-18 14:21 UTC (permalink / raw)
  To: Olivier Matz
  Cc: dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger, Ferruh Yigit,
	Ophir Munk

Hi Olivier,
Please find comments inline.
I sent v5 based on your review.
http://patches.dpdk.org/project/dpdk/list/?series=12354

> -----Original Message-----
> From: Olivier Matz <olivier.matz@6wind.com>
> Sent: Thursday, September 17, 2020 3:23 PM
> To: Ophir Munk <ophirmu@nvidia.com>
> Cc: dev@dpdk.org; Wenzhuo Lu <wenzhuo.lu@intel.com>; Beilei Xing
> <beilei.xing@intel.com>; Bernard Iremonger
> <bernard.iremonger@intel.com>; Ferruh Yigit <ferruh.yigit@intel.com>;
> Ophir Munk <ophirmu@mellanox.com>
> Subject: Re: [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing
> 
> Hi Ophir,
> 
> Please find some comments below.
> 
> On Tue, Sep 15, 2020 at 01:17:15PM +0000, Ophir Munk wrote:
> > From: Ophir Munk <ophirmu@mellanox.com>
> >
> > GENEVE is a widely used tunneling protocol in modern Virtualized
> > Networks. testpmd already supports parsing of several tunneling
> > protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
> > parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
> > based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
> > flexible than the other protocols.  In terms of protocol format GENEVE
> > header has a variable length options as opposed to other tunneling
> > protocols which have a fixed header size.
> >
> > Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> 
> 
> >  app/test-pmd/csumonly.c     | 70
> ++++++++++++++++++++++++++++++++++++++++++-
> >  app/test-pmd/testpmd.h      |  1 +
> >  lib/librte_net/meson.build  |  3 +-
> >  lib/librte_net/rte_geneve.h | 72
> > +++++++++++++++++++++++++++++++++++++++++++++
> >  4 files changed, 144 insertions(+), 2 deletions(-)  create mode
> > 100644 lib/librte_net/rte_geneve.h
> 
> An entry could be added in doc/api/doxy-api-index.md. Some more protocols
> are missing, I'll send a patch to add them.
> 

Thanks for sending a patch. I would appreciate it if it includes Geneve as well.

> > --- /dev/null
> > +++ b/lib/librte_net/rte_geneve.h
> > @@ -0,0 +1,72 @@
> > +/* SPDX-License-Identifier: BSD-3-Clause
> > + * Copyright 2020 Mellanox Technologies, Ltd  */
> > +
> > +#ifndef _RTE_GENEVE_H_
> > +#define _RTE_GENEVE_H_
> > +
> > +/**
> > + * @file
> > + *
> > + * GENEVE-related definitions
> > + */
> > +
> > +#include <stdint.h>
> > +
> > +#include <rte_udp.h>
> 
> Is this include needed? Maybe it comes from a copy/paste of VXLAN?
> 

The include was dropped in v5 (not needed).

> > +
> > +
> > +#ifdef __cplusplus
> > +extern "C" {
> > +#endif
> > +
> > +/** GENEVE default port. */
> > +#define RTE_GENEVE_DEFAULT_PORT 6081
> > +
> > +/**
> > + * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
> > + * Contains:
> > + * 2-bits version (must be 0).
> > + * 6-bits option length in four byte multiples, not including the eight
> > + *	bytes of the fixed tunnel header.
> > + * 1-bit control packet.
> > + * 1-bit critical options in packet.
> > + * 6-bits reserved
> > + * 16-bits Protocol Type. The protocol data unit after the Geneve header
> > + *	following the EtherType convention. Ethernet itself is represented by
> > + *	the value 0x6558.
> > + * 24-bits Virtual Network Identifier (VNI). Virtual network unique
> identified.
> > + * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
> > + * More-bits (optional) variable length options.
> > + */
> > +__extension__
> > +struct rte_geneve_hdr {
> > +#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
> > +	uint8_t ver:2;		/**< Version (2).  */
> 
> Isn't the (2) in the comment redundant with the :2 in the type?
> Here is how bitfield look like in doxygen documentation:
> https://nam11.safelinks.protection.outlook.com/?url=https%3A%2F%2Fdoc.
> dpdk.org%2Fapi%2Fstructrte__flow__attr.html%23ae4d19341d5298a2bc61f
> 9eb941b1179c&amp;data=02%7C01%7Cophirmu%40nvidia.com%7C95918f4
> 2491c4832d8a308d85b047a22%7C43083d15727340c1b7db39efd9ccc17a%7
> C0%7C0%7C637359422086641153&amp;sdata=LJjYkeHy9eHGc9xu42E%2F8
> h54dzxrmiO7V0NCeLXndpU%3D&amp;reserved=0
> 
> It's true that the field documentation miss the number of bits.
> So if you feel it's needed, I prefer something more explicit like "(2 bits)"
> instead of just "(2)".
> 

The number of bits is removed from the comments (v5).

> By the way, there are 2 spaces at the end of the comment.
> 

Extra spaces removed.

> > +	uint8_t opt_len:6;	/**< Options length (6). */
> > +	uint8_t oam:1;		/**< Control packet (1). */
> > +	uint8_t critical:1;	/**< Critical packet (1). */
> > +	uint8_t rsvd1:6;	/**< Reserved (6). */
> 
> "reserved" instead of "rsvd"?
> 

In v5 all "rsvd" fields are renamed as "reserved".

> The Internet-Draft says "Rsvd" for this one, but "Reserved" for the other.
> 
> > +#else
> > +	uint8_t opt_len:6;	/**< Options length (6). */
> > +	uint8_t ver:2;		/**< Version (2).  */
> > +	uint8_t rsvd1:6;	/**< Reserved (6). */
> > +	uint8_t critical:1;	/**< Critical packet (1). */
> > +	uint8_t oam:1;		/**< Control packet (1). */
> > +#endif
> > +	rte_be16_t proto;	/**< Protocol type (16). */
> > +	uint8_t vni[3];		/**< Virtual network identifier (24). */
> > +	uint8_t rsvd2;		/**< Reserved (8). */
> 
> vni is an identifier, so I wonder if it would make sense to have it as an integer
> instead of an array of uint8. Something like this:
> 
> 	#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
> 		uint32_t vni:24;
> 		uint32_t reserved2:8;
> 	#else
> 		uint32_t vni:24;
> 		uint32_t reserved2:8;
> 	#endif
> 

I suggest leaving the vni as is (array of unsigned chars) since I do not see a gain by changing it to an integer of 24 bits.
If we did change - it will not turn VNI from network order to host order. So in case you wanted to print the VNI (host order) you will have to manipulate the bytes order anyway based on endianness. 
What do you think?

> > +	uint8_t opts[];		/**<Variable length options. */
> 
> Since the option length is a multiple of four-bytes, would uint32_t[] make
> more sense here?
> 

opts[] type changed to uint32_t  in v5.

> Missing a space after "<".
> 

Space added.

> > +} __rte_packed;
> > +
> > +/* GENEVE next protocol types */
> > +#define RTE_GENEVE_TYPE_IPV4		0x0800 /**< IPv4 Protocol.
> */
> > +#define RTE_GENEVE_TYPE_IPV6		0x86dd /**< IPv6 Protocol.
> */
> > +#define RTE_GENEVE_TYPE_ETH		0x6558 /**< Ethernet
> Protocol. */
> 
> From what I understand in the draft, I think only RTE_GENEVE_TYPE_ETH is
> needed.
> 
>    Protocol Type (16 bits):  The type of the protocol data unit
>    appearing after the Geneve header.  This follows the EtherType
>    [ETYPES] convention; with Ethernet itself being represented by the
>    value 0x6558.
> 
> Shouldn't we use RTE_ETHER_TYPE_* instead of redefining them here?
> 
> 0x6558 is RTE_ETHER_TYPE_TEB (Transparent Ethernet Bridging) and is also
> used in case of NVGRE.
> 
> 

Definitions RTE_GENEVE_TYPE_IPV4 and RTE_GENEVE_TYPE_IPV6 dropped (remaining with RTE_GENEVE_TYPE_ETH only).

> Regards,
> Olivier

Regards,
Ophir

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

* Re: [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
@ 2020-10-06 14:30                   ` Ferruh Yigit
  2020-10-07 10:56                     ` Ophir Munk
  0 siblings, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-06 14:30 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk

On 9/18/2020 3:17 PM, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> This is a cleanup commit. It assembles all tunnel outer updates into one
> function call to avoid code duplications.
> It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
> other tunnel protocol definitions.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>   app/test-pmd/csumonly.c    | 72 +++++++++++++---------------------------------
>   lib/librte_net/rte_vxlan.h |  1 +
>   2 files changed, 21 insertions(+), 52 deletions(-)
> 
> diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
> index a9f33c6..7f9bfa6 100644
> --- a/app/test-pmd/csumonly.c
> +++ b/app/test-pmd/csumonly.c
> @@ -63,7 +63,7 @@
>   #define _htons(x) (x)
>   #endif
>   
> -uint16_t vxlan_gpe_udp_port = 4790;
> +uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
>   uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;

'RTE_VXLAN_DEFAULT_PORT' seems defined but '4789' still used as hardcoded in 
this file, since you are touching these, can you please update that usage too?

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

* Re: [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-10-06 14:30                   ` Ferruh Yigit
  2020-10-07 14:52                     ` Ophir Munk
  2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  1 sibling, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-06 14:30 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk

On 9/18/2020 3:17 PM, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> GENEVE is a widely used tunneling protocol in modern Virtualized
> Networks. testpmd already supports parsing of several tunneling
> protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
> parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
> based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
> flexible than the other protocols.  In terms of protocol format GENEVE
> header has a variable length options as opposed to other tunneling
> protocols which have a fixed header size.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>   app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++++-
>   app/test-pmd/testpmd.h      |  1 +
>   lib/librte_net/meson.build  |  3 +-
>   lib/librte_net/rte_geneve.h | 66 ++++++++++++++++++++++++++++++++++++++++++
>   4 files changed, 138 insertions(+), 2 deletions(-)
>   create mode 100644 lib/librte_net/rte_geneve.h
> 
> diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
> index 7ece398..a9f33c6 100644
> --- a/app/test-pmd/csumonly.c
> +++ b/app/test-pmd/csumonly.c
> @@ -43,6 +43,7 @@
>   #include <rte_flow.h>
>   #include <rte_gro.h>
>   #include <rte_gso.h>
> +#include <rte_geneve.h>
>   
>   #include "testpmd.h"
>   
> @@ -63,6 +64,7 @@
>   #endif
>   
>   uint16_t vxlan_gpe_udp_port = 4790;
> +uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
>   

There is a testpmd command to configure the NIC for GENEVE port,
"port config (port_id) udp_tunnel_port add|rm vxlan|geneve|vxlan-gpe (udp_port)"

You are adding support to testpmd to parse the GENEVE packets, but I think these 
two commads should be consistent.

What do you think "port config N add geneve X" update the 'geneve_udp_port=X"?

<...>


> @@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
>   				}
>   				parse_vxlan(udp_hdr, &info,
>   					    m->packet_type);
> -				if (info.is_tunnel)
> +				if (info.is_tunnel) {
>   					tx_ol_flags |=
>   						PKT_TX_TUNNEL_VXLAN;
> +					goto tunnel_update;
> +				}
> +				parse_geneve(udp_hdr, &info);
> +				if (info.is_tunnel) {
> +					tx_ol_flags |=
> +						PKT_TX_TUNNEL_GENEVE;
> +					goto tunnel_update;
> +				}

Can you please update the "csum parse-tunnel" documentation to mention "geneve" 
protocol?

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

* Re: [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd
  2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
                                   ` (2 preceding siblings ...)
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
@ 2020-10-06 14:58                 ` Ferruh Yigit
  2020-10-07 15:43                   ` Ophir Munk
  3 siblings, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-06 14:58 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz

On 9/18/2020 3:17 PM, Ophir Munk wrote:
> v1:
> Initial version
> v2:
> Rebased + Minor update in protocol options field:
> char opts[0] ===> uint8_t opts[]
> v3:
> Rebase
> document "geneve-port=N" parameter
> v4:
> Mispelling corrections
> v5:
> Rebase + Updates following review
> http://patches.dpdk.org/patch/77734/
> 
> Ophir Munk (3):
>    app/testpmd: add GENEVE parsing
>    app/testpmd: enable configuring GENEVE port
>    app/testpmd: reduce tunnel parsing code duplication
> 

Hi Ophir,

The patchset looks good except a few comments I put into the patches.

But I have two highlevel questions/comments,

1) The testpmd tunnel parsing feature is not documented properly, there are 
various related commands but there is no documentation to put all together.
What do you think putting a new section for it under the "Testpmd Runtime 
Functions" (testpmd_funcs.rst) with this patchset?

2) The 'csum' forwarding engine seems become forwarding engine for the case 
where packet payload needs to be parsed, like gro/gso, tunnel parse. Even the 
description of the forwarding engine in the documentation is not accurate now.
I wonder if we should rename the forwarding engine at this stage?

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

* Re: [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication
  2020-10-06 14:30                   ` Ferruh Yigit
@ 2020-10-07 10:56                     ` Ophir Munk
  0 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 10:56 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk


> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> Sent: Tuesday, October 6, 2020 5:30 PM
...
> Subject: Re: [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code
> duplication
...
> 'RTE_VXLAN_DEFAULT_PORT' seems defined but '4789' still used as
> hardcoded in this file, since you are touching these, can you please update
> that usage too?

Done in v6

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

* Re: [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-10-06 14:30                   ` Ferruh Yigit
@ 2020-10-07 14:52                     ` Ophir Munk
  2020-10-07 16:25                       ` Ferruh Yigit
  0 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 14:52 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk

Hi Ferruh,
Please find comments inline.

> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> Sent: Tuesday, October 6, 2020 5:31 PM
> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
<...>
> >
> >   uint16_t vxlan_gpe_udp_port = 4790;
> > +uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
> >
> 
> There is a testpmd command to configure the NIC for GENEVE port, "port
> config (port_id) udp_tunnel_port add|rm vxlan|geneve|vxlan-gpe
> (udp_port)"
> 
> You are adding support to testpmd to parse the GENEVE packets, but I think
> these two commads should be consistent.
> 
> What do you think "port config N add geneve X" update the
> 'geneve_udp_port=X"?
> 
> <...>
> 

It is not as simple as suggested.
The command "port config N add geneve X" can be repeated several times - adding another geneve port to the NIC Hardware/Firmware to recognize. As a result the NIC is configured with multiple geneve ports. On the other hand geneve_udp_port is a single variable - so whenever a new "port config" command is executed - we will override the last geneve port and forget all the precedent ones.
The port config command also has a "rm" option in addition to "add". So if we removed the last port - what will we assigned to geneve_udp_port? We need to have a small data base for managing geneve ports.
testpmd also has an option " --geneve-port=N". It should be synched with the "port config" command.

Another issue to consider is if there is a need for the suggested feature. I think the "port config" is mainly targeted for offloading. So the NIC will probably encap/decap a packet with geneve - leaving testpmd paring unneeded.

My point is that your suggestion requires an RFC before implementation.

> 
> > @@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream
> *fs)
> >   				}
> >   				parse_vxlan(udp_hdr, &info,
> >   					    m->packet_type);
> > -				if (info.is_tunnel)
> > +				if (info.is_tunnel) {
> >   					tx_ol_flags |=
> >   						PKT_TX_TUNNEL_VXLAN;
> > +					goto tunnel_update;
> > +				}
> > +				parse_geneve(udp_hdr, &info);
> > +				if (info.is_tunnel) {
> > +					tx_ol_flags |=
> > +						PKT_TX_TUNNEL_GENEVE;
> > +					goto tunnel_update;
> > +				}
> 
> Can you please update the "csum parse-tunnel" documentation to mention
> "geneve"
> protocol?

Done in v6. I added other missing tunnel protocols (in alphabetical order) such as "gtp". Since it is more than geneve I added it to the 3rd (cleanup) commit.


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

* [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd
  2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-10-06 14:30                   ` Ferruh Yigit
@ 2020-10-07 15:30                   ` Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                                       ` (2 more replies)
  1 sibling, 3 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 15:30 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]
v3:
Rebase
document "geneve-port=N" parameter
v4:
Mispelling corrections
v5:
Rebase + Updates following review
http://patches.dpdk.org/patch/77734/
v6:
Rebase + Updates following reviews: more cleanup and added documentation.

Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: tunnel parsing protocols cleanup

 app/test-pmd/cmdline_flow.c                 |   3 +-
 app/test-pmd/csumonly.c                     | 129 ++++++++++++++++++----------
 app/test-pmd/parameters.c                   |  14 ++-
 app/test-pmd/testpmd.h                      |   1 +
 doc/guides/testpmd_app_ug/run_app.rst       |   5 ++
 doc/guides/testpmd_app_ug/testpmd_funcs.rst |   6 +-
 lib/librte_net/meson.build                  |   3 +-
 lib/librte_net/rte_geneve.h                 |  66 ++++++++++++++
 lib/librte_net/rte_vxlan.h                  |   1 +
 9 files changed, 175 insertions(+), 53 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing
  2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-10-07 15:30                     ` Ophir Munk
  2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
  2 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 15:30 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c     | 70 ++++++++++++++++++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h      |  1 +
 lib/librte_net/meson.build  |  3 +-
 lib/librte_net/rte_geneve.h | 66 ++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 138 insertions(+), 2 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 7ece398..a9f33c6 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_ETHER_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index c7e7e41..14aae7c 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..bb67724
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,66 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+#include <stdint.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protocol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
+ * More-bits (optional) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version. */
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t oam:1;		/**< Control packet. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t reserved1:6;	/**< Reserved. */
+#else
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t ver:2;		/**< Version. */
+	uint8_t reserved1:6;	/**< Reserved. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t oam:1;		/**< Control packet. */
+#endif
+	rte_be16_t proto;	/**< Protocol type. */
+	uint8_t vni[3];		/**< Virtual network identifier. */
+	uint8_t reserved2;	/**< Reserved. */
+	uint32_t opts[];	/**< Variable length options. */
+} __rte_packed;
+
+/* GENEVE ETH next protocol types */
+#define RTE_GENEVE_TYPE_ETH	0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v6 2/3] app/testpmd: enable configuring GENEVE port
  2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-10-07 15:30                     ` Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
  2 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 15:30 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c             | 14 ++++++++++++--
 doc/guides/testpmd_app_ug/run_app.rst |  5 +++++
 2 files changed, 17 insertions(+), 2 deletions(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 1ead595..dcc9343 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,8 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= |"
 	       " --rxfreet= | --txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= | --record-core-cycles | "
-	       "--record-burst-stats]\n",
+	       "--vxlan-gpe-port= | --geneve-port= | "
+	       "--record-core-cycles | --record-burst-stats]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -202,6 +202,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-port=N: UPD port of tunnel GENEVE\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -671,6 +672,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1311,6 +1313,14 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name, "geneve-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
diff --git a/doc/guides/testpmd_app_ug/run_app.rst b/doc/guides/testpmd_app_ug/run_app.rst
index e2539f6..dbd22f1 100644
--- a/doc/guides/testpmd_app_ug/run_app.rst
+++ b/doc/guides/testpmd_app_ug/run_app.rst
@@ -426,6 +426,11 @@ The command line options are:
     Set the UDP port number of tunnel VXLAN-GPE to N.
     The default value is 4790.
 
+*   ``--geneve-port=N``
+
+    Set the UDP port number of tunnel GENEVE to N.
+    The default value is 6081.
+
 *   ``--mlockall``
 
     Enable locking all memory.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup
  2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-10-07 15:30                     ` Ophir Munk
  2020-10-07 16:05                       ` Ferruh Yigit
  2 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 15:30 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit.
It assembles all tunnel outer updates into one function call to avoid
code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.
It replaces all numeric values 4789 in their corresponding definition
RTE_VXLAN_GPE_DEFAULT_PORT.
It updates the 'csum parse-tunnel' documentation.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/cmdline_flow.c                 |  3 +-
 app/test-pmd/csumonly.c                     | 81 +++++++++--------------------
 doc/guides/testpmd_app_ug/testpmd_funcs.rst |  6 +--
 lib/librte_net/rte_vxlan.h                  |  1 +
 4 files changed, 31 insertions(+), 60 deletions(-)

diff --git a/app/test-pmd/cmdline_flow.c b/app/test-pmd/cmdline_flow.c
index 6e04d53..761ac5a 100644
--- a/app/test-pmd/cmdline_flow.c
+++ b/app/test-pmd/cmdline_flow.c
@@ -23,6 +23,7 @@
 #include <cmdline_parse_num.h>
 #include <rte_flow.h>
 #include <rte_hexdump.h>
+#include <rte_vxlan.h>
 
 #include "testpmd.h"
 
@@ -421,7 +422,7 @@ struct vxlan_encap_conf vxlan_encap_conf = {
 	.select_tos_ttl = 0,
 	.vni = "\x00\x00\x00",
 	.udp_src = 0,
-	.udp_dst = RTE_BE16(4789),
+	.udp_dst = RTE_BE16(RTE_VXLAN_DEFAULT_PORT),
 	.ipv4_src = RTE_IPV4(127, 0, 0, 1),
 	.ipv4_dst = RTE_IPV4(255, 255, 255, 255),
 	.ipv6_src = "\x00\x00\x00\x00\x00\x00\x00\x00"
diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index a9f33c6..8f2f840 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -250,18 +257,15 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 {
 	struct rte_ether_hdr *eth_hdr;
 
-	/* check udp destination port, 4789 is the default vxlan port
-	 * (rfc7348) or that the rx offload flag is set (i40e only
-	 * currently) */
-	if (udp_hdr->dst_port != _htons(4789) &&
+	/* check udp destination port, RTE_VXLAN_DEFAULT_PORT (4789) is the
+	 * default vxlan port (rfc7348) or that the rx offload flag is set
+	 * (i40e only currently)
+	 */
+	if (udp_hdr->dst_port != _htons(RTE_VXLAN_DEFAULT_PORT) &&
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +295,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +305,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +315,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +327,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +393,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +402,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +411,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/doc/guides/testpmd_app_ug/testpmd_funcs.rst b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
index 72bdb1b..bc6f2fd 100644
--- a/doc/guides/testpmd_app_ug/testpmd_funcs.rst
+++ b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
@@ -1135,11 +1135,11 @@ Where:
 * ``ip|udp|tcp|sctp`` always relate to  the inner layer.
 
 * ``outer-ip`` relates to the outer IP layer (only for IPv4) in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, gre and ipip are
+  as a tunnel packet by the forwarding engine (geneve, gre, gtp, ipip, vxlan and vxlan-gpe are
   supported). See also the ``csum parse-tunnel`` command.
 
 * ``outer-udp`` relates to the outer UDP layer in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, vxlan-gpe are
+  as a tunnel packet by the forwarding engine (geneve, gtp, vxlan and vxlan-gpe are
   supported). See also the ``csum parse-tunnel`` command.
 
 .. note::
@@ -1199,7 +1199,7 @@ engine::
    testpmd> csum parse-tunnel (on|off) (tx_port_id)
 
 If enabled, the csum forward engine will try to recognize supported
-tunnel headers (vxlan, gre, ipip).
+tunnel headers (ipip, geneve, gtp, gre, vxlan, vxlan-gpe).
 
 If disabled, treat tunnel packets as non-tunneled packets (a inner
 header is handled as a packet payload).
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd
  2020-10-06 14:58                 ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
@ 2020-10-07 15:43                   ` Ophir Munk
  2020-10-07 16:00                     ` Ferruh Yigit
  0 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-10-07 15:43 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz

Hi Ferruh,
I sent V6 which addresses your last review.

Please see more comments inline.

> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> Sent: Tuesday, October 6, 2020 5:59 PM
> On 9/18/2020 3:17 PM, Ophir Munk wrote:
> > v1:
> > Initial version
> > v2:
> > Rebased + Minor update in protocol options field:
> > char opts[0] ===> uint8_t opts[]
> > v3:
> > Rebase
> > document "geneve-port=N" parameter
> > v4:
> > Mispelling corrections
> > v5:
> > Rebase + Updates following review
> >
> https://nam11.safelinks.protection.outlook.com/?url=http%3A%2F%2Fpatch
> >
> es.dpdk.org%2Fpatch%2F77734%2F&amp;data=02%7C01%7Cophirmu%40nv
> idia.com
> >
> %7C1b01b5de39d24d61e38008d86a086ae2%7C43083d15727340c1b7db39e
> fd9ccc17a
> >
> %7C0%7C0%7C637375931691373733&amp;sdata=csLb5OdTmWlpv1k4Z7ZZ
> YN1b1d2cd8
> > %2BTxxnydgNnyQ4%3D&amp;reserved=0
> >
> > Ophir Munk (3):
> >    app/testpmd: add GENEVE parsing
> >    app/testpmd: enable configuring GENEVE port
> >    app/testpmd: reduce tunnel parsing code duplication
> >
> 
> Hi Ophir,
> 
> The patchset looks good except a few comments I put into the patches.
> 
> But I have two highlevel questions/comments,
> 
> 1) The testpmd tunnel parsing feature is not documented properly, there are
> various related commands but there is no documentation to put all together.
> What do you think putting a new section for it under the "Testpmd Runtime
> Functions" (testpmd_funcs.rst) with this patchset?

I prefer this to be in a separate patchset.
Geneve in testpmd is not complete yet. I know that there is current work in progress to add geneve options to flows.
Maybe its worth waiting till Geneve is finalized in testpmd.

> 
> 2) The 'csum' forwarding engine seems become forwarding engine for the
> case where packet payload needs to be parsed, like gro/gso, tunnel parse.
> Even the description of the forwarding engine in the documentation is not
> accurate now.
> I wonder if we should rename the forwarding engine at this stage?

Can you please be more specific to which renaming you are referring to?
Can you give examples?


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

* Re: [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd
  2020-10-07 15:43                   ` Ophir Munk
@ 2020-10-07 16:00                     ` Ferruh Yigit
  0 siblings, 0 replies; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-07 16:00 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz

On 10/7/2020 4:43 PM, Ophir Munk wrote:
> Hi Ferruh,
> I sent V6 which addresses your last review.
> 
> Please see more comments inline.
> 
>> -----Original Message-----
>> From: Ferruh Yigit <ferruh.yigit@intel.com>
>> Sent: Tuesday, October 6, 2020 5:59 PM
>> On 9/18/2020 3:17 PM, Ophir Munk wrote:
>>> v1:
>>> Initial version
>>> v2:
>>> Rebased + Minor update in protocol options field:
>>> char opts[0] ===> uint8_t opts[]
>>> v3:
>>> Rebase
>>> document "geneve-port=N" parameter
>>> v4:
>>> Mispelling corrections
>>> v5:
>>> Rebase + Updates following review
>>>
>> https://nam11.safelinks.protection.outlook.com/?url=http%3A%2F%2Fpatch
>>>
>> es.dpdk.org%2Fpatch%2F77734%2F&amp;data=02%7C01%7Cophirmu%40nv
>> idia.com
>>>
>> %7C1b01b5de39d24d61e38008d86a086ae2%7C43083d15727340c1b7db39e
>> fd9ccc17a
>>>
>> %7C0%7C0%7C637375931691373733&amp;sdata=csLb5OdTmWlpv1k4Z7ZZ
>> YN1b1d2cd8
>>> %2BTxxnydgNnyQ4%3D&amp;reserved=0
>>>
>>> Ophir Munk (3):
>>>     app/testpmd: add GENEVE parsing
>>>     app/testpmd: enable configuring GENEVE port
>>>     app/testpmd: reduce tunnel parsing code duplication
>>>
>>
>> Hi Ophir,
>>
>> The patchset looks good except a few comments I put into the patches.
>>
>> But I have two highlevel questions/comments,
>>
>> 1) The testpmd tunnel parsing feature is not documented properly, there are
>> various related commands but there is no documentation to put all together.
>> What do you think putting a new section for it under the "Testpmd Runtime
>> Functions" (testpmd_funcs.rst) with this patchset?
> 
> I prefer this to be in a separate patchset.
> Geneve in testpmd is not complete yet. I know that there is current work in progress to add geneve options to flows.
> Maybe its worth waiting till Geneve is finalized in testpmd.
> 
>>
>> 2) The 'csum' forwarding engine seems become forwarding engine for the
>> case where packet payload needs to be parsed, like gro/gso, tunnel parse.
>> Even the description of the forwarding engine in the documentation is not
>> accurate now.
>> I wonder if we should rename the forwarding engine at this stage?
> 
> Can you please be more specific to which renaming you are referring to?
> Can you give examples?
> 

I am asking about forwarding engine name, it is 'csum' and in documentation it 
is described as:
"
Changes the checksum field with hardware or software methods depending on the 
offload flags on the packet.
"

So the initial purpose of the forwarding engine is to calculate checksums (or 
offload calculation to HW) before sending packets, but now it detects and parses 
the tunneling protocols and updates packet accordingly and logs it.
It also does GRO and GSO.

Is the forwarding engine name 'csum' still make sense, or should we find 
something else. I don't have any suggestion, just the question.


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

* Re: [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
@ 2020-10-07 16:05                       ` Ferruh Yigit
  0 siblings, 0 replies; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-07 16:05 UTC (permalink / raw)
  To: Ophir Munk, dev, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

On 10/7/2020 4:30 PM, Ophir Munk wrote:
> From: Ophir Munk <ophirmu@mellanox.com>
> 
> This is a cleanup commit.
> It assembles all tunnel outer updates into one function call to avoid
> code duplications.
> It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
> other tunnel protocol definitions.
> It replaces all numeric values 4789 in their corresponding definition
> RTE_VXLAN_GPE_DEFAULT_PORT.
> It updates the 'csum parse-tunnel' documentation.
> 
> Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
> ---
>   app/test-pmd/cmdline_flow.c                 |  3 +-
>   app/test-pmd/csumonly.c                     | 81 +++++++++--------------------
>   doc/guides/testpmd_app_ug/testpmd_funcs.rst |  6 +--

I think this documentation update should be part of 1/3, if there will be a new 
version can you please move, if not I can do myself while merging.

>   lib/librte_net/rte_vxlan.h                  |  1 +
>   4 files changed, 31 insertions(+), 60 deletions(-)

<...>

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

* Re: [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-10-07 14:52                     ` Ophir Munk
@ 2020-10-07 16:25                       ` Ferruh Yigit
  2020-10-08  8:44                         ` Ophir Munk
  0 siblings, 1 reply; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-07 16:25 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk

On 10/7/2020 3:52 PM, Ophir Munk wrote:
> Hi Ferruh,
> Please find comments inline.
> 
>> -----Original Message-----
>> From: Ferruh Yigit <ferruh.yigit@intel.com>
>> Sent: Tuesday, October 6, 2020 5:31 PM
>> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
> <...>
>>>
>>>    uint16_t vxlan_gpe_udp_port = 4790;
>>> +uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
>>>
>>
>> There is a testpmd command to configure the NIC for GENEVE port, "port
>> config (port_id) udp_tunnel_port add|rm vxlan|geneve|vxlan-gpe
>> (udp_port)"
>>
>> You are adding support to testpmd to parse the GENEVE packets, but I think
>> these two commads should be consistent.
>>
>> What do you think "port config N add geneve X" update the
>> 'geneve_udp_port=X"?
>>
>> <...>
>>
> 
> It is not as simple as suggested.
> The command "port config N add geneve X" can be repeated several times - adding another geneve port to the NIC Hardware/Firmware to recognize. As a result the NIC is configured with multiple geneve ports. On the other hand geneve_udp_port is a single variable - so whenever a new "port config" command is executed - we will override the last geneve port and forget all the precedent ones.
> The port config command also has a "rm" option in addition to "add". So if we removed the last port - what will we assigned to geneve_udp_port? We need to have a small data base for managing geneve ports.
> testpmd also has an option " --geneve-port=N". It should be synched with the "port config" command.
> 
> Another issue to consider is if there is a need for the suggested feature. I think the "port config" is mainly targeted for offloading. So the NIC will probably encap/decap a packet with geneve - leaving testpmd paring unneeded.
> 
> My point is that your suggestion requires an RFC before implementation.
> 

I am not sure about adding database for geneve ports, I think no need to make it 
more complex.

Only when user set via "--geneve-port=N", it is the port for testpmd to parse 
(same for 'geneve_udp_port' global variable), but when user give command "port 
config N add geneve X" it is to configure the NIC to offload the parsing.
This is too confusing, user can't know (or remember) this without checking the 
source code.

Can we rename the command and variable to highlight that it is for testpmd to 
parse, I think that will be enough, instead of trying to merge them, which is 
hard as you described above.

What do you think for "--testpmd-geneve-port=N" parameter and 
'testpmd_geneve_udp_port' variable name?
We can also update the documentation to say this is only the port testpmd uses 
for parsing, HW may be configured to use another port.


>>
>>> @@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream
>> *fs)
>>>    				}
>>>    				parse_vxlan(udp_hdr, &info,
>>>    					    m->packet_type);
>>> -				if (info.is_tunnel)
>>> +				if (info.is_tunnel) {
>>>    					tx_ol_flags |=
>>>    						PKT_TX_TUNNEL_VXLAN;
>>> +					goto tunnel_update;
>>> +				}
>>> +				parse_geneve(udp_hdr, &info);
>>> +				if (info.is_tunnel) {
>>> +					tx_ol_flags |=
>>> +						PKT_TX_TUNNEL_GENEVE;
>>> +					goto tunnel_update;
>>> +				}
>>
>> Can you please update the "csum parse-tunnel" documentation to mention
>> "geneve"
>> protocol?
> 
> Done in v6. I added other missing tunnel protocols (in alphabetical order) such as "gtp". Since it is more than geneve I added it to the 3rd (cleanup) commit.
> 

Would you mind adding the 'geneve' with the patch adding 'geneve' support (1/3), 
and add the other missing ones in the patch 3/3 ?

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

* Re: [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-10-07 16:25                       ` Ferruh Yigit
@ 2020-10-08  8:44                         ` Ophir Munk
  2020-10-08 13:37                           ` Ferruh Yigit
  0 siblings, 1 reply; 50+ messages in thread
From: Ophir Munk @ 2020-10-08  8:44 UTC (permalink / raw)
  To: Ferruh Yigit, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk



> -----Original Message-----
> From: Ferruh Yigit <ferruh.yigit@intel.com>
> Sent: Wednesday, October 7, 2020 7:25 PM
> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
<...>
> Only when user set via "--geneve-port=N", it is the port for testpmd to parse
> (same for 'geneve_udp_port' global variable), but when user give command
> "port config N add geneve X" it is to configure the NIC to offload the parsing.
> This is too confusing, user can't know (or remember) this without checking
> the source code.
> 
> Can we rename the command and variable to highlight that it is for testpmd
> to parse, I think that will be enough, instead of trying to merge them, which
> is hard as you described above.
> 
> What do you think for "--testpmd-geneve-port=N" parameter and
> 'testpmd_geneve_udp_port' variable name?

I am suggesting two options:
1. "--geneve-port-identifier=N" and "geneve_udp_port_identifier" as variable name.
2. "--geneve-parsed-port=N" and "geneve_udp_port" as variable name.
Can you select one of them?

> We can also update the documentation to say this is only the port testpmd
> uses for parsing, HW may be configured to use another port.
> 

Will update documentation.

<...>
> > Done in v6. I added other missing tunnel protocols (in alphabetical order)
> such as "gtp". Since it is more than geneve I added it to the 3rd (cleanup)
> commit.
> >
> 
> Would you mind adding the 'geneve' with the patch adding 'geneve' support
> (1/3), and add the other missing ones in the patch 3/3 ?

Will update accordingly


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

* Re: [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing
  2020-10-08  8:44                         ` Ophir Munk
@ 2020-10-08 13:37                           ` Ferruh Yigit
  0 siblings, 0 replies; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-08 13:37 UTC (permalink / raw)
  To: Ophir Munk, dev, Wenzhuo Lu, Beilei Xing, Bernard Iremonger,
	Olivier Matz
  Cc: Ophir Munk

On 10/8/2020 9:44 AM, Ophir Munk wrote:
> 
> 
>> -----Original Message-----
>> From: Ferruh Yigit <ferruh.yigit@intel.com>
>> Sent: Wednesday, October 7, 2020 7:25 PM
>> To: Ophir Munk <ophirmu@nvidia.com>; dev@dpdk.org; Wenzhuo Lu
> <...>
>> Only when user set via "--geneve-port=N", it is the port for testpmd to parse
>> (same for 'geneve_udp_port' global variable), but when user give command
>> "port config N add geneve X" it is to configure the NIC to offload the parsing.
>> This is too confusing, user can't know (or remember) this without checking
>> the source code.
>>
>> Can we rename the command and variable to highlight that it is for testpmd
>> to parse, I think that will be enough, instead of trying to merge them, which
>> is hard as you described above.
>>
>> What do you think for "--testpmd-geneve-port=N" parameter and
>> 'testpmd_geneve_udp_port' variable name?
> 
> I am suggesting two options:
> 1. "--geneve-port-identifier=N" and "geneve_udp_port_identifier" as variable name.
> 2. "--geneve-parsed-port=N" and "geneve_udp_port" as variable name.
> Can you select one of them?
> 

I think 'identifier' doesn't add any more clarification, lets go with (2). Thanks.

>> We can also update the documentation to say this is only the port testpmd
>> uses for parsing, HW may be configured to use another port.
>>
> 
> Will update documentation.
> 
> <...>
>>> Done in v6. I added other missing tunnel protocols (in alphabetical order)
>> such as "gtp". Since it is more than geneve I added it to the 3rd (cleanup)
>> commit.
>>>
>>
>> Would you mind adding the 'geneve' with the patch adding 'geneve' support
>> (1/3), and add the other missing ones in the patch 3/3 ?
> 
> Will update accordingly
> 


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

* [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd
  2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-10-08 20:16                       ` Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 1/3] app/testpmd: add GENEVE parsing Ophir Munk
                                           ` (3 more replies)
  0 siblings, 4 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-08 20:16 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

v1:
Initial version
v2:
Rebased + Minor update in protocol options field:
char opts[0] ===> uint8_t opts[]
v3:
Rebase
document "geneve-port=N" parameter
v4:
Mispelling corrections
v5:
Rebase + Updates following review
http://patches.dpdk.org/patch/77734/
v6:
Rebase + Updates following reviews: more cleanup and added documentation.
v7:
Updates following reviews: rename geneve-port as geneve-parsed-port + added documentation.


Ophir Munk (3):
  app/testpmd: add GENEVE parsing
  app/testpmd: enable configuring GENEVE port
  app/testpmd: tunnel parsing protocols cleanup

 app/test-pmd/cmdline_flow.c                 |   3 +-
 app/test-pmd/csumonly.c                     | 129 ++++++++++++++++++----------
 app/test-pmd/parameters.c                   |  15 +++-
 app/test-pmd/testpmd.h                      |   1 +
 doc/guides/testpmd_app_ug/run_app.rst       |   6 ++
 doc/guides/testpmd_app_ug/testpmd_funcs.rst |   6 +-
 lib/librte_net/meson.build                  |   3 +-
 lib/librte_net/rte_geneve.h                 |  66 ++++++++++++++
 lib/librte_net/rte_vxlan.h                  |   1 +
 9 files changed, 177 insertions(+), 53 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

-- 
2.8.4


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

* [dpdk-dev] [PATCH v7 1/3] app/testpmd: add GENEVE parsing
  2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
@ 2020-10-08 20:16                         ` Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
                                           ` (2 subsequent siblings)
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-08 20:16 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

GENEVE is a widely used tunneling protocol in modern Virtualized
Networks. testpmd already supports parsing of several tunneling
protocols including VXLAN, VXLAN-GPE, GRE. This commit adds GENEVE
parsing of inner protocols (IPv4-0x0800, IPv6-0x86dd, Ethernet-0x6558)
based on IETF draft-ietf-nvo3-geneve-09. GENEVE is considered more
flexible than the other protocols.  In terms of protocol format GENEVE
header has a variable length options as opposed to other tunneling
protocols which have a fixed header size.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/csumonly.c                     | 70 ++++++++++++++++++++++++++++-
 app/test-pmd/testpmd.h                      |  1 +
 doc/guides/testpmd_app_ug/testpmd_funcs.rst |  6 +--
 lib/librte_net/meson.build                  |  3 +-
 lib/librte_net/rte_geneve.h                 | 66 +++++++++++++++++++++++++++
 5 files changed, 141 insertions(+), 5 deletions(-)
 create mode 100644 lib/librte_net/rte_geneve.h

diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index 7ece398..a9f33c6 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -43,6 +43,7 @@
 #include <rte_flow.h>
 #include <rte_gro.h>
 #include <rte_gso.h>
+#include <rte_geneve.h>
 
 #include "testpmd.h"
 
@@ -63,6 +64,7 @@
 #endif
 
 uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
 struct testpmd_offload_info {
@@ -333,6 +335,64 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
+/* Parse a geneve header */
+static void
+parse_geneve(struct rte_udp_hdr *udp_hdr,
+	    struct testpmd_offload_info *info)
+{
+	struct rte_ether_hdr *eth_hdr;
+	struct rte_ipv4_hdr *ipv4_hdr;
+	struct rte_ipv6_hdr *ipv6_hdr;
+	struct rte_geneve_hdr *geneve_hdr;
+	uint16_t geneve_len;
+
+	/* Check udp destination port. */
+	if (udp_hdr->dst_port != _htons(geneve_udp_port))
+		return;
+
+	geneve_hdr = (struct rte_geneve_hdr *)((char *)udp_hdr +
+				sizeof(struct rte_udp_hdr));
+	geneve_len = sizeof(struct rte_geneve_hdr) + geneve_hdr->opt_len * 4;
+	if (!geneve_hdr->proto || geneve_hdr->proto ==
+	    _htons(RTE_ETHER_TYPE_IPV4)) {
+		update_tunnel_outer(info);
+		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		parse_ipv4(ipv4_hdr, info);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV4);
+		info->l2_len = 0;
+	} else if (geneve_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
+		update_tunnel_outer(info);
+		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)geneve_hdr +
+			   geneve_len);
+		info->ethertype = _htons(RTE_ETHER_TYPE_IPV6);
+		parse_ipv6(ipv6_hdr, info);
+		info->l2_len = 0;
+
+	} else if (geneve_hdr->proto == _htons(RTE_GENEVE_TYPE_ETH)) {
+		update_tunnel_outer(info);
+		eth_hdr = (struct rte_ether_hdr *)((char *)geneve_hdr +
+			  geneve_len);
+		parse_ethernet(eth_hdr, info);
+	} else
+		return;
+
+	info->l2_len +=
+		(sizeof(struct rte_udp_hdr) + sizeof(struct rte_geneve_hdr) +
+		((struct rte_geneve_hdr *)geneve_hdr)->opt_len * 4);
+}
+
 /* Parse a gre header */
 static void
 parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
@@ -865,9 +925,17 @@ pkt_burst_checksum_forward(struct fwd_stream *fs)
 				}
 				parse_vxlan(udp_hdr, &info,
 					    m->packet_type);
-				if (info.is_tunnel)
+				if (info.is_tunnel) {
 					tx_ol_flags |=
 						PKT_TX_TUNNEL_VXLAN;
+					goto tunnel_update;
+				}
+				parse_geneve(udp_hdr, &info);
+				if (info.is_tunnel) {
+					tx_ol_flags |=
+						PKT_TX_TUNNEL_GENEVE;
+					goto tunnel_update;
+				}
 			} else if (info.l4_proto == IPPROTO_GRE) {
 				struct simple_gre_hdr *gre_hdr;
 
diff --git a/app/test-pmd/testpmd.h b/app/test-pmd/testpmd.h
index c7e7e41..14aae7c 100644
--- a/app/test-pmd/testpmd.h
+++ b/app/test-pmd/testpmd.h
@@ -452,6 +452,7 @@ extern struct fwd_lcore  **fwd_lcores;
 extern struct fwd_stream **fwd_streams;
 
 extern uint16_t vxlan_gpe_udp_port; /**< UDP port of tunnel VXLAN-GPE. */
+extern uint16_t geneve_udp_port; /**< UDP port of tunnel GENEVE. */
 
 extern portid_t nb_peer_eth_addrs; /**< Number of peer ethernet addresses. */
 extern struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS];
diff --git a/doc/guides/testpmd_app_ug/testpmd_funcs.rst b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
index 72bdb1b..c448e2d 100644
--- a/doc/guides/testpmd_app_ug/testpmd_funcs.rst
+++ b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
@@ -1135,11 +1135,11 @@ Where:
 * ``ip|udp|tcp|sctp`` always relate to  the inner layer.
 
 * ``outer-ip`` relates to the outer IP layer (only for IPv4) in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, gre and ipip are
+  as a tunnel packet by the forwarding engine (vxlan, gre, ipip and geneve are
   supported). See also the ``csum parse-tunnel`` command.
 
 * ``outer-udp`` relates to the outer UDP layer in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, vxlan-gpe are
+  as a tunnel packet by the forwarding engine (vxlan, vxlan-gpe, geneve are
   supported). See also the ``csum parse-tunnel`` command.
 
 .. note::
@@ -1199,7 +1199,7 @@ engine::
    testpmd> csum parse-tunnel (on|off) (tx_port_id)
 
 If enabled, the csum forward engine will try to recognize supported
-tunnel headers (vxlan, gre, ipip).
+tunnel headers (vxlan, gre, ipip, geneve).
 
 If disabled, treat tunnel packets as non-tunneled packets (a inner
 header is handled as a packet payload).
diff --git a/lib/librte_net/meson.build b/lib/librte_net/meson.build
index 24ed825..52d3a97 100644
--- a/lib/librte_net/meson.build
+++ b/lib/librte_net/meson.build
@@ -16,7 +16,8 @@ headers = files('rte_ip.h',
 	'rte_net_crc.h',
 	'rte_mpls.h',
 	'rte_higig.h',
-	'rte_ecpri.h')
+	'rte_ecpri.h',
+	'rte_geneve.h')
 
 sources = files('rte_arp.c', 'rte_ether.c', 'rte_net.c', 'rte_net_crc.c')
 deps += ['mbuf']
diff --git a/lib/librte_net/rte_geneve.h b/lib/librte_net/rte_geneve.h
new file mode 100644
index 0000000..bb67724
--- /dev/null
+++ b/lib/librte_net/rte_geneve.h
@@ -0,0 +1,66 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright 2020 Mellanox Technologies, Ltd
+ */
+
+#ifndef _RTE_GENEVE_H_
+#define _RTE_GENEVE_H_
+
+/**
+ * @file
+ *
+ * GENEVE-related definitions
+ */
+#include <stdint.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** GENEVE default port. */
+#define RTE_GENEVE_DEFAULT_PORT 6081
+
+/**
+ * GENEVE protocol header. (draft-ietf-nvo3-geneve-09)
+ * Contains:
+ * 2-bits version (must be 0).
+ * 6-bits option length in four byte multiples, not including the eight
+ *	bytes of the fixed tunnel header.
+ * 1-bit control packet.
+ * 1-bit critical options in packet.
+ * 6-bits reserved
+ * 16-bits Protocol Type. The protocol data unit after the Geneve header
+ *	following the EtherType convention. Ethernet itself is represented by
+ *	the value 0x6558.
+ * 24-bits Virtual Network Identifier (VNI). Virtual network unique identified.
+ * 8-bits reserved bits (must be 0 on transmission and ignored on receipt).
+ * More-bits (optional) variable length options.
+ */
+__extension__
+struct rte_geneve_hdr {
+#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN
+	uint8_t ver:2;		/**< Version. */
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t oam:1;		/**< Control packet. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t reserved1:6;	/**< Reserved. */
+#else
+	uint8_t opt_len:6;	/**< Options length. */
+	uint8_t ver:2;		/**< Version. */
+	uint8_t reserved1:6;	/**< Reserved. */
+	uint8_t critical:1;	/**< Critical packet. */
+	uint8_t oam:1;		/**< Control packet. */
+#endif
+	rte_be16_t proto;	/**< Protocol type. */
+	uint8_t vni[3];		/**< Virtual network identifier. */
+	uint8_t reserved2;	/**< Reserved. */
+	uint32_t opts[];	/**< Variable length options. */
+} __rte_packed;
+
+/* GENEVE ETH next protocol types */
+#define RTE_GENEVE_TYPE_ETH	0x6558 /**< Ethernet Protocol. */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RTE_GENEVE_H_ */
-- 
2.8.4


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

* [dpdk-dev] [PATCH v7 2/3] app/testpmd: enable configuring GENEVE port
  2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 1/3] app/testpmd: add GENEVE parsing Ophir Munk
@ 2020-10-08 20:16                         ` Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
  2020-10-09 12:49                         ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-08 20:16 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

IANA has assigned port 6081 as the fixed well-known destination port for
GENEVE. Nevertheless draft-ietf-nvo3-geneve-09 recommends that
implementations make this configurable.  This commit enables specifying
any positive UDP destination port number for GENEVE protocol parsing.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/parameters.c             | 15 +++++++++++++--
 doc/guides/testpmd_app_ug/run_app.rst |  6 ++++++
 2 files changed, 19 insertions(+), 2 deletions(-)

diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
index 1ead595..15ce8c1 100644
--- a/app/test-pmd/parameters.c
+++ b/app/test-pmd/parameters.c
@@ -70,8 +70,8 @@ usage(char* progname)
 	       "--rxpt= | --rxht= | --rxwt= |"
 	       " --rxfreet= | --txpt= | --txht= | --txwt= | --txfreet= | "
 	       "--txrst= | --tx-offloads= | | --rx-offloads= | "
-	       "--vxlan-gpe-port= | --record-core-cycles | "
-	       "--record-burst-stats]\n",
+	       "--vxlan-gpe-port= | --geneve-parsed-port= | "
+	       "--record-core-cycles | --record-burst-stats]\n",
 	       progname);
 #ifdef RTE_LIBRTE_CMDLINE
 	printf("  --interactive: run in interactive mode.\n");
@@ -202,6 +202,7 @@ usage(char* progname)
 	printf("  --rx-offloads=0xXXXXXXXX: hexadecimal bitmask of RX queue offloads\n");
 	printf("  --hot-plug: enable hot plug for device.\n");
 	printf("  --vxlan-gpe-port=N: UPD port of tunnel VXLAN-GPE\n");
+	printf("  --geneve-parsed-port=N: UPD port to parse GENEVE tunnel protocol\n");
 	printf("  --mlockall: lock all memory\n");
 	printf("  --no-mlockall: do not lock all memory\n");
 	printf("  --mp-alloc <native|anon|xmem|xmemhuge>: mempool allocation method.\n"
@@ -671,6 +672,7 @@ launch_args_parse(int argc, char** argv)
 		{ "rx-offloads",		1, 0, 0 },
 		{ "hot-plug",			0, 0, 0 },
 		{ "vxlan-gpe-port",		1, 0, 0 },
+		{ "geneve-parsed-port",		1, 0, 0 },
 		{ "mlockall",			0, 0, 0 },
 		{ "no-mlockall",		0, 0, 0 },
 		{ "mp-alloc",			1, 0, 0 },
@@ -1311,6 +1313,15 @@ launch_args_parse(int argc, char** argv)
 					rte_exit(EXIT_FAILURE,
 						 "vxlan-gpe-port must be >= 0\n");
 			}
+			if (!strcmp(lgopts[opt_idx].name,
+				    "geneve-parsed-port")) {
+				n = atoi(optarg);
+				if (n >= 0)
+					geneve_udp_port = (uint16_t)n;
+				else
+					rte_exit(EXIT_FAILURE,
+						 "geneve-parsed-port must be >= 0\n");
+			}
 			if (!strcmp(lgopts[opt_idx].name, "print-event"))
 				if (parse_event_printing_config(optarg, 1)) {
 					rte_exit(EXIT_FAILURE,
diff --git a/doc/guides/testpmd_app_ug/run_app.rst b/doc/guides/testpmd_app_ug/run_app.rst
index e2539f6..ec085c2 100644
--- a/doc/guides/testpmd_app_ug/run_app.rst
+++ b/doc/guides/testpmd_app_ug/run_app.rst
@@ -426,6 +426,12 @@ The command line options are:
     Set the UDP port number of tunnel VXLAN-GPE to N.
     The default value is 4790.
 
+*   ``--geneve-parsed-port=N``
+
+    Set the UDP port number that is used for parsing the GENEVE protocol to N.
+    HW may be configured with another tunnel Geneve port.
+    The default value is 6081.
+
 *   ``--mlockall``
 
     Enable locking all memory.
-- 
2.8.4


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

* [dpdk-dev] [PATCH v7 3/3] app/testpmd: tunnel parsing protocols cleanup
  2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 1/3] app/testpmd: add GENEVE parsing Ophir Munk
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
@ 2020-10-08 20:16                         ` Ophir Munk
  2020-10-09 12:49                         ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
  3 siblings, 0 replies; 50+ messages in thread
From: Ophir Munk @ 2020-10-08 20:16 UTC (permalink / raw)
  To: dev, Ferruh Yigit, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

From: Ophir Munk <ophirmu@mellanox.com>

This is a cleanup commit.
It assembles all tunnel outer updates into one function call to avoid
code duplications.
It defines RTE_VXLAN_GPE_DEFAULT_PORT (4790) in accordance with all
other tunnel protocol definitions.
It replaces all numeric values 4789 in their corresponding definition
RTE_VXLAN_GPE_DEFAULT_PORT.
It updates the 'csum parse-tunnel' documentation.

Signed-off-by: Ophir Munk <ophirmu@mellanox.com>
---
 app/test-pmd/cmdline_flow.c                 |  3 +-
 app/test-pmd/csumonly.c                     | 81 +++++++++--------------------
 doc/guides/testpmd_app_ug/testpmd_funcs.rst |  6 +--
 lib/librte_net/rte_vxlan.h                  |  1 +
 4 files changed, 31 insertions(+), 60 deletions(-)

diff --git a/app/test-pmd/cmdline_flow.c b/app/test-pmd/cmdline_flow.c
index 6e04d53..761ac5a 100644
--- a/app/test-pmd/cmdline_flow.c
+++ b/app/test-pmd/cmdline_flow.c
@@ -23,6 +23,7 @@
 #include <cmdline_parse_num.h>
 #include <rte_flow.h>
 #include <rte_hexdump.h>
+#include <rte_vxlan.h>
 
 #include "testpmd.h"
 
@@ -421,7 +422,7 @@ struct vxlan_encap_conf vxlan_encap_conf = {
 	.select_tos_ttl = 0,
 	.vni = "\x00\x00\x00",
 	.udp_src = 0,
-	.udp_dst = RTE_BE16(4789),
+	.udp_dst = RTE_BE16(RTE_VXLAN_DEFAULT_PORT),
 	.ipv4_src = RTE_IPV4(127, 0, 0, 1),
 	.ipv4_dst = RTE_IPV4(255, 255, 255, 255),
 	.ipv6_src = "\x00\x00\x00\x00\x00\x00\x00\x00"
diff --git a/app/test-pmd/csumonly.c b/app/test-pmd/csumonly.c
index a9f33c6..8f2f840 100644
--- a/app/test-pmd/csumonly.c
+++ b/app/test-pmd/csumonly.c
@@ -63,7 +63,7 @@
 #define _htons(x) (x)
 #endif
 
-uint16_t vxlan_gpe_udp_port = 4790;
+uint16_t vxlan_gpe_udp_port = RTE_VXLAN_GPE_DEFAULT_PORT;
 uint16_t geneve_udp_port = RTE_GENEVE_DEFAULT_PORT;
 
 /* structure that caches offload info for the current packet */
@@ -181,6 +181,17 @@ parse_ethernet(struct rte_ether_hdr *eth_hdr, struct testpmd_offload_info *info)
 	}
 }
 
+/* Fill in outer layers length */
+static void
+update_tunnel_outer(struct testpmd_offload_info *info)
+{
+	info->is_tunnel = 1;
+	info->outer_ethertype = info->ethertype;
+	info->outer_l2_len = info->l2_len;
+	info->outer_l3_len = info->l3_len;
+	info->outer_l4_proto = info->l4_proto;
+}
+
 /*
  * Parse a GTP protocol header.
  * No optional fields and next extension header type.
@@ -201,11 +212,7 @@ parse_gtp(struct rte_udp_hdr *udp_hdr,
 	    udp_hdr->dst_port != _htons(RTE_GTPU_UDP_PORT))
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 	info->l2_len = 0;
 
 	gtp_hdr = (struct rte_gtp_hdr *)((char *)udp_hdr +
@@ -250,18 +257,15 @@ parse_vxlan(struct rte_udp_hdr *udp_hdr,
 {
 	struct rte_ether_hdr *eth_hdr;
 
-	/* check udp destination port, 4789 is the default vxlan port
-	 * (rfc7348) or that the rx offload flag is set (i40e only
-	 * currently) */
-	if (udp_hdr->dst_port != _htons(4789) &&
+	/* check udp destination port, RTE_VXLAN_DEFAULT_PORT (4789) is the
+	 * default vxlan port (rfc7348) or that the rx offload flag is set
+	 * (i40e only currently)
+	 */
+	if (udp_hdr->dst_port != _htons(RTE_VXLAN_DEFAULT_PORT) &&
 		RTE_ETH_IS_TUNNEL_PKT(pkt_type) == 0)
 		return;
 
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
+	update_tunnel_outer(info);
 
 	eth_hdr = (struct rte_ether_hdr *)((char *)udp_hdr +
 		sizeof(struct rte_udp_hdr) +
@@ -291,11 +295,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 
 	if (!vxlan_gpe_hdr->proto || vxlan_gpe_hdr->proto ==
 	    RTE_VXLAN_GPE_TYPE_IPV4) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -305,11 +305,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_IPV6) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)vxlan_gpe_hdr +
 			   vxlan_gpe_len);
@@ -319,11 +315,7 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 		info->l2_len = 0;
 
 	} else if (vxlan_gpe_hdr->proto == RTE_VXLAN_GPE_TYPE_ETH) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)vxlan_gpe_hdr +
 			  vxlan_gpe_len);
@@ -335,17 +327,6 @@ parse_vxlan_gpe(struct rte_udp_hdr *udp_hdr,
 	info->l2_len += RTE_ETHER_VXLAN_GPE_HLEN;
 }
 
-/* Fill in outer layers length */
-static void
-update_tunnel_outer(struct testpmd_offload_info *info)
-{
-	info->is_tunnel = 1;
-	info->outer_ethertype = info->ethertype;
-	info->outer_l2_len = info->l2_len;
-	info->outer_l3_len = info->l3_len;
-	info->outer_l4_proto = info->l4_proto;
-}
-
 /* Parse a geneve header */
 static void
 parse_geneve(struct rte_udp_hdr *udp_hdr,
@@ -412,11 +393,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		gre_len += GRE_EXT_LEN;
 
 	if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV4)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv4_hdr = (struct rte_ipv4_hdr *)((char *)gre_hdr + gre_len);
 
@@ -425,11 +402,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_IPV6)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		ipv6_hdr = (struct rte_ipv6_hdr *)((char *)gre_hdr + gre_len);
 
@@ -438,11 +411,7 @@ parse_gre(struct simple_gre_hdr *gre_hdr, struct testpmd_offload_info *info)
 		info->l2_len = 0;
 
 	} else if (gre_hdr->proto == _htons(RTE_ETHER_TYPE_TEB)) {
-		info->is_tunnel = 1;
-		info->outer_ethertype = info->ethertype;
-		info->outer_l2_len = info->l2_len;
-		info->outer_l3_len = info->l3_len;
-		info->outer_l4_proto = info->l4_proto;
+		update_tunnel_outer(info);
 
 		eth_hdr = (struct rte_ether_hdr *)((char *)gre_hdr + gre_len);
 
diff --git a/doc/guides/testpmd_app_ug/testpmd_funcs.rst b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
index c448e2d..5cd2079 100644
--- a/doc/guides/testpmd_app_ug/testpmd_funcs.rst
+++ b/doc/guides/testpmd_app_ug/testpmd_funcs.rst
@@ -1135,11 +1135,11 @@ Where:
 * ``ip|udp|tcp|sctp`` always relate to  the inner layer.
 
 * ``outer-ip`` relates to the outer IP layer (only for IPv4) in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, gre, ipip and geneve are
+  as a tunnel packet by the forwarding engine (geneve, gre, gtp, ipip, vxlan and vxlan-gpe are
   supported). See also the ``csum parse-tunnel`` command.
 
 * ``outer-udp`` relates to the outer UDP layer in the case where the packet is recognized
-  as a tunnel packet by the forwarding engine (vxlan, vxlan-gpe, geneve are
+  as a tunnel packet by the forwarding engine (geneve, gtp, vxlan and vxlan-gpe are
   supported). See also the ``csum parse-tunnel`` command.
 
 .. note::
@@ -1199,7 +1199,7 @@ engine::
    testpmd> csum parse-tunnel (on|off) (tx_port_id)
 
 If enabled, the csum forward engine will try to recognize supported
-tunnel headers (vxlan, gre, ipip, geneve).
+tunnel headers (geneve, gtp, gre, ipip, vxlan, vxlan-gpe).
 
 If disabled, treat tunnel packets as non-tunneled packets (a inner
 header is handled as a packet payload).
diff --git a/lib/librte_net/rte_vxlan.h b/lib/librte_net/rte_vxlan.h
index c23c10c..2ad6061 100644
--- a/lib/librte_net/rte_vxlan.h
+++ b/lib/librte_net/rte_vxlan.h
@@ -22,6 +22,7 @@ extern "C" {
 
 /** VXLAN default port. */
 #define RTE_VXLAN_DEFAULT_PORT 4789
+#define RTE_VXLAN_GPE_DEFAULT_PORT 4790
 
 /**
  * VXLAN protocol header.
-- 
2.8.4


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

* Re: [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd
  2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
                                           ` (2 preceding siblings ...)
  2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
@ 2020-10-09 12:49                         ` Ferruh Yigit
  3 siblings, 0 replies; 50+ messages in thread
From: Ferruh Yigit @ 2020-10-09 12:49 UTC (permalink / raw)
  To: Ophir Munk, dev, Olivier Matz, Wenzhuo Lu, Jingjing Wu,
	Bernard Iremonger
  Cc: Ophir Munk

On 10/8/2020 9:16 PM, Ophir Munk wrote:
> v1:
> Initial version
> v2:
> Rebased + Minor update in protocol options field:
> char opts[0] ===> uint8_t opts[]
> v3:
> Rebase
> document "geneve-port=N" parameter
> v4:
> Mispelling corrections
> v5:
> Rebase + Updates following review
> http://patches.dpdk.org/patch/77734/
> v6:
> Rebase + Updates following reviews: more cleanup and added documentation.
> v7:
> Updates following reviews: rename geneve-port as geneve-parsed-port + added documentation.
> 
> 
> Ophir Munk (3):
>    app/testpmd: add GENEVE parsing
>    app/testpmd: enable configuring GENEVE port
>    app/testpmd: tunnel parsing protocols cleanup
> 

For series,
Reviewed-by: Ferruh Yigit <ferruh.yigit@intel.com>

Series applied to dpdk-next-net/main, thanks.

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

end of thread, back to index

Thread overview: 50+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-07-29  8:29 [dpdk-dev] [PATCH v1 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-07-29  8:29 ` [dpdk-dev] [PATCH v1 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
2020-08-27  7:02   ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-09-14 17:27       ` Ferruh Yigit
2020-09-15 12:53       ` [dpdk-dev] [PATCH v3 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-09-15 13:17           ` [dpdk-dev] [PATCH v4 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-09-15 13:56               ` Ophir Munk
2020-09-17 12:23               ` Olivier Matz
2020-09-18 14:21                 ` Ophir Munk
2020-09-18 14:17               ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-10-06 14:30                   ` Ferruh Yigit
2020-10-07 14:52                     ` Ophir Munk
2020-10-07 16:25                       ` Ferruh Yigit
2020-10-08  8:44                         ` Ophir Munk
2020-10-08 13:37                           ` Ferruh Yigit
2020-10-07 15:30                   ` [dpdk-dev] [PATCH v6 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-10-08 20:16                       ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk
2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 1/3] app/testpmd: add GENEVE parsing Ophir Munk
2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-10-08 20:16                         ` [dpdk-dev] [PATCH v7 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
2020-10-09 12:49                         ` [dpdk-dev] [PATCH v7 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-10-07 15:30                     ` [dpdk-dev] [PATCH v6 3/3] app/testpmd: tunnel parsing protocols cleanup Ophir Munk
2020-10-07 16:05                       ` Ferruh Yigit
2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-09-18 14:17                 ` [dpdk-dev] [PATCH v5 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
2020-10-06 14:30                   ` Ferruh Yigit
2020-10-07 10:56                     ` Ophir Munk
2020-10-06 14:58                 ` [dpdk-dev] [PATCH v5 0/3] Add GENEVE protocol parsing to testpmd Ferruh Yigit
2020-10-07 15:43                   ` Ophir Munk
2020-10-07 16:00                     ` Ferruh Yigit
2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-09-15 13:17             ` [dpdk-dev] [PATCH v4 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-09-15 12:53         ` [dpdk-dev] [PATCH v3 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 2/3] app/testpmd: enable configuring GENEVE port Ophir Munk
2020-09-14 17:31       ` Ferruh Yigit
2020-09-15  8:46         ` Ophir Munk
2020-09-15 11:07           ` Ferruh Yigit
2020-09-15 12:59             ` Ophir Munk
2020-09-15 13:19               ` Ophir Munk
2020-08-27  7:02     ` [dpdk-dev] [PATCH v2 3/3] app/testpmd: reduce tunnel parsing code duplication Ophir Munk
2020-08-31  6:40     ` [dpdk-dev] [PATCH v2 0/3] Add GENEVE protocol parsing to testpmd Ophir Munk

DPDK patches and discussions

Archives are clonable:
	git clone --mirror https://inbox.dpdk.org/dev/0 dev/git/0.git

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


Newsgroup available over NNTP:
	nntp://inbox.dpdk.org/inbox.dpdk.dev


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