* [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing
@ 2017-08-09 15:33 David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 1/3] iproute: add helper functions for SRH processing David Lebrun
` (3 more replies)
0 siblings, 4 replies; 5+ messages in thread
From: David Lebrun @ 2017-08-09 15:33 UTC (permalink / raw)
To: netdev; +Cc: David Lebrun
This patch series adds support and documentation for the seg6local
lightweight tunnel, enabling to perform operations to SR-enabled packets
based on their active segment.
v2: use a table for action names
Signed-off-by: David Lebrun <david.lebrun@uclouvain.be>
David Lebrun (3):
iproute: add helper functions for SRH processing
iproute: add support for SRv6 local segment processing
man: add documentation for seg6local lwt
ip/iproute.c | 2 +-
ip/iproute_lwtunnel.c | 324 +++++++++++++++++++++++++++++++++++++++++--------
man/man8/ip-route.8.in | 62 +++++++++-
3 files changed, 338 insertions(+), 50 deletions(-)
--
2.10.2
^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH iproute2 net-next v2 1/3] iproute: add helper functions for SRH processing
2017-08-09 15:33 [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing David Lebrun
@ 2017-08-09 15:33 ` David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 2/3] iproute: add support for SRv6 local segment processing David Lebrun
` (2 subsequent siblings)
3 siblings, 0 replies; 5+ messages in thread
From: David Lebrun @ 2017-08-09 15:33 UTC (permalink / raw)
To: netdev; +Cc: David Lebrun
This patch adds two helper functions to print and parse
Segment Routing Headers.
Signed-off-by: David Lebrun <david.lebrun@uclouvain.be>
---
ip/iproute_lwtunnel.c | 124 +++++++++++++++++++++++++++++---------------------
1 file changed, 72 insertions(+), 52 deletions(-)
diff --git a/ip/iproute_lwtunnel.c b/ip/iproute_lwtunnel.c
index 5c0c7d1..16d2584 100644
--- a/ip/iproute_lwtunnel.c
+++ b/ip/iproute_lwtunnel.c
@@ -83,24 +83,10 @@ static int read_encap_type(const char *name)
return LWTUNNEL_ENCAP_NONE;
}
-static void print_encap_seg6(FILE *fp, struct rtattr *encap)
+static void print_srh(FILE *fp, struct ipv6_sr_hdr *srh)
{
- struct rtattr *tb[SEG6_IPTUNNEL_MAX+1];
- struct seg6_iptunnel_encap *tuninfo;
- struct ipv6_sr_hdr *srh;
int i;
- parse_rtattr_nested(tb, SEG6_IPTUNNEL_MAX, encap);
-
- if (!tb[SEG6_IPTUNNEL_SRH])
- return;
-
- tuninfo = RTA_DATA(tb[SEG6_IPTUNNEL_SRH]);
- fprintf(fp, "mode %s ",
- (tuninfo->mode == SEG6_IPTUN_MODE_ENCAP) ? "encap" : "inline");
-
- srh = tuninfo->srh;
-
fprintf(fp, "segs %d [ ", srh->first_segment + 1);
for (i = srh->first_segment; i >= 0; i--)
@@ -118,6 +104,23 @@ static void print_encap_seg6(FILE *fp, struct rtattr *encap)
}
}
+static void print_encap_seg6(FILE *fp, struct rtattr *encap)
+{
+ struct rtattr *tb[SEG6_IPTUNNEL_MAX+1];
+ struct seg6_iptunnel_encap *tuninfo;
+
+ parse_rtattr_nested(tb, SEG6_IPTUNNEL_MAX, encap);
+
+ if (!tb[SEG6_IPTUNNEL_SRH])
+ return;
+
+ tuninfo = RTA_DATA(tb[SEG6_IPTUNNEL_SRH]);
+ fprintf(fp, "mode %s ",
+ (tuninfo->mode == SEG6_IPTUN_MODE_ENCAP) ? "encap" : "inline");
+
+ print_srh(fp, tuninfo->srh);
+}
+
static void print_encap_mpls(FILE *fp, struct rtattr *encap)
{
struct rtattr *tb[MPLS_IPTUNNEL_MAX+1];
@@ -290,6 +293,55 @@ void lwt_print_encap(FILE *fp, struct rtattr *encap_type,
}
}
+static struct ipv6_sr_hdr *parse_srh(char *segbuf, int hmac, bool encap)
+{
+ struct ipv6_sr_hdr *srh;
+ int nsegs = 0;
+ int srhlen;
+ char *s;
+ int i;
+
+ s = segbuf;
+ for (i = 0; *s; *s++ == ',' ? i++ : *s);
+ nsegs = i + 1;
+
+ if (!encap)
+ nsegs++;
+
+ srhlen = 8 + 16*nsegs;
+
+ if (hmac)
+ srhlen += 40;
+
+ srh = malloc(srhlen);
+ memset(srh, 0, srhlen);
+
+ srh->hdrlen = (srhlen >> 3) - 1;
+ srh->type = 4;
+ srh->segments_left = nsegs - 1;
+ srh->first_segment = nsegs - 1;
+
+ if (hmac)
+ srh->flags |= SR6_FLAG1_HMAC;
+
+ i = srh->first_segment;
+ for (s = strtok(segbuf, ","); s; s = strtok(NULL, ",")) {
+ inet_get_addr(s, NULL, &srh->segments[i]);
+ i--;
+ }
+
+ if (hmac) {
+ struct sr6_tlv_hmac *tlv;
+
+ tlv = (struct sr6_tlv_hmac *)((char *)srh + srhlen - 40);
+ tlv->tlvhdr.type = SR6_TLV_HMAC;
+ tlv->tlvhdr.len = 38;
+ tlv->hmackeyid = htonl(hmac);
+ }
+
+ return srh;
+}
+
static int parse_encap_seg6(struct rtattr *rta, size_t len, int *argcp,
char ***argvp)
{
@@ -301,10 +353,7 @@ static int parse_encap_seg6(struct rtattr *rta, size_t len, int *argcp,
int argc = *argcp;
int encap = -1;
__u32 hmac = 0;
- int nsegs = 0;
int srhlen;
- char *s;
- int i;
while (argc > 0) {
if (strcmp(*argv, "mode") == 0) {
@@ -338,17 +387,8 @@ static int parse_encap_seg6(struct rtattr *rta, size_t len, int *argcp,
argc--; argv++;
}
- s = segbuf;
- for (i = 0; *s; *s++ == ',' ? i++ : *s);
- nsegs = i + 1;
-
- if (!encap)
- nsegs++;
-
- srhlen = 8 + 16*nsegs;
-
- if (hmac)
- srhlen += 40;
+ srh = parse_srh(segbuf, hmac, encap);
+ srhlen = (srh->hdrlen + 1) << 3;
tuninfo = malloc(sizeof(*tuninfo) + srhlen);
memset(tuninfo, 0, sizeof(*tuninfo) + srhlen);
@@ -358,33 +398,13 @@ static int parse_encap_seg6(struct rtattr *rta, size_t len, int *argcp,
else
tuninfo->mode = SEG6_IPTUN_MODE_INLINE;
- srh = tuninfo->srh;
- srh->hdrlen = (srhlen >> 3) - 1;
- srh->type = 4;
- srh->segments_left = nsegs - 1;
- srh->first_segment = nsegs - 1;
-
- if (hmac)
- srh->flags |= SR6_FLAG1_HMAC;
-
- i = srh->first_segment;
- for (s = strtok(segbuf, ","); s; s = strtok(NULL, ",")) {
- inet_get_addr(s, NULL, &srh->segments[i]);
- i--;
- }
-
- if (hmac) {
- struct sr6_tlv_hmac *tlv;
-
- tlv = (struct sr6_tlv_hmac *)((char *)srh + srhlen - 40);
- tlv->tlvhdr.type = SR6_TLV_HMAC;
- tlv->tlvhdr.len = 38;
- tlv->hmackeyid = htonl(hmac);
- }
+ memcpy(tuninfo->srh, srh, srhlen);
rta_addattr_l(rta, len, SEG6_IPTUNNEL_SRH, tuninfo,
sizeof(*tuninfo) + srhlen);
+
free(tuninfo);
+ free(srh);
*argcp = argc + 1;
*argvp = argv - 1;
--
2.10.2
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH iproute2 net-next v2 2/3] iproute: add support for SRv6 local segment processing
2017-08-09 15:33 [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 1/3] iproute: add helper functions for SRH processing David Lebrun
@ 2017-08-09 15:33 ` David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 3/3] man: add documentation for seg6local lwt David Lebrun
2017-08-15 23:45 ` [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing Stephen Hemminger
3 siblings, 0 replies; 5+ messages in thread
From: David Lebrun @ 2017-08-09 15:33 UTC (permalink / raw)
To: netdev; +Cc: David Lebrun
This patch adds support for the seg6local lightweight tunnel
("ip route add ... encap seg6local ...").
Signed-off-by: David Lebrun <david.lebrun@uclouvain.be>
---
ip/iproute.c | 2 +-
ip/iproute_lwtunnel.c | 208 ++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 209 insertions(+), 1 deletion(-)
diff --git a/ip/iproute.c b/ip/iproute.c
index cb695ad..7a37df5 100644
--- a/ip/iproute.c
+++ b/ip/iproute.c
@@ -100,7 +100,7 @@ static void usage(void)
fprintf(stderr, "TIME := NUMBER[s|ms]\n");
fprintf(stderr, "BOOL := [1|0]\n");
fprintf(stderr, "FEATURES := ecn\n");
- fprintf(stderr, "ENCAPTYPE := [ mpls | ip | ip6 | seg6 ]\n");
+ fprintf(stderr, "ENCAPTYPE := [ mpls | ip | ip6 | seg6 | seg6local ]\n");
fprintf(stderr, "ENCAPHDR := [ MPLSLABEL | SEG6HDR ]\n");
fprintf(stderr, "SEG6HDR := [ mode SEGMODE ] segs ADDR1,ADDRi,ADDRn [hmac HMACKEYID] [cleanup]\n");
fprintf(stderr, "SEGMODE := [ encap | inline ]\n");
diff --git a/ip/iproute_lwtunnel.c b/ip/iproute_lwtunnel.c
index 16d2584..7dde4b2 100644
--- a/ip/iproute_lwtunnel.c
+++ b/ip/iproute_lwtunnel.c
@@ -29,6 +29,8 @@
#include <linux/seg6.h>
#include <linux/seg6_iptunnel.h>
#include <linux/seg6_hmac.h>
+#include <linux/seg6_local.h>
+#include <net/if.h>
static const char *format_encap_type(int type)
{
@@ -45,6 +47,8 @@ static const char *format_encap_type(int type)
return "bpf";
case LWTUNNEL_ENCAP_SEG6:
return "seg6";
+ case LWTUNNEL_ENCAP_SEG6_LOCAL:
+ return "seg6local";
default:
return "unknown";
}
@@ -77,6 +81,8 @@ static int read_encap_type(const char *name)
return LWTUNNEL_ENCAP_BPF;
else if (strcmp(name, "seg6") == 0)
return LWTUNNEL_ENCAP_SEG6;
+ else if (strcmp(name, "seg6local") == 0)
+ return LWTUNNEL_ENCAP_SEG6_LOCAL;
else if (strcmp(name, "help") == 0)
encap_type_usage();
@@ -121,6 +127,94 @@ static void print_encap_seg6(FILE *fp, struct rtattr *encap)
print_srh(fp, tuninfo->srh);
}
+static const char *seg6_action_names[SEG6_LOCAL_ACTION_MAX + 1] = {
+ [SEG6_LOCAL_ACTION_END] = "End",
+ [SEG6_LOCAL_ACTION_END_X] = "End.X",
+ [SEG6_LOCAL_ACTION_END_T] = "End.T",
+ [SEG6_LOCAL_ACTION_END_DX2] = "End.DX2",
+ [SEG6_LOCAL_ACTION_END_DX6] = "End.DX6",
+ [SEG6_LOCAL_ACTION_END_DX4] = "End.DX4",
+ [SEG6_LOCAL_ACTION_END_DT6] = "End.DT6",
+ [SEG6_LOCAL_ACTION_END_DT4] = "End.DT4",
+ [SEG6_LOCAL_ACTION_END_B6] = "End.B6",
+ [SEG6_LOCAL_ACTION_END_B6_ENCAP] = "End.B6.Encaps",
+ [SEG6_LOCAL_ACTION_END_BM] = "End.BM",
+ [SEG6_LOCAL_ACTION_END_S] = "End.S",
+ [SEG6_LOCAL_ACTION_END_AS] = "End.AS",
+ [SEG6_LOCAL_ACTION_END_AM] = "End.AM",
+};
+
+static const char *format_action_type(int action)
+{
+ if (action < 0 || action > SEG6_LOCAL_ACTION_MAX)
+ return "<invalid>";
+
+ return seg6_action_names[action] ?: "<unknown>";
+}
+
+static int read_action_type(const char *name)
+{
+ int i;
+
+ for (i = 0; i < SEG6_LOCAL_ACTION_MAX + 1; i++) {
+ if (!seg6_action_names[i])
+ continue;
+
+ if (strcmp(seg6_action_names[i], name) == 0)
+ return i;
+ }
+
+ return SEG6_LOCAL_ACTION_UNSPEC;
+}
+
+static void print_encap_seg6local(FILE *fp, struct rtattr *encap)
+{
+ struct rtattr *tb[SEG6_LOCAL_MAX + 1];
+ char ifbuf[IFNAMSIZ];
+ int action;
+
+ parse_rtattr_nested(tb, SEG6_LOCAL_MAX, encap);
+
+ if (!tb[SEG6_LOCAL_ACTION])
+ return;
+
+ action = rta_getattr_u32(tb[SEG6_LOCAL_ACTION]);
+
+ fprintf(fp, "action %s ", format_action_type(action));
+
+ if (tb[SEG6_LOCAL_SRH]) {
+ fprintf(fp, "srh ");
+ print_srh(fp, RTA_DATA(tb[SEG6_LOCAL_SRH]));
+ }
+
+ if (tb[SEG6_LOCAL_TABLE])
+ fprintf(fp, "table %u ", rta_getattr_u32(tb[SEG6_LOCAL_TABLE]));
+
+ if (tb[SEG6_LOCAL_NH4]) {
+ fprintf(fp, "nh4 %s ",
+ rt_addr_n2a_rta(AF_INET, tb[SEG6_LOCAL_NH4]));
+ }
+
+ if (tb[SEG6_LOCAL_NH6]) {
+ fprintf(fp, "nh6 %s ",
+ rt_addr_n2a_rta(AF_INET6, tb[SEG6_LOCAL_NH6]));
+ }
+
+ if (tb[SEG6_LOCAL_IIF]) {
+ int iif = rta_getattr_u32(tb[SEG6_LOCAL_IIF]);
+
+ fprintf(fp, "iif %s ",
+ if_indextoname(iif, ifbuf) ?: "<unknown>");
+ }
+
+ if (tb[SEG6_LOCAL_OIF]) {
+ int oif = rta_getattr_u32(tb[SEG6_LOCAL_OIF]);
+
+ fprintf(fp, "oif %s ",
+ if_indextoname(oif, ifbuf) ?: "<unknown>");
+ }
+}
+
static void print_encap_mpls(FILE *fp, struct rtattr *encap)
{
struct rtattr *tb[MPLS_IPTUNNEL_MAX+1];
@@ -290,6 +384,9 @@ void lwt_print_encap(FILE *fp, struct rtattr *encap_type,
case LWTUNNEL_ENCAP_SEG6:
print_encap_seg6(fp, encap);
break;
+ case LWTUNNEL_ENCAP_SEG6_LOCAL:
+ print_encap_seg6local(fp, encap);
+ break;
}
}
@@ -412,6 +509,114 @@ static int parse_encap_seg6(struct rtattr *rta, size_t len, int *argcp,
return 0;
}
+static int parse_encap_seg6local(struct rtattr *rta, size_t len, int *argcp,
+ char ***argvp)
+{
+ int segs_ok = 0, hmac_ok = 0, table_ok = 0, nh4_ok = 0, nh6_ok = 0;
+ int iif_ok = 0, oif_ok = 0, action_ok = 0, srh_ok = 0;
+ __u32 action = 0, table, iif, oif;
+ struct ipv6_sr_hdr *srh;
+ char **argv = *argvp;
+ int argc = *argcp;
+ char segbuf[1024];
+ inet_prefix addr;
+ __u32 hmac = 0;
+
+ while (argc > 0) {
+ if (strcmp(*argv, "action") == 0) {
+ NEXT_ARG();
+ if (action_ok++)
+ duparg2("action", *argv);
+ action = read_action_type(*argv);
+ if (!action)
+ invarg("\"action\" value is invalid\n", *argv);
+ rta_addattr32(rta, len, SEG6_LOCAL_ACTION, action);
+ } else if (strcmp(*argv, "table") == 0) {
+ NEXT_ARG();
+ if (table_ok++)
+ duparg2("table", *argv);
+ get_u32(&table, *argv, 0);
+ rta_addattr32(rta, len, SEG6_LOCAL_TABLE, table);
+ } else if (strcmp(*argv, "nh4") == 0) {
+ NEXT_ARG();
+ if (nh4_ok++)
+ duparg2("nh4", *argv);
+ get_addr(&addr, *argv, AF_INET);
+ rta_addattr_l(rta, len, SEG6_LOCAL_NH4, &addr.data,
+ addr.bytelen);
+ } else if (strcmp(*argv, "nh6") == 0) {
+ NEXT_ARG();
+ if (nh6_ok++)
+ duparg2("nh6", *argv);
+ get_addr(&addr, *argv, AF_INET6);
+ rta_addattr_l(rta, len, SEG6_LOCAL_NH6, &addr.data,
+ addr.bytelen);
+ } else if (strcmp(*argv, "iif") == 0) {
+ NEXT_ARG();
+ if (iif_ok++)
+ duparg2("iif", *argv);
+ iif = if_nametoindex(*argv);
+ if (!iif)
+ invarg("\"iif\" interface not found\n", *argv);
+ rta_addattr32(rta, len, SEG6_LOCAL_IIF, iif);
+ } else if (strcmp(*argv, "oif") == 0) {
+ NEXT_ARG();
+ if (oif_ok++)
+ duparg2("oif", *argv);
+ oif = if_nametoindex(*argv);
+ if (!oif)
+ invarg("\"oif\" interface not found\n", *argv);
+ rta_addattr32(rta, len, SEG6_LOCAL_OIF, oif);
+ } else if (strcmp(*argv, "srh") == 0) {
+ NEXT_ARG();
+ if (srh_ok++)
+ duparg2("srh", *argv);
+ if (strcmp(*argv, "segs") != 0)
+ invarg("missing \"segs\" attribute for srh\n",
+ *argv);
+ NEXT_ARG();
+ if (segs_ok++)
+ duparg2("segs", *argv);
+ strncpy(segbuf, *argv, 1024);
+ segbuf[1023] = 0;
+ if (!NEXT_ARG_OK())
+ break;
+ NEXT_ARG();
+ if (strcmp(*argv, "hmac") == 0) {
+ NEXT_ARG();
+ if (hmac_ok++)
+ duparg2("hmac", *argv);
+ get_u32(&hmac, *argv, 0);
+ } else {
+ continue;
+ }
+ } else {
+ break;
+ }
+ argc--; argv++;
+ }
+
+ if (!action) {
+ fprintf(stderr, "Missing action type\n");
+ exit(-1);
+ }
+
+ if (srh_ok) {
+ int srhlen;
+
+ srh = parse_srh(segbuf, hmac,
+ action == SEG6_LOCAL_ACTION_END_B6_ENCAP);
+ srhlen = (srh->hdrlen + 1) << 3;
+ rta_addattr_l(rta, len, SEG6_LOCAL_SRH, srh, srhlen);
+ free(srh);
+ }
+
+ *argcp = argc + 1;
+ *argvp = argv - 1;
+
+ return 0;
+}
+
static int parse_encap_mpls(struct rtattr *rta, size_t len,
int *argcp, char ***argvp)
{
@@ -771,6 +976,9 @@ int lwt_parse_encap(struct rtattr *rta, size_t len, int *argcp, char ***argvp)
case LWTUNNEL_ENCAP_SEG6:
parse_encap_seg6(rta, len, &argc, &argv);
break;
+ case LWTUNNEL_ENCAP_SEG6_LOCAL:
+ parse_encap_seg6local(rta, len, &argc, &argv);
+ break;
default:
fprintf(stderr, "Error: unsupported encap type\n");
break;
--
2.10.2
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH iproute2 net-next v2 3/3] man: add documentation for seg6local lwt
2017-08-09 15:33 [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 1/3] iproute: add helper functions for SRH processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 2/3] iproute: add support for SRv6 local segment processing David Lebrun
@ 2017-08-09 15:33 ` David Lebrun
2017-08-15 23:45 ` [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing Stephen Hemminger
3 siblings, 0 replies; 5+ messages in thread
From: David Lebrun @ 2017-08-09 15:33 UTC (permalink / raw)
To: netdev; +Cc: David Lebrun
This patch adds documentation in the ip-route man page
about the seg6local lightweight tunnel.
Signed-off-by: David Lebrun <david.lebrun@uclouvain.be>
---
man/man8/ip-route.8.in | 62 +++++++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 61 insertions(+), 1 deletion(-)
diff --git a/man/man8/ip-route.8.in b/man/man8/ip-route.8.in
index fc28492..11dd9d0 100644
--- a/man/man8/ip-route.8.in
+++ b/man/man8/ip-route.8.in
@@ -177,7 +177,7 @@ throw " | " unreachable " | " prohibit " | " blackhole " | " nat " ]"
.ti -8
.IR ENCAP " := [ "
-.IR MPLS " | " IP " | " BPF " | " SEG6 " ] "
+.IR MPLS " | " IP " | " BPF " | " SEG6 " | " SEG6LOCAL " ] "
.ti -8
.IR ENCAP_MPLS " := "
@@ -221,6 +221,13 @@ throw " | " unreachable " | " prohibit " | " blackhole " | " nat " ]"
.IR KEYID " ]"
.ti -8
+.IR ENCAP_SEG6LOCAL " := "
+.B seg6local
+.BR action
+.IR SEG6_ACTION " [ "
+.IR SEG6_ACTION_PARAM " ] "
+
+.ti -8
.IR ROUTE_GET_FLAGS " := "
.BR " [ "
.BR fibmatch
@@ -674,6 +681,9 @@ is a string specifying the supported encapsulation type. Namely:
.sp
.BI seg6
- encapsulation type IPv6 Segment Routing
+.sp
+.BI seg6local
+- local SRv6 segment processing
.in -8
.I ENCAPHDR
@@ -749,6 +759,56 @@ is a set of encapsulation attributes specific to the
.in -2
.sp
+.B seg6local
+.in +2
+.IR SEG6_ACTION " [ "
+.IR SEG6_ACTION_PARAM " ] "
+- Operation to perform on matching packets.
+The following actions are currently supported (\fB4.14+ only\fR).
+.in +2
+
+.B End
+- Regular SRv6 processing as intermediate segment endpoint.
+This action only accepts packets with a non-zero Segments Left
+value. Other matching packets are dropped.
+
+.B End.X nh6
+.I NEXTHOP
+- Regular SRv6 processing as intermediate segment endpoint.
+Additionally, forward processed packets to given next-hop.
+This action only accepts packets with a non-zero Segments Left
+value. Other matching packets are dropped.
+
+.B End.DX6 nh6
+.I NEXTHOP
+- Decapsulate inner IPv6 packet and forward it to the
+specified next-hop. If the argument is set to ::, then
+the next-hop is selected according to the local selection
+rules. This action only accepts packets with either a zero Segments
+Left value or no SRH at all, and an inner IPv6 packet. Other
+matching packets are dropped.
+
+.B End.B6 srh segs
+.IR SEGMENTS " [ "
+.B hmac
+.IR KEYID " ] "
+- Insert the specified SRH immediately after the IPv6 header,
+update the DA with the first segment of the newly inserted SRH,
+then forward the resulting packet. The original SRH is not
+modified. This action only accepts packets with a non-zero
+Segments Left value. Other matching packets are dropped.
+
+.B End.B6.Encaps srh segs
+.IR SEGMENTS " [ "
+.B hmac
+.IR KEYID " ] "
+- Regular SRv6 processing as intermediate segment endpoint.
+Additionally, encapsulate the matching packet within an outer IPv6 header
+followed by the specified SRH. The destination address of the outer IPv6
+header is set to the first segment of the new SRH. The source
+address is set as described in \fBip-sr\fR(8).
+.in -4
+
.in -8
.TP
--
2.10.2
^ permalink raw reply related [flat|nested] 5+ messages in thread
* Re: [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing
2017-08-09 15:33 [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing David Lebrun
` (2 preceding siblings ...)
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 3/3] man: add documentation for seg6local lwt David Lebrun
@ 2017-08-15 23:45 ` Stephen Hemminger
3 siblings, 0 replies; 5+ messages in thread
From: Stephen Hemminger @ 2017-08-15 23:45 UTC (permalink / raw)
To: David Lebrun; +Cc: netdev
On Wed, 9 Aug 2017 17:33:23 +0200
David Lebrun <david.lebrun@uclouvain.be> wrote:
> This patch series adds support and documentation for the seg6local
> lightweight tunnel, enabling to perform operations to SR-enabled packets
> based on their active segment.
>
> v2: use a table for action names
>
> Signed-off-by: David Lebrun <david.lebrun@uclouvain.be>
>
> David Lebrun (3):
> iproute: add helper functions for SRH processing
> iproute: add support for SRv6 local segment processing
> man: add documentation for seg6local lwt
>
> ip/iproute.c | 2 +-
> ip/iproute_lwtunnel.c | 324 +++++++++++++++++++++++++++++++++++++++++--------
> man/man8/ip-route.8.in | 62 +++++++++-
> 3 files changed, 338 insertions(+), 50 deletions(-)
>
Applied to net-next branch.
Thanks David.
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2017-08-15 23:45 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2017-08-09 15:33 [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 1/3] iproute: add helper functions for SRH processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 2/3] iproute: add support for SRv6 local segment processing David Lebrun
2017-08-09 15:33 ` [PATCH iproute2 net-next v2 3/3] man: add documentation for seg6local lwt David Lebrun
2017-08-15 23:45 ` [PATCH iproute2 net-next v2 0/3] Add support for SRv6 local segment processing Stephen Hemminger
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.