diff options
author | Mikael Magnusson <mikma@users.sourceforge.net> | 2018-09-04 18:32:42 +0000 |
---|---|---|
committer | Mikael Magnusson <mikma@users.sourceforge.net> | 2023-08-24 02:25:38 +0200 |
commit | 1bcfbb67cfc5aa81048b4da3e2400d54ea4a0640 (patch) | |
tree | a7683890e995a0bf2883a0b5697e09f8ef28fc18 | |
parent | 4a21bf851d2ac6e70d366ca3c39054d93f37f233 (diff) |
BGP: Tunnel Encapsulation attribute
Refer to RFC 9012, The BGP Tunnel Encapsulation Attribute.
-rw-r--r-- | proto/bgp/attrs.c | 43 | ||||
-rw-r--r-- | proto/bgp/bgp.h | 1 | ||||
-rw-r--r-- | proto/bgp/config.Y | 4 |
3 files changed, 47 insertions, 1 deletions
diff --git a/proto/bgp/attrs.c b/proto/bgp/attrs.c index de45cae0..0ca40581 100644 --- a/proto/bgp/attrs.c +++ b/proto/bgp/attrs.c @@ -21,6 +21,7 @@ #include "lib/resource.h" #include "lib/string.h" #include "lib/unaligned.h" +#include "lib/tunnel_encaps.h" #include "bgp.h" @@ -916,6 +917,39 @@ bgp_decode_otc(struct bgp_parse_state *s, uint code UNUSED, uint flags, byte *da static void +bgp_export_tunnel_encap(struct bgp_export_state *s UNUSED, eattr *a) +{ + if (a->u.ptr->length == 0) + UNSET(a); + + /* + * TODO: In situations where a tunnel could be encoded using a barebones TLV, + * it MUST be encoded using the corresponding Encapsulation Extended + * Community. (RFC9012 section 4.1) + */ +} + +static void +bgp_decode_tunnel_encap(struct bgp_parse_state *s, uint code UNUSED, uint flags, byte *data, uint len, ea_list **to) +{ + bgp_set_attr_data(to, s->pool, BA_TUNNEL_ENCAP, flags, data, len); +} + +static int +bgp_encode_tunnel_encap(struct bgp_write_state *s UNUSED, eattr *a, byte *buf, uint size) +{ + return bgp_put_attr(buf, size, EA_ID(a->id), a->flags, a->u.ptr->data, a->u.ptr->length); +} + +static void +bgp_format_tunnel_encap(const eattr *a, byte *buf, uint size) +{ + int l = format_tunnel_encap(a->u.ptr, buf, size); + if (l > 0) + ADVANCE(buf, size, l); +} + +static void bgp_export_mpls_label_stack(struct bgp_export_state *s, eattr *a) { net_addr *n = s->route->net->n.addr; @@ -1135,6 +1169,15 @@ static const struct bgp_attr_desc bgp_attr_table[] = { .encode = bgp_encode_u32, .decode = bgp_decode_otc, }, + [BA_TUNNEL_ENCAP] = { + .name = "tunnel_encap", + .type = EAF_TYPE_TUNNEL_ENCAP, + .flags = BAF_OPTIONAL | BAF_TRANSITIVE, + .export = bgp_export_tunnel_encap, + .encode = bgp_encode_tunnel_encap, + .decode = bgp_decode_tunnel_encap, + .format = bgp_format_tunnel_encap, + }, [BA_MPLS_LABEL_STACK] = { .name = "mpls_label_stack", .type = EAF_TYPE_INT_SET, diff --git a/proto/bgp/bgp.h b/proto/bgp/bgp.h index c11433ec..178ff827 100644 --- a/proto/bgp/bgp.h +++ b/proto/bgp/bgp.h @@ -702,6 +702,7 @@ byte *bgp_create_end_mark_(struct bgp_channel *c, byte *buf); #define BA_EXT_COMMUNITY 0x10 /* RFC 4360 */ #define BA_AS4_PATH 0x11 /* RFC 6793 */ #define BA_AS4_AGGREGATOR 0x12 /* RFC 6793 */ +#define BA_TUNNEL_ENCAP 0x17 /* RFC 9012 */ #define BA_AIGP 0x1a /* RFC 7311 */ #define BA_LARGE_COMMUNITY 0x20 /* RFC 8092 */ #define BA_ONLY_TO_CUSTOMER 0x23 /* RFC 9234 */ diff --git a/proto/bgp/config.Y b/proto/bgp/config.Y index 218e0d04..b59534e4 100644 --- a/proto/bgp/config.Y +++ b/proto/bgp/config.Y @@ -32,7 +32,7 @@ CF_KEYWORDS(BGP, LOCAL, NEIGHBOR, AS, HOLD, TIME, CONNECT, RETRY, KEEPALIVE, LIVED, STALE, IMPORT, IBGP, EBGP, MANDATORY, INTERNAL, EXTERNAL, SETS, DYNAMIC, RANGE, NAME, DIGITS, BGP_AIGP, AIGP, ORIGINATE, COST, ENFORCE, FIRST, FREE, VALIDATE, BASE, ROLE, ROLES, PEER, PROVIDER, CUSTOMER, - RS_SERVER, RS_CLIENT, REQUIRE, BGP_OTC, GLOBAL) + RS_SERVER, RS_CLIENT, REQUIRE, BGP_OTC, GLOBAL, BGP_TUNNEL_ENCAP) %type <i> bgp_nh %type <i32> bgp_afi @@ -364,6 +364,8 @@ dynamic_attr: BGP_LARGE_COMMUNITY { $$ = f_new_dynamic_attr(EAF_TYPE_LC_SET, T_LCLIST, EA_CODE(PROTOCOL_BGP, BA_LARGE_COMMUNITY)); } ; dynamic_attr: BGP_OTC { $$ = f_new_dynamic_attr(EAF_TYPE_INT, T_INT, EA_CODE(PROTOCOL_BGP, BA_ONLY_TO_CUSTOMER)); } ; +dynamic_attr: BGP_TUNNEL_ENCAP + { $$ = f_new_dynamic_attr(EAF_TYPE_TUNNEL_ENCAP, T_TLVLIST, EA_CODE(PROTOCOL_BGP, BA_TUNNEL_ENCAP)); } ; |