From: Radu Nicolau <radu.nicolau@intel.com>
To: Radu Nicolau <radu.nicolau@intel.com>, Akhil Goyal <gakhil@marvell.com>
Cc: dev@dpdk.org, declan.doherty@intel.com
Subject: [dpdk-dev] [PATCH 2/7] examples/ipsec-secgw: add support for NAT-T
Date: Fri, 3 Sep 2021 12:22:52 +0100 [thread overview]
Message-ID: <20210903112257.303961-3-radu.nicolau@intel.com> (raw)
In-Reply-To: <20210903112257.303961-1-radu.nicolau@intel.com>
Add support to the sample application to support IPsec NAT-T for both
transport and tunnel modes, for both IPv4 and IPv6.
Signed-off-by: Declan Doherty <declan.doherty@intel.com>
Signed-off-by: Radu Nicolau <radu.nicolau@intel.com>
---
examples/ipsec-secgw/esp.c | 7 +-
examples/ipsec-secgw/ipsec-secgw.c | 3 -
examples/ipsec-secgw/ipsec.c | 375 ++++++++++++-----------------
examples/ipsec-secgw/ipsec.h | 19 +-
examples/ipsec-secgw/sa.c | 240 +++++++++++++-----
examples/ipsec-secgw/sad.c | 10 +-
examples/ipsec-secgw/sad.h | 20 +-
7 files changed, 365 insertions(+), 309 deletions(-)
diff --git a/examples/ipsec-secgw/esp.c b/examples/ipsec-secgw/esp.c
index bfa7ff7217..3762d61597 100644
--- a/examples/ipsec-secgw/esp.c
+++ b/examples/ipsec-secgw/esp.c
@@ -265,9 +265,9 @@ esp_outbound(struct rte_mbuf *m, struct ipsec_sa *sa,
RTE_ASSERT(IS_TUNNEL(sa->flags) || IS_TRANSPORT(sa->flags));
- if (likely(IS_IP4_TUNNEL(sa->flags)))
+ if (likely((IS_TUNNEL(sa->flags) && IS_IP4(sa->flags))))
ip_hdr_len = sizeof(struct ip);
- else if (IS_IP6_TUNNEL(sa->flags))
+ else if ((IS_TUNNEL(sa->flags) && IS_IP6(sa->flags)))
ip_hdr_len = sizeof(struct ip6_hdr);
else if (!IS_TRANSPORT(sa->flags)) {
RTE_LOG(ERR, IPSEC_ESP, "Unsupported SA flags: 0x%x\n",
@@ -308,7 +308,8 @@ esp_outbound(struct rte_mbuf *m, struct ipsec_sa *sa,
&sa->src, &sa->dst);
esp = (struct rte_esp_hdr *)(ip6 + 1);
break;
- case TRANSPORT:
+ case IP4_TRANSPORT:
+ case IP6_TRANSPORT:
new_ip = (uint8_t *)rte_pktmbuf_prepend(m,
sizeof(struct rte_esp_hdr) + sa->iv_len);
memmove(new_ip, ip4, ip_hdr_len);
diff --git a/examples/ipsec-secgw/ipsec-secgw.c b/examples/ipsec-secgw/ipsec-secgw.c
index 6d516e2221..46fb49d91e 100644
--- a/examples/ipsec-secgw/ipsec-secgw.c
+++ b/examples/ipsec-secgw/ipsec-secgw.c
@@ -2299,9 +2299,6 @@ port_init(uint16_t portid, uint64_t req_rx_offloads, uint64_t req_tx_offloads)
/* Pre-populate pkt offloads based on capabilities */
qconf->outbound.ipv4_offloads = PKT_TX_IPV4;
qconf->outbound.ipv6_offloads = PKT_TX_IPV6;
- if (local_port_conf.txmode.offloads & DEV_TX_OFFLOAD_IPV4_CKSUM)
- qconf->outbound.ipv4_offloads |= PKT_TX_IP_CKSUM;
-
tx_queueid++;
/* init RX queues */
diff --git a/examples/ipsec-secgw/ipsec.c b/examples/ipsec-secgw/ipsec.c
index 5b032fecfb..aa68e4f827 100644
--- a/examples/ipsec-secgw/ipsec.c
+++ b/examples/ipsec-secgw/ipsec.c
@@ -24,7 +24,7 @@ set_ipsec_conf(struct ipsec_sa *sa, struct rte_security_ipsec_xform *ipsec)
if (ipsec->mode == RTE_SECURITY_IPSEC_SA_MODE_TUNNEL) {
struct rte_security_ipsec_tunnel_param *tunnel =
&ipsec->tunnel;
- if (IS_IP4_TUNNEL(sa->flags)) {
+ if (IS_TUNNEL(sa->flags) && IS_IP4(sa->flags)) {
tunnel->type =
RTE_SECURITY_IPSEC_TUNNEL_IPV4;
tunnel->ipv4.ttl = IPDEFTTL;
@@ -34,7 +34,7 @@ set_ipsec_conf(struct ipsec_sa *sa, struct rte_security_ipsec_xform *ipsec)
memcpy((uint8_t *)&tunnel->ipv4.dst_ip,
(uint8_t *)&sa->dst.ip.ip4, 4);
- } else if (IS_IP6_TUNNEL(sa->flags)) {
+ } else if (IS_TUNNEL(sa->flags) && IS_IP6(sa->flags)) {
tunnel->type =
RTE_SECURITY_IPSEC_TUNNEL_IPV6;
tunnel->ipv6.hlimit = IPDEFTTL;
@@ -163,262 +163,196 @@ create_inline_session(struct socket_ctx *skt_ctx, struct ipsec_sa *sa,
{
int32_t ret = 0;
struct rte_security_ctx *sec_ctx;
+ const struct rte_security_capability *sec_cap;
struct rte_security_session_conf sess_conf = {
.action_type = ips->type,
.protocol = RTE_SECURITY_PROTOCOL_IPSEC,
{.ipsec = {
- .spi = sa->spi,
+ .spi = htonl(sa->spi),
.salt = sa->salt,
.options = { 0 },
.replay_win_sz = 0,
.direction = sa->direction,
- .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP,
- .mode = (sa->flags == IP4_TUNNEL ||
- sa->flags == IP6_TUNNEL) ?
- RTE_SECURITY_IPSEC_SA_MODE_TUNNEL :
- RTE_SECURITY_IPSEC_SA_MODE_TRANSPORT,
+ .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP
} },
.crypto_xform = sa->xforms,
.userdata = NULL,
};
- RTE_LOG_DP(DEBUG, IPSEC, "Create session for SA spi %u on port %u\n",
- sa->spi, sa->portid);
+ if (IS_TRANSPORT(sa->flags)) {
+ sess_conf.ipsec.mode = RTE_SECURITY_IPSEC_SA_MODE_TRANSPORT;
+ /**
+ * TODO: address this in rte_security API
+ * Use tunnel parameters to pass both transport IP addresses
+ */
+ if (IS_IP4(sa->flags)) {
+ sess_conf.ipsec.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV4;
- if (ips->type == RTE_SECURITY_ACTION_TYPE_INLINE_CRYPTO) {
- struct rte_flow_error err;
- const struct rte_security_capability *sec_cap;
- int ret = 0;
-
- sec_ctx = (struct rte_security_ctx *)
- rte_eth_dev_get_sec_ctx(
- sa->portid);
- if (sec_ctx == NULL) {
- RTE_LOG(ERR, IPSEC,
- " rte_eth_dev_get_sec_ctx failed\n");
- return -1;
- }
+ sess_conf.ipsec.tunnel.ipv4.src_ip.s_addr =
+ sa->src.ip.ip4;
+ sess_conf.ipsec.tunnel.ipv4.dst_ip.s_addr =
+ sa->dst.ip.ip4;
+ } else if (IS_IP6(sa->flags)) {
+ sess_conf.ipsec.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV6;
- ips->security.ses = rte_security_session_create(sec_ctx,
- &sess_conf, skt_ctx->session_pool,
- skt_ctx->session_priv_pool);
- if (ips->security.ses == NULL) {
- RTE_LOG(ERR, IPSEC,
- "SEC Session init failed: err: %d\n", ret);
- return -1;
+ memcpy(sess_conf.ipsec.tunnel.ipv6.src_addr.s6_addr,
+ sa->src.ip.ip6.ip6_b, 16);
+ memcpy(sess_conf.ipsec.tunnel.ipv6.dst_addr.s6_addr,
+ sa->dst.ip.ip6.ip6_b, 16);
}
+ } else if (IS_TUNNEL(sa->flags)) {
+ sess_conf.ipsec.mode = RTE_SECURITY_IPSEC_SA_MODE_TUNNEL;
- sec_cap = rte_security_capabilities_get(sec_ctx);
-
- /* iterate until ESP tunnel*/
- while (sec_cap->action != RTE_SECURITY_ACTION_TYPE_NONE) {
- if (sec_cap->action == ips->type &&
- sec_cap->protocol ==
- RTE_SECURITY_PROTOCOL_IPSEC &&
- sec_cap->ipsec.mode ==
- RTE_SECURITY_IPSEC_SA_MODE_TUNNEL &&
- sec_cap->ipsec.direction == sa->direction)
- break;
- sec_cap++;
- }
+ if (IS_IP4(sa->flags)) {
+ sess_conf.ipsec.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV4;
- if (sec_cap->action == RTE_SECURITY_ACTION_TYPE_NONE) {
- RTE_LOG(ERR, IPSEC,
- "No suitable security capability found\n");
+ sess_conf.ipsec.tunnel.ipv4.src_ip.s_addr =
+ sa->src.ip.ip4;
+ sess_conf.ipsec.tunnel.ipv4.dst_ip.s_addr =
+ sa->dst.ip.ip4;
+ } else if (IS_IP6(sa->flags)) {
+ sess_conf.ipsec.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV6;
+
+ memcpy(sess_conf.ipsec.tunnel.ipv6.src_addr.s6_addr,
+ sa->src.ip.ip6.ip6_b, 16);
+ memcpy(sess_conf.ipsec.tunnel.ipv6.dst_addr.s6_addr,
+ sa->dst.ip.ip6.ip6_b, 16);
+ } else {
+ RTE_LOG(ERR, IPSEC, "invalid tunnel type\n");
return -1;
}
+ }
- ips->security.ol_flags = sec_cap->ol_flags;
- ips->security.ctx = sec_ctx;
- sa->pattern[0].type = RTE_FLOW_ITEM_TYPE_ETH;
+ if (IS_NATT_UDP_TUNNEL(sa->flags)) {
+ sess_conf.ipsec.options.udp_encap = 1;
- if (IS_IP6(sa->flags)) {
- sa->pattern[1].mask = &rte_flow_item_ipv6_mask;
- sa->pattern[1].type = RTE_FLOW_ITEM_TYPE_IPV6;
- sa->pattern[1].spec = &sa->ipv6_spec;
+ sess_conf.ipsec.udp.sport = htons(sa->udp.sport);
+ sess_conf.ipsec.udp.dport = htons(sa->udp.dport);
+ }
- memcpy(sa->ipv6_spec.hdr.dst_addr,
- sa->dst.ip.ip6.ip6_b, 16);
- memcpy(sa->ipv6_spec.hdr.src_addr,
- sa->src.ip.ip6.ip6_b, 16);
- } else if (IS_IP4(sa->flags)) {
- sa->pattern[1].mask = &rte_flow_item_ipv4_mask;
- sa->pattern[1].type = RTE_FLOW_ITEM_TYPE_IPV4;
- sa->pattern[1].spec = &sa->ipv4_spec;
-
- sa->ipv4_spec.hdr.dst_addr = sa->dst.ip.ip4;
- sa->ipv4_spec.hdr.src_addr = sa->src.ip.ip4;
- }
+ struct rte_flow_action_security action_security;
+ struct rte_flow_error err;
+
+ RTE_LOG_DP(DEBUG, IPSEC, "Create session for SA spi %u on port %u\n",
+ sa->spi, sa->portid);
+
+ sec_ctx = (struct rte_security_ctx *)
+ rte_eth_dev_get_sec_ctx(sa->portid);
+ if (sec_ctx == NULL) {
+ RTE_LOG(ERR, IPSEC,
+ " rte_eth_dev_get_sec_ctx failed\n");
+ return -1;
+ }
+
+ ips->security.ses = rte_security_session_create(sec_ctx,
+ &sess_conf, skt_ctx->session_pool,
+ skt_ctx->session_priv_pool);
+ if (ips->security.ses == NULL) {
+ RTE_LOG(ERR, IPSEC,
+ "SEC Session init failed: err: %d\n", ret);
+ return -1;
+ }
+
+ ips->security.ctx = sec_ctx;
+
+ sec_cap = rte_security_capabilities_get(sec_ctx);
+
+ ips->security.ol_flags = sec_cap->ol_flags;
+
+ if (sa->direction == RTE_SECURITY_IPSEC_SA_DIR_EGRESS)
+ return 0;
+
+ sa->pattern[0].type = RTE_FLOW_ITEM_TYPE_ETH;
+ sa->pattern[0].spec = NULL;
+
+ if (IS_IP6(sa->flags)) {
+ memcpy(sa->ipv6_spec.hdr.dst_addr,
+ sa->dst.ip.ip6.ip6_b, 16);
+ memcpy(sa->ipv6_spec.hdr.src_addr,
+ sa->src.ip.ip6.ip6_b, 16);
+
+ sa->pattern[1].mask = &rte_flow_item_ipv6_mask;
+ sa->pattern[1].type = RTE_FLOW_ITEM_TYPE_IPV6;
+ sa->pattern[1].spec = &sa->ipv6_spec;
+
+ } else if (IS_IP4(sa->flags)) {
+ sa->ipv4_spec.hdr.dst_addr = sa->dst.ip.ip4;
+ sa->ipv4_spec.hdr.src_addr = sa->src.ip.ip4;
+
+ sa->pattern[1].mask = &rte_flow_item_ipv4_mask;
+ sa->pattern[1].type = RTE_FLOW_ITEM_TYPE_IPV4;
+ sa->pattern[1].spec = &sa->ipv4_spec;
+ }
+
+ if (IS_NATT_UDP_TUNNEL(sa->flags)) {
+
+ sa->udp_spec.hdr.dst_port = rte_cpu_to_be_16(sa->udp.dport);
+ sa->udp_spec.hdr.src_port = rte_cpu_to_be_16(sa->udp.sport);
+
+ sa->pattern[2].mask = &rte_flow_item_udp_mask;
+ sa->pattern[2].type = RTE_FLOW_ITEM_TYPE_UDP;
+ sa->pattern[2].spec = &sa->udp_spec;
+
+ sa->esp_spec.hdr.spi = rte_cpu_to_be_32(sa->spi);
+
+ sa->pattern[3].type = RTE_FLOW_ITEM_TYPE_ESP;
+ sa->pattern[3].spec = &sa->esp_spec;
+ sa->pattern[3].mask = &rte_flow_item_esp_mask;
+
+ sa->pattern[4].type = RTE_FLOW_ITEM_TYPE_END;
+ } else {
+ sa->esp_spec.hdr.spi = rte_cpu_to_be_32(sa->spi);
sa->pattern[2].type = RTE_FLOW_ITEM_TYPE_ESP;
sa->pattern[2].spec = &sa->esp_spec;
sa->pattern[2].mask = &rte_flow_item_esp_mask;
- sa->esp_spec.hdr.spi = rte_cpu_to_be_32(sa->spi);
sa->pattern[3].type = RTE_FLOW_ITEM_TYPE_END;
+ }
- sa->action[0].type = RTE_FLOW_ACTION_TYPE_SECURITY;
- sa->action[0].conf = ips->security.ses;
-
- sa->action[1].type = RTE_FLOW_ACTION_TYPE_END;
-
- sa->attr.egress = (sa->direction ==
- RTE_SECURITY_IPSEC_SA_DIR_EGRESS);
- sa->attr.ingress = (sa->direction ==
- RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
- if (sa->attr.ingress) {
- uint8_t rss_key[40];
- struct rte_eth_rss_conf rss_conf = {
- .rss_key = rss_key,
- .rss_key_len = 40,
- };
- struct rte_eth_dev_info dev_info;
- uint16_t queue[RTE_MAX_QUEUES_PER_PORT];
- struct rte_flow_action_rss action_rss;
- unsigned int i;
- unsigned int j;
-
- /* Don't create flow if default flow is created */
- if (flow_info_tbl[sa->portid].rx_def_flow)
- return 0;
-
- ret = rte_eth_dev_info_get(sa->portid, &dev_info);
- if (ret != 0) {
- RTE_LOG(ERR, IPSEC,
- "Error during getting device (port %u) info: %s\n",
- sa->portid, strerror(-ret));
- return ret;
- }
-
- sa->action[2].type = RTE_FLOW_ACTION_TYPE_END;
- /* Try RSS. */
- sa->action[1].type = RTE_FLOW_ACTION_TYPE_RSS;
- sa->action[1].conf = &action_rss;
- ret = rte_eth_dev_rss_hash_conf_get(sa->portid,
- &rss_conf);
- if (ret != 0) {
- RTE_LOG(ERR, IPSEC,
- "rte_eth_dev_rss_hash_conf_get:ret=%d\n",
- ret);
- return -1;
- }
- for (i = 0, j = 0; i < dev_info.nb_rx_queues; ++i)
- queue[j++] = i;
-
- action_rss = (struct rte_flow_action_rss){
- .types = rss_conf.rss_hf,
- .key_len = rss_conf.rss_key_len,
- .queue_num = j,
- .key = rss_key,
- .queue = queue,
- };
- ret = rte_flow_validate(sa->portid, &sa->attr,
- sa->pattern, sa->action,
- &err);
- if (!ret)
- goto flow_create;
- /* Try Queue. */
- sa->action[1].type = RTE_FLOW_ACTION_TYPE_QUEUE;
- sa->action[1].conf =
- &(struct rte_flow_action_queue){
- .index = 0,
- };
- ret = rte_flow_validate(sa->portid, &sa->attr,
- sa->pattern, sa->action,
- &err);
- /* Try End. */
- sa->action[1].type = RTE_FLOW_ACTION_TYPE_END;
- sa->action[1].conf = NULL;
- ret = rte_flow_validate(sa->portid, &sa->attr,
- sa->pattern, sa->action,
- &err);
- if (ret)
- goto flow_create_failure;
- } else if (sa->attr.egress &&
- (ips->security.ol_flags &
- RTE_SECURITY_TX_HW_TRAILER_OFFLOAD)) {
- sa->action[1].type =
- RTE_FLOW_ACTION_TYPE_PASSTHRU;
- sa->action[2].type =
- RTE_FLOW_ACTION_TYPE_END;
- }
-flow_create:
- sa->flow = rte_flow_create(sa->portid,
- &sa->attr, sa->pattern, sa->action, &err);
- if (sa->flow == NULL) {
-flow_create_failure:
- RTE_LOG(ERR, IPSEC,
- "Failed to create ipsec flow msg: %s\n",
- err.message);
- return -1;
- }
- } else if (ips->type == RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL) {
- const struct rte_security_capability *sec_cap;
+ action_security.security_session = ips->security.ses;
- sec_ctx = (struct rte_security_ctx *)
- rte_eth_dev_get_sec_ctx(sa->portid);
+ sa->action[0].type = RTE_FLOW_ACTION_TYPE_SECURITY;
+ sa->action[0].conf = &action_security;
- if (sec_ctx == NULL) {
- RTE_LOG(ERR, IPSEC,
- "Ethernet device doesn't have security features registered\n");
- return -1;
- }
- /* Set IPsec parameters in conf */
- set_ipsec_conf(sa, &(sess_conf.ipsec));
-
- /* Save SA as userdata for the security session. When
- * the packet is received, this userdata will be
- * retrieved using the metadata from the packet.
- *
- * The PMD is expected to set similar metadata for other
- * operations, like rte_eth_event, which are tied to
- * security session. In such cases, the userdata could
- * be obtained to uniquely identify the security
- * parameters denoted.
- */
+ sa->action[1].type = RTE_FLOW_ACTION_TYPE_END;
+ sa->action[1].conf = NULL;
- sess_conf.userdata = (void *) sa;
+ sa->attr.egress = (sa->direction ==
+ RTE_SECURITY_IPSEC_SA_DIR_EGRESS);
- ips->security.ses = rte_security_session_create(sec_ctx,
- &sess_conf, skt_ctx->session_pool,
- skt_ctx->session_priv_pool);
- if (ips->security.ses == NULL) {
- RTE_LOG(ERR, IPSEC,
- "SEC Session init failed: err: %d\n", ret);
- return -1;
- }
+ if (sa->attr.egress)
+ return 0;
- sec_cap = rte_security_capabilities_get(sec_ctx);
- if (sec_cap == NULL) {
- RTE_LOG(ERR, IPSEC,
- "No capabilities registered\n");
- return -1;
- }
+ sa->attr.ingress = (sa->direction ==
+ RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
- /* iterate until ESP tunnel*/
- while (sec_cap->action !=
- RTE_SECURITY_ACTION_TYPE_NONE) {
- if (sec_cap->action == ips->type &&
- sec_cap->protocol ==
- RTE_SECURITY_PROTOCOL_IPSEC &&
- sec_cap->ipsec.mode ==
- sess_conf.ipsec.mode &&
- sec_cap->ipsec.direction == sa->direction)
- break;
- sec_cap++;
- }
- if (sec_cap->action == RTE_SECURITY_ACTION_TYPE_NONE) {
- RTE_LOG(ERR, IPSEC,
- "No suitable security capability found\n");
- return -1;
- }
+ ret = rte_flow_validate(sa->portid,
+ &sa->attr,
+ sa->pattern,
+ sa->action,
+ &err);
+ if (ret)
+ goto flow_create_failure;
- ips->security.ol_flags = sec_cap->ol_flags;
- ips->security.ctx = sec_ctx;
+ sa->flow = rte_flow_create(sa->portid, &sa->attr, sa->pattern,
+ sa->action, &err);
+ if (sa->flow == NULL) {
+flow_create_failure:
+ RTE_LOG(ERR, IPSEC,
+ "Failed to create ipsec flow msg: %s\n",
+ err.message);
+ return -1;
}
+ sa->cdev_id_qp = 0;
+
return 0;
}
@@ -427,23 +361,28 @@ create_ipsec_esp_flow(struct ipsec_sa *sa)
{
int ret = 0;
struct rte_flow_error err;
+
if (sa->direction == RTE_SECURITY_IPSEC_SA_DIR_EGRESS) {
RTE_LOG(ERR, IPSEC,
"No Flow director rule for Egress traffic\n");
return -1;
}
- if (sa->flags == TRANSPORT) {
+
+ if (IS_TRANSPORT(sa->flags)) {
RTE_LOG(ERR, IPSEC,
"No Flow director rule for transport mode\n");
return -1;
}
+
sa->action[0].type = RTE_FLOW_ACTION_TYPE_QUEUE;
sa->pattern[0].type = RTE_FLOW_ITEM_TYPE_ETH;
sa->action[0].conf = &(struct rte_flow_action_queue) {
.index = sa->fdir_qid,
};
+
sa->attr.egress = 0;
sa->attr.ingress = 1;
+
if (IS_IP6(sa->flags)) {
sa->pattern[1].mask = &rte_flow_item_ipv6_mask;
sa->pattern[1].type = RTE_FLOW_ITEM_TYPE_IPV6;
diff --git a/examples/ipsec-secgw/ipsec.h b/examples/ipsec-secgw/ipsec.h
index ae5058de27..b496b4a936 100644
--- a/examples/ipsec-secgw/ipsec.h
+++ b/examples/ipsec-secgw/ipsec.h
@@ -122,11 +122,15 @@ struct ipsec_sa {
uint16_t flags;
#define IP4_TUNNEL (1 << 0)
#define IP6_TUNNEL (1 << 1)
-#define TRANSPORT (1 << 2)
+#define NATT_UDP_TUNNEL (1 << 2)
#define IP4_TRANSPORT (1 << 3)
#define IP6_TRANSPORT (1 << 4)
struct ip_addr src;
struct ip_addr dst;
+ struct {
+ uint16_t sport;
+ uint16_t dport;
+ } udp;
uint8_t cipher_key[MAX_KEY_SIZE];
uint16_t cipher_key_len;
uint8_t auth_key[MAX_KEY_SIZE];
@@ -142,7 +146,7 @@ struct ipsec_sa {
uint8_t fdir_qid;
uint8_t fdir_flag;
-#define MAX_RTE_FLOW_PATTERN (4)
+#define MAX_RTE_FLOW_PATTERN (5)
#define MAX_RTE_FLOW_ACTIONS (3)
struct rte_flow_item pattern[MAX_RTE_FLOW_PATTERN];
struct rte_flow_action action[MAX_RTE_FLOW_ACTIONS];
@@ -151,6 +155,7 @@ struct ipsec_sa {
struct rte_flow_item_ipv4 ipv4_spec;
struct rte_flow_item_ipv6 ipv6_spec;
};
+ struct rte_flow_item_udp udp_spec;
struct rte_flow_item_esp esp_spec;
struct rte_flow *flow;
struct rte_security_session_conf sess_conf;
@@ -181,18 +186,16 @@ struct ipsec_mbuf_metadata {
uint8_t buf[32];
} __rte_cache_aligned;
-#define IS_TRANSPORT(flags) ((flags) & TRANSPORT)
+#define IS_TRANSPORT(flags) ((flags) & (IP4_TRANSPORT | IP6_TRANSPORT))
#define IS_TUNNEL(flags) ((flags) & (IP4_TUNNEL | IP6_TUNNEL))
+#define IS_NATT_UDP_TUNNEL(flags) ((flags) & NATT_UDP_TUNNEL)
+
#define IS_IP4(flags) ((flags) & (IP4_TUNNEL | IP4_TRANSPORT))
#define IS_IP6(flags) ((flags) & (IP6_TUNNEL | IP6_TRANSPORT))
-#define IS_IP4_TUNNEL(flags) ((flags) & IP4_TUNNEL)
-
-#define IS_IP6_TUNNEL(flags) ((flags) & IP6_TUNNEL)
-
/*
* Macro for getting ipsec_sa flags statuses without version of protocol
* used for transport (IP4_TRANSPORT and IP6_TRANSPORT flags).
@@ -200,7 +203,7 @@ struct ipsec_mbuf_metadata {
#define WITHOUT_TRANSPORT_VERSION(flags) \
((flags) & (IP4_TUNNEL | \
IP6_TUNNEL | \
- TRANSPORT))
+ (IP4_TRANSPORT | IP6_TRANSPORT)))
struct cdev_qp {
uint16_t id;
diff --git a/examples/ipsec-secgw/sa.c b/examples/ipsec-secgw/sa.c
index 17a28556c9..d5943f8cdc 100644
--- a/examples/ipsec-secgw/sa.c
+++ b/examples/ipsec-secgw/sa.c
@@ -17,6 +17,7 @@
#include <rte_byteorder.h>
#include <rte_errno.h>
#include <rte_ip.h>
+#include <rte_udp.h>
#include <rte_random.h>
#include <rte_ethdev.h>
#include <rte_malloc.h>
@@ -339,13 +340,28 @@ parse_sa_tokens(char **tokens, uint32_t n_tokens,
if (strcmp(tokens[ti], "ipv4-tunnel") == 0) {
sa_cnt->nb_v4++;
rule->flags = IP4_TUNNEL;
+ } else if (strcmp(tokens[ti], "ipv4-udp-tunnel") == 0) {
+ sa_cnt->nb_v4++;
+ rule->flags = IP4_TUNNEL | NATT_UDP_TUNNEL;
+ rule->udp.sport = 0;
+ rule->udp.dport = 4500;
} else if (strcmp(tokens[ti], "ipv6-tunnel") == 0) {
sa_cnt->nb_v6++;
rule->flags = IP6_TUNNEL;
+ } else if (strcmp(tokens[ti], "ipv6-udp-tunnel") == 0) {
+ sa_cnt->nb_v6++;
+ rule->flags = IP6_TUNNEL | NATT_UDP_TUNNEL;
} else if (strcmp(tokens[ti], "transport") == 0) {
sa_cnt->nb_v4++;
sa_cnt->nb_v6++;
- rule->flags = TRANSPORT;
+ rule->flags = IP4_TRANSPORT | IP6_TRANSPORT;
+ } else if (strcmp(tokens[ti], "udp-transport") == 0) {
+ sa_cnt->nb_v4++;
+ sa_cnt->nb_v6++;
+ rule->flags = IP4_TRANSPORT | IP6_TRANSPORT |
+ NATT_UDP_TUNNEL;
+ rule->udp.sport = 0;
+ rule->udp.dport = 4500;
} else {
APP_CHECK(0, status, "unrecognized "
"input \"%s\"", tokens[ti]);
@@ -548,7 +564,7 @@ parse_sa_tokens(char **tokens, uint32_t n_tokens,
if (status->status < 0)
return;
- if (IS_IP4_TUNNEL(rule->flags)) {
+ if (IS_IP4(rule->flags) && IS_TUNNEL(rule->flags)) {
struct in_addr ip;
APP_CHECK(parse_ipv4_addr(tokens[ti],
@@ -560,7 +576,8 @@ parse_sa_tokens(char **tokens, uint32_t n_tokens,
return;
rule->src.ip.ip4 = rte_bswap32(
(uint32_t)ip.s_addr);
- } else if (IS_IP6_TUNNEL(rule->flags)) {
+ } else if (IS_IP6(rule->flags) &&
+ IS_TUNNEL(rule->flags)) {
struct in6_addr ip;
APP_CHECK(parse_ipv6_addr(tokens[ti], &ip,
@@ -591,7 +608,7 @@ parse_sa_tokens(char **tokens, uint32_t n_tokens,
if (status->status < 0)
return;
- if (IS_IP4_TUNNEL(rule->flags)) {
+ if (IS_IP4(rule->flags) && IS_TUNNEL(rule->flags)) {
struct in_addr ip;
APP_CHECK(parse_ipv4_addr(tokens[ti],
@@ -603,7 +620,8 @@ parse_sa_tokens(char **tokens, uint32_t n_tokens,
return;
rule->dst.ip.ip4 = rte_bswap32(
(uint32_t)ip.s_addr);
- } else if (IS_IP6_TUNNEL(rule->flags)) {
+ } else if (IS_IP6(rule->flags) &&
+ IS_TUNNEL(rule->flags)) {
struct in6_addr ip;
APP_CHECK(parse_ipv6_addr(tokens[ti], &ip,
@@ -832,19 +850,19 @@ print_one_sa_rule(const struct ipsec_sa *sa, int inbound)
const struct rte_ipsec_session *ips;
const struct rte_ipsec_session *fallback_ips;
- printf("\tspi_%s(%3u):", inbound?"in":"out", sa->spi);
+ printf("\tspi_%s (%3u):", inbound?"in":"out", sa->spi);
for (i = 0; i < RTE_DIM(cipher_algos); i++) {
if (cipher_algos[i].algo == sa->cipher_algo &&
cipher_algos[i].key_len == sa->cipher_key_len) {
- printf("%s ", cipher_algos[i].keyword);
+ printf(" %s", cipher_algos[i].keyword);
break;
}
}
for (i = 0; i < RTE_DIM(auth_algos); i++) {
if (auth_algos[i].algo == sa->auth_algo) {
- printf("%s ", auth_algos[i].keyword);
+ printf(" %s", auth_algos[i].keyword);
break;
}
}
@@ -852,23 +870,29 @@ print_one_sa_rule(const struct ipsec_sa *sa, int inbound)
for (i = 0; i < RTE_DIM(aead_algos); i++) {
if (aead_algos[i].algo == sa->aead_algo &&
aead_algos[i].key_len-4 == sa->cipher_key_len) {
- printf("%s ", aead_algos[i].keyword);
+ printf(" %s ", aead_algos[i].keyword);
break;
}
}
- printf("mode:");
+ printf(", mode:");
+
+ if (IS_IP4(sa->flags) && IS_TUNNEL(sa->flags)) {
- switch (WITHOUT_TRANSPORT_VERSION(sa->flags)) {
- case IP4_TUNNEL:
- printf("IP4Tunnel ");
+ if (IS_NATT_UDP_TUNNEL(sa->flags))
+ printf("IP4Tunnel NAT-T (");
+ else
+ printf("IP4Tunnel (");
uint32_t_to_char(sa->src.ip.ip4, &a, &b, &c, &d);
printf("%hhu.%hhu.%hhu.%hhu ", d, c, b, a);
uint32_t_to_char(sa->dst.ip.ip4, &a, &b, &c, &d);
printf("%hhu.%hhu.%hhu.%hhu", d, c, b, a);
- break;
- case IP6_TUNNEL:
- printf("IP6Tunnel ");
+ } else if (IS_IP6(sa->flags) && IS_TUNNEL(sa->flags)) {
+
+ if (IS_NATT_UDP_TUNNEL(sa->flags))
+ printf("IP6Tunnel NAT-T (");
+ else
+ printf("IP6Tunnel (");
for (i = 0; i < 16; i++) {
if (i % 2 && i != 15)
printf("%.2x:", sa->src.ip.ip6.ip6_b[i]);
@@ -882,14 +906,15 @@ print_one_sa_rule(const struct ipsec_sa *sa, int inbound)
else
printf("%.2x", sa->dst.ip.ip6.ip6_b[i]);
}
- break;
- case TRANSPORT:
- printf("Transport ");
- break;
+ } else if (IS_TRANSPORT(sa->flags)) {
+ if (IS_NATT_UDP_TUNNEL(sa->flags))
+ printf("Transport NAT-T (");
+ else
+ printf("Transport (");
}
ips = &sa->sessions[IPSEC_SESSION_PRIMARY];
- printf(" type:");
+ printf("), type: ");
switch (ips->type) {
case RTE_SECURITY_ACTION_TYPE_NONE:
printf("no-offload ");
@@ -1053,7 +1078,11 @@ sa_add_address_inline_crypto(struct ipsec_sa *sa)
protocol = get_spi_proto(sa->spi, sa->direction, ip_addr, mask);
if (protocol < 0)
return protocol;
- else if (protocol == IPPROTO_IPIP) {
+
+ /* Clear transport bits before selecting IP4/IP6 */
+ sa->flags &= ~(IP4_TRANSPORT | IP6_TRANSPORT);
+
+ if (protocol == IPPROTO_IPIP) {
sa->flags |= IP4_TRANSPORT;
if (mask[0] == IP4_FULL_MASK &&
mask[1] == IP4_FULL_MASK &&
@@ -1131,12 +1160,7 @@ sa_add_rules(struct sa_ctx *sa_ctx, const struct ipsec_sa entries[],
return -EINVAL;
}
- switch (WITHOUT_TRANSPORT_VERSION(sa->flags)) {
- case IP4_TUNNEL:
- sa->src.ip.ip4 = rte_cpu_to_be_32(sa->src.ip.ip4);
- sa->dst.ip.ip4 = rte_cpu_to_be_32(sa->dst.ip.ip4);
- break;
- case TRANSPORT:
+ if (IS_TRANSPORT(sa->flags)) {
if (ips->type ==
RTE_SECURITY_ACTION_TYPE_INLINE_CRYPTO) {
inline_status =
@@ -1144,11 +1168,25 @@ sa_add_rules(struct sa_ctx *sa_ctx, const struct ipsec_sa entries[],
if (inline_status < 0)
return inline_status;
}
- break;
+ } else if (IS_TUNNEL(sa->flags)) {
+ if (IS_IP4(sa->flags)) {
+ sa->src.ip.ip4 =
+ rte_cpu_to_be_32(sa->src.ip.ip4);
+ sa->dst.ip.ip4 =
+ rte_cpu_to_be_32(sa->dst.ip.ip4);
+ }
+
}
- if (sa->aead_algo == RTE_CRYPTO_AEAD_AES_GCM) {
- iv_length = 12;
+
+ if (sa->aead_algo == RTE_CRYPTO_AEAD_AES_GCM ||
+ sa->aead_algo == RTE_CRYPTO_AEAD_AES_CCM ||
+ sa->aead_algo == RTE_CRYPTO_AEAD_CHACHA20_POLY1305) {
+
+ if (ips->type == RTE_SECURITY_ACTION_TYPE_INLINE_CRYPTO)
+ iv_length = 8;
+ else
+ iv_length = 12;
sa_ctx->xf[idx].a.type = RTE_CRYPTO_SYM_XFORM_AEAD;
sa_ctx->xf[idx].a.aead.algo = sa->aead_algo;
@@ -1285,9 +1323,21 @@ fill_ipsec_app_sa_prm(struct rte_ipsec_sa_prm *prm,
prm->ipsec_xform.replay_win_sz = app_prm->window_size;
}
+struct udp_ipv4_tunnel {
+ struct rte_ipv4_hdr v4;
+ struct rte_udp_hdr udp;
+} __rte_packed;
+
+struct udp_ipv6_tunnel {
+ struct rte_ipv6_hdr v6;
+ struct rte_udp_hdr udp;
+} __rte_packed;
+
static int
fill_ipsec_sa_prm(struct rte_ipsec_sa_prm *prm, const struct ipsec_sa *ss,
- const struct rte_ipv4_hdr *v4, struct rte_ipv6_hdr *v6)
+ const struct rte_ipv4_hdr *v4, struct rte_ipv6_hdr *v6,
+ const struct udp_ipv4_tunnel *udp_ipv4,
+ const struct udp_ipv6_tunnel *udp_ipv6)
{
int32_t rc;
@@ -1311,22 +1361,49 @@ fill_ipsec_sa_prm(struct rte_ipsec_sa_prm *prm, const struct ipsec_sa *ss,
prm->ipsec_xform.mode = (IS_TRANSPORT(ss->flags)) ?
RTE_SECURITY_IPSEC_SA_MODE_TRANSPORT :
RTE_SECURITY_IPSEC_SA_MODE_TUNNEL;
+ prm->ipsec_xform.options.udp_encap =
+ (IS_NATT_UDP_TUNNEL(ss->flags)) ? 1 : 0;
prm->ipsec_xform.options.ecn = 1;
prm->ipsec_xform.options.copy_dscp = 1;
- if (IS_IP4_TUNNEL(ss->flags)) {
- prm->ipsec_xform.tunnel.type = RTE_SECURITY_IPSEC_TUNNEL_IPV4;
- prm->tun.hdr_len = sizeof(*v4);
- prm->tun.next_proto = rc;
- prm->tun.hdr = v4;
- } else if (IS_IP6_TUNNEL(ss->flags)) {
- prm->ipsec_xform.tunnel.type = RTE_SECURITY_IPSEC_TUNNEL_IPV6;
- prm->tun.hdr_len = sizeof(*v6);
- prm->tun.next_proto = rc;
- prm->tun.hdr = v6;
- } else {
+ if (IS_TRANSPORT(ss->flags)) {
/* transport mode */
prm->trs.proto = rc;
+ } else if (IS_TUNNEL(ss->flags)) {
+ prm->tun.hdr_l3_off = 0;
+
+ /* tunnel mode */
+ if (IS_IP4(ss->flags)) {
+ prm->ipsec_xform.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV4;
+ prm->tun.next_proto = rc;
+ prm->tun.hdr_l3_len = sizeof(*v4);
+
+ if (IS_NATT_UDP_TUNNEL(ss->flags)) {
+ prm->tun.hdr_len = sizeof(*udp_ipv4);
+ prm->tun.hdr = udp_ipv4;
+
+ } else {
+ prm->tun.hdr_len = sizeof(*v4);
+ prm->tun.hdr = v4;
+ }
+
+ } else if (IS_IP6(ss->flags)) {
+ prm->ipsec_xform.tunnel.type =
+ RTE_SECURITY_IPSEC_TUNNEL_IPV6;
+ prm->tun.next_proto = rc;
+ prm->tun.hdr_l3_len = sizeof(*v6);
+
+ if (IS_NATT_UDP_TUNNEL(ss->flags)) {
+
+ prm->tun.hdr_len = sizeof(*udp_ipv6);
+ prm->tun.hdr = udp_ipv6;
+
+ } else {
+ prm->tun.hdr_len = sizeof(*v6);
+ prm->tun.hdr = v6;
+ }
+ }
}
/* setup crypto section */
@@ -1362,25 +1439,66 @@ ipsec_sa_init(struct ipsec_sa *lsa, struct rte_ipsec_sa *sa, uint32_t sa_size)
int rc;
struct rte_ipsec_sa_prm prm;
struct rte_ipsec_session *ips;
- struct rte_ipv4_hdr v4 = {
- .version_ihl = IPVERSION << 4 |
- sizeof(v4) / RTE_IPV4_IHL_MULTIPLIER,
- .time_to_live = IPDEFTTL,
- .next_proto_id = IPPROTO_ESP,
- .src_addr = lsa->src.ip.ip4,
- .dst_addr = lsa->dst.ip.ip4,
- };
- struct rte_ipv6_hdr v6 = {
- .vtc_flow = htonl(IP6_VERSION << 28),
- .proto = IPPROTO_ESP,
- };
-
- if (IS_IP6_TUNNEL(lsa->flags)) {
- memcpy(v6.src_addr, lsa->src.ip.ip6.ip6_b, sizeof(v6.src_addr));
- memcpy(v6.dst_addr, lsa->dst.ip.ip6.ip6_b, sizeof(v6.dst_addr));
+ struct rte_ipv4_hdr v4;
+ struct rte_ipv6_hdr v6;
+ struct udp_ipv4_tunnel udp_ipv4;
+ struct udp_ipv6_tunnel udp_ipv6;
+
+
+ if (IS_TUNNEL(lsa->flags) && IS_NATT_UDP_TUNNEL(lsa->flags)) {
+ if (IS_IP4(lsa->flags)) {
+
+ udp_ipv4.v4.version_ihl = IPVERSION << 4 | sizeof(v4) /
+ RTE_IPV4_IHL_MULTIPLIER;
+ udp_ipv4.v4.time_to_live = IPDEFTTL;
+ udp_ipv4.v4.next_proto_id = IPPROTO_UDP;
+ udp_ipv4.v4.src_addr = lsa->src.ip.ip4;
+ udp_ipv4.v4.dst_addr = lsa->dst.ip.ip4;
+
+ udp_ipv4.udp.src_port =
+ rte_cpu_to_be_16(lsa->udp.sport);
+ udp_ipv4.udp.dst_port =
+ rte_cpu_to_be_16(lsa->udp.dport);
+
+ } else if (IS_IP6(lsa->flags)) {
+
+ udp_ipv6.v6.vtc_flow = htonl(IP6_VERSION << 28),
+ udp_ipv6.v6.proto = IPPROTO_UDP,
+ memcpy(udp_ipv6.v6.src_addr, lsa->src.ip.ip6.ip6_b,
+ sizeof(udp_ipv6.v6.src_addr));
+ memcpy(udp_ipv6.v6.dst_addr, lsa->dst.ip.ip6.ip6_b,
+ sizeof(udp_ipv6.v6.dst_addr));
+
+ udp_ipv6.udp.src_port =
+ rte_cpu_to_be_16(lsa->udp.sport);
+ udp_ipv6.udp.dst_port =
+ rte_cpu_to_be_16(lsa->udp.dport);
+ }
+
+ } else if (IS_TUNNEL(lsa->flags)) {
+
+ if (IS_IP4(lsa->flags)) {
+ v4.version_ihl = IPVERSION << 4 | sizeof(v4) /
+ RTE_IPV4_IHL_MULTIPLIER;
+ v4.time_to_live = IPDEFTTL;
+ v4.next_proto_id = IPPROTO_ESP;
+ v4.src_addr = lsa->src.ip.ip4;
+ v4.dst_addr = lsa->dst.ip.ip4;
+
+ } else if (IS_IP6(lsa->flags)) {
+
+ v6.vtc_flow = htonl(IP6_VERSION << 28),
+ v6.proto = IPPROTO_ESP,
+ memcpy(v6.src_addr, lsa->src.ip.ip6.ip6_b,
+ sizeof(v6.src_addr));
+ memcpy(v6.dst_addr, lsa->dst.ip.ip6.ip6_b,
+ sizeof(v6.dst_addr));
+
+ }
+
}
- rc = fill_ipsec_sa_prm(&prm, lsa, &v4, &v6);
+ rc = fill_ipsec_sa_prm(&prm, lsa, &v4, &v6, &udp_ipv4, &udp_ipv6);
if (rc == 0)
rc = rte_ipsec_sa_init(sa, &prm, sa_size);
if (rc < 0)
@@ -1415,7 +1533,7 @@ ipsec_satbl_init(struct sa_ctx *ctx, uint32_t nb_ent, int32_t socket)
/* determine SA size */
idx = 0;
- fill_ipsec_sa_prm(&prm, ctx->sa + idx, NULL, NULL);
+ fill_ipsec_sa_prm(&prm, ctx->sa + idx, NULL, NULL, NULL, NULL);
sz = rte_ipsec_sa_size(&prm);
if (sz < 0) {
RTE_LOG(ERR, IPSEC, "%s(%p, %u, %d): "
diff --git a/examples/ipsec-secgw/sad.c b/examples/ipsec-secgw/sad.c
index 5b2c0e6792..191fc79faf 100644
--- a/examples/ipsec-secgw/sad.c
+++ b/examples/ipsec-secgw/sad.c
@@ -25,8 +25,8 @@ ipsec_sad_add(struct ipsec_sad *sad, struct ipsec_sa *sa)
/* spi field is common for ipv4 and ipv6 key types */
key.v4.spi = rte_cpu_to_be_32(sa->spi);
lookup_key[0] = &key;
- switch (WITHOUT_TRANSPORT_VERSION(sa->flags)) {
- case IP4_TUNNEL:
+
+ if (IS_IP4(sa->flags) && IS_TUNNEL(sa->flags)) {
rte_ipsec_sad_lookup(sad->sad_v4, lookup_key, &tmp, 1);
if (tmp != NULL)
return -EEXIST;
@@ -35,8 +35,7 @@ ipsec_sad_add(struct ipsec_sad *sad, struct ipsec_sa *sa)
RTE_IPSEC_SAD_SPI_ONLY, sa);
if (ret != 0)
return ret;
- break;
- case IP6_TUNNEL:
+ } else if (IS_IP6(sa->flags) && IS_TUNNEL(sa->flags)) {
rte_ipsec_sad_lookup(sad->sad_v6, lookup_key, &tmp, 1);
if (tmp != NULL)
return -EEXIST;
@@ -45,8 +44,7 @@ ipsec_sad_add(struct ipsec_sad *sad, struct ipsec_sa *sa)
RTE_IPSEC_SAD_SPI_ONLY, sa);
if (ret != 0)
return ret;
- break;
- case TRANSPORT:
+ } else if (IS_TRANSPORT(sa->flags)) {
if (sp4_spi_present(sa->spi, 1, NULL, NULL) >= 0) {
rte_ipsec_sad_lookup(sad->sad_v4, lookup_key, &tmp, 1);
if (tmp != NULL)
diff --git a/examples/ipsec-secgw/sad.h b/examples/ipsec-secgw/sad.h
index 3224b6252c..6813a47942 100644
--- a/examples/ipsec-secgw/sad.h
+++ b/examples/ipsec-secgw/sad.h
@@ -29,16 +29,16 @@ static inline int
cmp_sa_key(struct ipsec_sa *sa, int is_v4, struct rte_ipv4_hdr *ipv4,
struct rte_ipv6_hdr *ipv6)
{
- int sa_type = WITHOUT_TRANSPORT_VERSION(sa->flags);
- if ((sa_type == TRANSPORT) ||
- /* IPv4 check */
- (is_v4 && (sa_type == IP4_TUNNEL) &&
- (sa->src.ip.ip4 == ipv4->src_addr) &&
- (sa->dst.ip.ip4 == ipv4->dst_addr)) ||
- /* IPv6 check */
- (!is_v4 && (sa_type == IP6_TUNNEL) &&
- (!memcmp(sa->src.ip.ip6.ip6, ipv6->src_addr, 16)) &&
- (!memcmp(sa->dst.ip.ip6.ip6, ipv6->dst_addr, 16))))
+
+ if (IS_TRANSPORT(sa->flags) ||
+ /* IPv4 check */
+ (is_v4 && IS_IP4(sa->flags) &&
+ (sa->src.ip.ip4 == ipv4->src_addr) &&
+ (sa->dst.ip.ip4 == ipv4->dst_addr)) ||
+ /* IPv6 check */
+ (!is_v4 && IS_IP6(sa->flags) &&
+ (!memcmp(sa->src.ip.ip6.ip6, ipv6->src_addr, 16)) &&
+ (!memcmp(sa->dst.ip.ip6.ip6, ipv6->dst_addr, 16))))
return 1;
return 0;
--
2.25.1
next prev parent reply other threads:[~2021-09-03 11:29 UTC|newest]
Thread overview: 82+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-09-03 11:22 [dpdk-dev] [PATCH 0/7] IPsec Sec GW new features Radu Nicolau
2021-09-03 11:22 ` [dpdk-dev] [PATCH 1/7] examples/ipsec-secgw: add ol_flags support Radu Nicolau
2021-09-08 12:48 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-09 8:57 ` Nicolau, Radu
2021-09-03 11:22 ` Radu Nicolau [this message]
2021-09-08 10:36 ` [dpdk-dev] [EXT] [PATCH 2/7] examples/ipsec-secgw: add support for NAT-T Akhil Goyal
2021-09-03 11:22 ` [dpdk-dev] [PATCH 3/7] examples/ipsec-secgw: add support for TSO Radu Nicolau
2021-09-08 12:54 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-03 11:22 ` [dpdk-dev] [PATCH 4/7] examples/ipsec-secgw: enable stats by default Radu Nicolau
2021-09-03 12:50 ` Zhang, Roy Fan
2021-09-08 13:08 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-08 16:05 ` Hemant Agrawal
2021-09-03 11:22 ` [dpdk-dev] [PATCH 5/7] examples/ipsec-secgw: add support for telemetry Radu Nicolau
2021-09-08 14:09 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-03 11:22 ` [dpdk-dev] [PATCH 6/7] examples/ipsec-secgw: add support for defining initial sequence number value Radu Nicolau
2021-09-08 14:11 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-03 11:22 ` [dpdk-dev] [PATCH 7/7] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-09-08 14:24 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 0/9] IPsec Sec GW new features Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 1/9] examples/ipsec-secgw: update create inline session Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 2/9] examples/ipsec-secgw: update SA parameters with L3 options Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 3/9] examples/ipsec-secgw: add support for telemetry Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 4/9] examples/ipsec-secgw: add stats interval argument Radu Nicolau
2021-09-16 9:13 ` Hemant Agrawal
2021-09-16 9:30 ` [dpdk-dev] [EXT] " Anoob Joseph
2021-09-16 10:24 ` Nicolau, Radu
2021-09-17 12:51 ` Anoob Joseph
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 5/9] examples/ipsec-secgw: add support for TSO Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 6/9] examples/ipsec-secgw: add support for defining initial sequence number value Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 7/9] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 8/9] examples/ipsec-secgw: add support for additional algorithms Radu Nicolau
2021-09-15 13:45 ` [dpdk-dev] [PATCH v2 9/9] examples/ipsec-secgw: add support for inline crypto UDP encapsulation Radu Nicolau
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 0/8] IPsec Sec GW new features Radu Nicolau
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 1/8] examples/ipsec-secgw: add stats interval argument Radu Nicolau
2021-10-08 18:37 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 2/8] examples/ipsec-secgw: update create inline session Radu Nicolau
2021-10-08 18:38 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 3/8] examples/ipsec-secgw: add support for inline crypto UDP encapsulation Radu Nicolau
2021-10-08 18:42 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 4/8] examples/ipsec-secgw: add support for TSO Radu Nicolau
2021-10-08 18:46 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:51 ` [dpdk-dev] [PATCH v3 5/8] examples/ipsec-secgw: add support for telemetry Radu Nicolau
2021-10-08 18:51 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:52 ` [dpdk-dev] [PATCH v3 6/8] examples/ipsec-secgw: add support for defining initial sequence number value Radu Nicolau
2021-10-08 18:57 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-01 9:52 ` [dpdk-dev] [PATCH v3 7/8] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-10-01 9:52 ` [dpdk-dev] [PATCH v3 8/8] examples/ipsec-secgw: add support for additional algorithms Radu Nicolau
2021-10-08 19:07 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-11 15:40 ` Nicolau, Radu
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 0/7] IPsec Sec GW new features Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 1/7] examples/ipsec-secgw: add stats interval argument Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 2/7] examples/ipsec-secgw: update create inline session Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 3/7] examples/ipsec-secgw: add support for inline crypto UDP encapsulation Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 4/7] examples/ipsec-secgw: support telemetry Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 5/7] examples/ipsec-secgw: define initial ESN value Radu Nicolau
2021-10-18 10:28 ` [dpdk-dev] [PATCH v4 6/7] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-10-18 10:29 ` [dpdk-dev] [PATCH v4 7/7] examples/ipsec-secgw: add support for additional algorithms Radu Nicolau
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 0/7] IPsec Sec GW new features Radu Nicolau
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 1/7] examples/ipsec-secgw: add stats interval argument Radu Nicolau
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 2/7] examples/ipsec-secgw: update create inline session Radu Nicolau
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 3/7] examples/ipsec-secgw: add support for inline crypto UDP encapsulation Radu Nicolau
2021-10-31 20:03 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 4/7] examples/ipsec-secgw: support telemetry Radu Nicolau
2021-10-31 20:22 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 5/7] examples/ipsec-secgw: define initial ESN value Radu Nicolau
2021-10-31 20:23 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 6/7] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-10-31 20:25 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-10-27 11:45 ` [dpdk-dev] [PATCH v5 7/7] examples/ipsec-secgw: add support for additional algorithms Radu Nicolau
2021-10-31 20:29 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 0/7] IPsec Sec GW new features Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 1/7] examples/ipsec-secgw: add stats interval argument Radu Nicolau
2021-11-03 9:23 ` [dpdk-dev] [EXT] " Akhil Goyal
2021-11-03 10:51 ` Nicolau, Radu
2021-11-03 13:20 ` Akhil Goyal
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 2/7] examples/ipsec-secgw: update create inline session Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 3/7] examples/ipsec-secgw: add support for inline crypto UDP encapsulation Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 4/7] examples/ipsec-secgw: support telemetry Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 5/7] examples/ipsec-secgw: define initial ESN value Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 6/7] examples/ipsec-secgw: add ethdev reset callback Radu Nicolau
2021-11-01 12:58 ` [dpdk-dev] [PATCH v6 7/7] examples/ipsec-secgw: add support for additional algorithms Radu Nicolau
2021-11-03 14:13 ` [dpdk-dev] [EXT] [PATCH v6 0/7] IPsec Sec GW new features Akhil Goyal
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20210903112257.303961-3-radu.nicolau@intel.com \
--to=radu.nicolau@intel.com \
--cc=declan.doherty@intel.com \
--cc=dev@dpdk.org \
--cc=gakhil@marvell.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).