]> git.puffer.fish Git - matthieu/frr.git/commitdiff
bgpd: Add missing bgp well-known communities
authorChristoffer <netravnen@gmail.com>
Thu, 19 Jul 2018 11:29:11 +0000 (13:29 +0200)
committerChristoffer <netravnen@gmail.com>
Sun, 29 Jul 2018 14:54:16 +0000 (16:54 +0200)
Updated the list with listed well-known communities from document IANA's https://www.iana.org/assignments/bgp-well-known-communities/bgp-well-known-communities.txt with last update date as of 2018-03-07.

- GRACEFUL_SHUTDOWN moved to 2nd entry in all lists in touched code.
- Added ACCEPT_OWN - [RFC7611]
- Added ROUTE_FILTER_TRANSLATED_v4 - currently [draft-l3vpn-legacy-rtc]
- Added ROUTE_FILTER_v4 - currently [draft-l3vpn-legacy-rtc]
- Added ROUTE_FILTER_TRANSLATED_v6 - currently [draft-l3vpn-legacy-rtc]
- Added ROUTE_FILTER_v6 - currently [draft-l3vpn-legacy-rtc]
- Added LLGR_STALE - currently [draft-uttaro-idr-bgp-persistence]
- Added NO_LLGR - currently [draft-uttaro-idr-bgp-persistence]
- Added accept-own-nexthop - currently [draft-agrewal-idr-accept-own-nexthop]
- Added BLACKHOLE - [RFC7999]
- Added NOPEER - [RFC3765]

bgpd/bgp_clist.c
bgpd/bgp_community.c
bgpd/bgp_community.h

index b2f34dd968b8851bfda67cc986fdcd4076732085..1aa40fec3c24563bc6b2dca0ecd4a12c95102346 100644 (file)
@@ -346,6 +346,36 @@ static char *community_str_get(struct community *com, int i)
        case COMMUNITY_INTERNET:
                len = strlen(" internet");
                break;
+       case COMMUNITY_GSHUT:
+               len = strlen(" graceful-shutdown");
+               break;
+       case COMMUNITY_ACCEPT_OWN:
+               len = strlen(" accept-own");
+               break;
+       case COMMUNITY_ROUTE_FILTER_TRANSLATED_v4:
+               len = strlen(" route-filter-translated-v4");
+               break;
+       case COMMUNITY_ROUTE_FILTER_v4:
+               len = strlen(" route-filter-v4");
+               break;
+       case COMMUNITY_ROUTE_FILTER_TRANSLATED_v6:
+               len = strlen(" route-filter-translated-v6");
+               break;
+       case COMMUNITY_ROUTE_FILTER_v6:
+               len = strlen(" route-filter-v6");
+               break;
+       case COMMUNITY_LLGR_STALE:
+               len = strlen(" llgr-stale");
+               break;
+       case COMMUNITY_NO_LLGR:
+               len = strlen(" no-llgr");
+               break;
+       case COMMUNITY_ACCEPT_OWN_NEXTHOP:
+               len = strlen(" accept-own-nexthop");
+               break;
+       case COMMUNITY_BLACKHOLE:
+               len = strlen(" blackhole");
+               break;
        case COMMUNITY_NO_EXPORT:
                len = strlen(" no-export");
                break;
@@ -355,8 +385,8 @@ static char *community_str_get(struct community *com, int i)
        case COMMUNITY_LOCAL_AS:
                len = strlen(" local-AS");
                break;
-       case COMMUNITY_GSHUT:
-               len = strlen(" graceful-shutdown");
+       case COMMUNITY_NO_PEER:
+               len = strlen(" no-peer");
                break;
        default:
                len = strlen(" 65536:65535");
@@ -371,6 +401,46 @@ static char *community_str_get(struct community *com, int i)
                strcpy(pnt, "internet");
                pnt += strlen("internet");
                break;
+       case COMMUNITY_GSHUT:
+               strcpy(pnt, "graceful-shutdown");
+               pnt += strlen("graceful-shutdown");
+               break;
+       case COMMUNITY_ACCEPT_OWN:
+               strcpy(pnt, "accept-own");
+               pnt += strlen("accept-own");
+               break;
+       case COMMUNITY_ROUTE_FILTER_TRANSLATED_v4:
+               strcpy(pnt, "route-filter-translated-v4");
+               pnt += strlen("route-filter-translated-v4");
+               break;
+       case COMMUNITY_ROUTE_FILTER_v4:
+               strcpy(pnt, "route-filter-v4");
+               pnt += strlen("route-filter-v4");
+               break;
+       case COMMUNITY_ROUTE_FILTER_TRANSLATED_v6:
+               strcpy(pnt, "route-filter-translated-v6");
+               pnt += strlen("route-filter-translated-v6");
+               break;
+       case COMMUNITY_ROUTE_FILTER_v6:
+               strcpy(pnt, "route-filter-v6");
+               pnt += strlen("route-filter-v6");
+               break;
+       case COMMUNITY_LLGR_STALE:
+               strcpy(pnt, "llgr-stale");
+               pnt += strlen("llgr-stale");
+               break;
+       case COMMUNITY_NO_LLGR:
+               strcpy(pnt, "no-llgr");
+               pnt += strlen("no-llgr");
+               break;
+       case COMMUNITY_ACCEPT_OWN_NEXTHOP:
+               strcpy(pnt, "accept-own-nexthop");
+               pnt += strlen("accept-own-nexthop");
+               break;
+       case COMMUNITY_BLACKHOLE:
+               strcpy(pnt, "blackhole");
+               pnt += strlen("blackhole");
+               break;
        case COMMUNITY_NO_EXPORT:
                strcpy(pnt, "no-export");
                pnt += strlen("no-export");
@@ -383,11 +453,11 @@ static char *community_str_get(struct community *com, int i)
                strcpy(pnt, "local-AS");
                pnt += strlen("local-AS");
                break;
-       case COMMUNITY_GSHUT:
-               strcpy(pnt, "graceful-shutdown");
-               pnt += strlen("graceful-shutdown");
+       case COMMUNITY_NO_PEER:
+               strcpy(pnt, "no-peer");
+               pnt += strlen("no-peer");
                break;
-       default:
+    default:
                as = (comval >> 16) & 0xFFFF;
                val = comval & 0xFFFF;
                sprintf(pnt, "%u:%d", as, val);
@@ -547,47 +617,77 @@ static int ecommunity_regexp_match(struct ecommunity *ecom, regex_t *reg)
 static struct community *
 community_regexp_delete (struct community *com, regex_t * reg)
 {
-  int i;
-  uint32_t comval;
-  /* Maximum is "65535:65535" + '\0'. */
-  char c[12];
-  const char *str;
-
-  if (!com)
-    return NULL;
-
-  i = 0;
-  while (i < com->size)
-    {
-      memcpy (&comval, com_nthval (com, i), sizeof (uint32_t));
-      comval = ntohl (comval);
-
-      switch (comval)
-        {
-        case COMMUNITY_INTERNET:
-          str = "internet";
-          break;
-        case COMMUNITY_NO_EXPORT:
-          str = "no-export";
-          break;
-        case COMMUNITY_NO_ADVERTISE:
-          str = "no-advertise";
-          break;
-        case COMMUNITY_LOCAL_AS:
-          str = "local-AS";
-          break;
-        default:
-          sprintf (c, "%d:%d", (comval >> 16) & 0xFFFF, comval & 0xFFFF);
-          str = c;
-          break;
-        }
-
-      if (regexec (reg, str, 0, NULL, 0) == 0)
-        community_del_val (com, com_nthval (com, i));
-      else
-        i++;
-    }
-  return com;
+       int i;
+       uint32_t comval;
+       /* Maximum is "65535:65535" + '\0'. */
+       char c[12];
+       const char *str;
+
+       if (!com)
+               return NULL;
+
+       i = 0;
+       while (i < com->size)
+       {
+               memcpy (&comval, com_nthval (com, i), sizeof (uint32_t));
+               comval = ntohl (comval);
+
+               switch (comval) {
+               case COMMUNITY_INTERNET:
+                       str = "internet";
+                       break;
+               case COMMUNITY_ACCEPT_OWN:
+                       str = "accept-own";
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v4:
+                       str = "route-filter-translated-v4";
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v4:
+                       str = "route-filter-v4";
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v6:
+                       str = "route-filter-translated-v6";
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v6:
+                       str = "route-filter-v6";
+                       break;
+               case COMMUNITY_LLGR_STALE:
+                       str = "llgr-stale";
+                       break;
+               case COMMUNITY_NO_LLGR:
+                       str = "no-llgr";
+                       break;
+               case COMMUNITY_ACCEPT_OWN_NEXTHOP:
+                       str = "accept-own-nexthop";
+                       break;
+               case COMMUNITY_BLACKHOLE:
+                       str = "blackhole";
+                       break;
+               case COMMUNITY_NO_EXPORT:
+                       str = "no-export";
+                       break;
+               case COMMUNITY_NO_ADVERTISE:
+                       str = "no-advertise";
+                       break;
+               case COMMUNITY_LOCAL_AS:
+                       str = "local-AS";
+                       break;
+               case COMMUNITY_NO_PEER:
+                       str = "no-peer";
+                       break;
+               default:
+                       sprintf (c, "%d:%d", (comval >> 16) & 0xFFFF,
+                        comval & 0xFFFF);
+                       str = c;
+                       break;
+               }
+
+               if (regexec (reg, str, 0, NULL, 0) == 0)
+                       community_del_val (com, com_nthval (com, i));
+               else
+                       i++;
+       }
+       return com;
 }
 #endif
 
index 9170481769dd4fa9507d5ea0423aed3c8871f974..e40674d635982635742c2cdb71869b531684efb4 100644 (file)
@@ -188,10 +188,20 @@ struct community *community_uniq_sort(struct community *com)
    For Well-known communities value, below keyword is used.
 
    0x0             "internet"
+   0xFFFF0000      "graceful-shutdown"
+   0xFFFF0001      "accept-own"
+   0xFFFF0002      "route-filter-translated-v4"
+   0xFFFF0003      "route-filter-v4"
+   0xFFFF0004      "route-filter-translated-v6"
+   0xFFFF0005      "route-filter-v6"
+   0xFFFF0006      "llgr-stale"
+   0xFFFF0007      "no-llgr"
+   0xFFFF0008      "accept-own-nexthop"
+   0xFFFF029A      "blackhole"
    0xFFFFFF01      "no-export"
    0xFFFFFF02      "no-advertise"
    0xFFFFFF03      "local-AS"
-   0xFFFF0000      "graceful-shutdown"
+   0xFFFFFF04      "no-peer"
 
    For other values, "AS:VAL" format is used.  */
 static void set_community_string(struct community *com, bool make_json)
@@ -241,6 +251,36 @@ static void set_community_string(struct community *com, bool make_json)
                case COMMUNITY_INTERNET:
                        len += strlen(" internet");
                        break;
+               case COMMUNITY_GSHUT:
+                       len += strlen(" graceful-shutdown");
+                       break;
+               case COMMUNITY_ACCEPT_OWN:
+                       len += strlen(" accept-own");
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v4:
+                       len += strlen(" route-filter-translated-v4");
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v4:
+                       len += strlen(" route-filter-v4");
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v6:
+                       len += strlen(" route-filter-translated-v6");
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v6:
+                       len += strlen(" route-filter-v6");
+                       break;
+               case COMMUNITY_LLGR_STALE:
+                       len += strlen(" llgr-stale");
+                       break;
+               case COMMUNITY_NO_LLGR:
+                       len += strlen(" no-llgr");
+                       break;
+               case COMMUNITY_ACCEPT_OWN_NEXTHOP:
+                       len += strlen(" accept-own-nexthop");
+                       break;
+               case COMMUNITY_BLACKHOLE:
+                       len += strlen(" blackhole");
+                       break;
                case COMMUNITY_NO_EXPORT:
                        len += strlen(" no-export");
                        break;
@@ -250,8 +290,8 @@ static void set_community_string(struct community *com, bool make_json)
                case COMMUNITY_LOCAL_AS:
                        len += strlen(" local-AS");
                        break;
-               case COMMUNITY_GSHUT:
-                       len += strlen(" graceful-shutdown");
+               case COMMUNITY_NO_PEER:
+                       len += strlen(" no-peer");
                        break;
                default:
                        len += strlen(" 65536:65535");
@@ -284,6 +324,106 @@ static void set_community_string(struct community *com, bool make_json)
                                                      json_string);
                        }
                        break;
+               case COMMUNITY_GSHUT:
+                       strcpy(pnt, "graceful-shutdown");
+                       pnt += strlen("graceful-shutdown");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "gracefulShutdown");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ACCEPT_OWN:
+                       strcpy(pnt, "accept-own");
+                       pnt += strlen("accept-own");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "acceptown");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v4:
+                       strcpy(pnt, "route-filter-translated-v4");
+                       pnt += strlen("route-filter-translated-v4");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "routeFilterTranslatedV4");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v4:
+                       strcpy(pnt, "route-filter-v4");
+                       pnt += strlen("route-filter-v4");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "routeFilterV4");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ROUTE_FILTER_TRANSLATED_v6:
+                       strcpy(pnt, "route-filter-translated-v6");
+                       pnt += strlen("route-filter-translated-v6");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "routeFilterTranslatedV6");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ROUTE_FILTER_v6:
+                       strcpy(pnt, "route-filter-v6");
+                       pnt += strlen("route-filter-v6");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "routeFilterV6");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_LLGR_STALE:
+                       strcpy(pnt, "llgr-stale");
+                       pnt += strlen("llgr-stale");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "llgrStale");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_NO_LLGR:
+                       strcpy(pnt, "no-llgr");
+                       pnt += strlen("no-llgr");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "noLlgr");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_ACCEPT_OWN_NEXTHOP:
+                       strcpy(pnt, "accept-own-nexthop");
+                       pnt += strlen("accept-own-nexthop");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "acceptownnexthop");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
+               case COMMUNITY_BLACKHOLE:
+                       strcpy(pnt, "blackhole");
+                       pnt += strlen("blackhole");
+                       if (make_json) {
+                               json_string = json_object_new_string(
+                                       "blackhole");
+                               json_object_array_add(json_community_list,
+                                                     json_string);
+                       }
+                       break;
                case COMMUNITY_NO_EXPORT:
                        strcpy(pnt, "no-export");
                        pnt += strlen("no-export");
@@ -313,12 +453,11 @@ static void set_community_string(struct community *com, bool make_json)
                                                      json_string);
                        }
                        break;
-               case COMMUNITY_GSHUT:
-                       strcpy(pnt, "graceful-shutdown");
-                       pnt += strlen("graceful-shutdown");
+               case COMMUNITY_NO_PEER:
+                       strcpy(pnt, "no-peer");
+                       pnt += strlen("no-peer");
                        if (make_json) {
-                               json_string = json_object_new_string(
-                                       "gracefulShutdown");
+                               json_string = json_object_new_string("noPeer");
                                json_object_array_add(json_community_list,
                                                      json_string);
                        }
@@ -508,10 +647,20 @@ struct community *community_merge(struct community *com1,
 /* Community token enum. */
 enum community_token {
        community_token_val,
+       community_token_gshut,
+       community_token_accept_own,
+       community_token_route_filter_translated_v4,
+       community_token_route_filter_v4,
+       community_token_route_filter_translated_v6,
+       community_token_route_filter_v6,
+       community_token_llgr_stale,
+       community_token_no_llgr,
+       community_token_accept_own_nexthop,
+       community_token_blackhole,
        community_token_no_export,
        community_token_no_advertise,
        community_token_local_as,
-       community_token_gshut,
+       community_token_no_peer,
        community_token_unknown
 };
 
@@ -537,6 +686,79 @@ community_gettoken(const char *buf, enum community_token *token, uint32_t *val)
                        p += strlen("internet");
                        return p;
                }
+               if (strncmp(p, "graceful-shutdown", strlen("graceful-shutdown"))
+                   == 0) {
+                       *val = COMMUNITY_GSHUT;
+                       *token = community_token_gshut;
+                       p += strlen("graceful-shutdown");
+                       return p;
+               }
+               if (strncmp(p, "accept-own", strlen("accept-own"))
+                   == 0) {
+                       *val = COMMUNITY_ACCEPT_OWN;
+                       *token = community_token_accept_own;
+                       p += strlen("accept-own");
+                       return p;
+               }
+               if (strncmp(p, "route-filter-translated-v4",
+                       strlen("route-filter-translated-v4"))
+                   == 0) {
+                       *val = COMMUNITY_ROUTE_FILTER_TRANSLATED_v4;
+                       *token = community_token_route_filter_translated_v4;
+                       p += strlen("route-filter-translated-v4");
+                       return p;
+               }
+               if (strncmp(p, "route-filter-v4", strlen("route-filter-v4"))
+                   == 0) {
+                       *val = COMMUNITY_ROUTE_FILTER_v4;
+                       *token = community_token_route_filter_v4;
+                       p += strlen("route-filter-v4");
+                       return p;
+               }
+               if (strncmp(p, "route-filter-translated-v6",
+                       strlen("route-filter-translated-v6"))
+                   == 0) {
+                       *val = COMMUNITY_ROUTE_FILTER_TRANSLATED_v6;
+                       *token = community_token_route_filter_translated_v6;
+                       p += strlen("route-filter-translated-v6");
+                       return p;
+               }
+               if (strncmp(p, "route-filter-v6", strlen("route-filter-v6"))
+                   == 0) {
+                       *val = COMMUNITY_ROUTE_FILTER_v6;
+                       *token = community_token_route_filter_v6;
+                       p += strlen("route-filter-v6");
+                       return p;
+               }
+               if (strncmp(p, "llgr-stale", strlen("llgr-stale"))
+                   == 0) {
+                       *val = COMMUNITY_LLGR_STALE;
+                       *token = community_token_llgr_stale;
+                       p += strlen("llgr-stale");
+                       return p;
+               }
+               if (strncmp(p, "no-llgr", strlen("no-llgr"))
+                   == 0) {
+                       *val = COMMUNITY_NO_LLGR;
+                       *token = community_token_no_llgr;
+                       p += strlen("no-llgr");
+                       return p;
+               }
+               if (strncmp(p, "accept-own-nexthop",
+                       strlen("accept-own-nexthop"))
+                   == 0) {
+                       *val = COMMUNITY_ACCEPT_OWN_NEXTHOP;
+                       *token = community_token_accept_own_nexthop;
+                       p += strlen("accept-own-nexthop");
+                       return p;
+               }
+               if (strncmp(p, "blackhole", strlen("blackhole"))
+                   == 0) {
+                       *val = COMMUNITY_BLACKHOLE;
+                       *token = community_token_blackhole;
+                       p += strlen("blackhole");
+                       return p;
+               }
                if (strncmp(p, "no-export", strlen("no-export")) == 0) {
                        *val = COMMUNITY_NO_EXPORT;
                        *token = community_token_no_export;
@@ -555,11 +777,10 @@ community_gettoken(const char *buf, enum community_token *token, uint32_t *val)
                        p += strlen("local-AS");
                        return p;
                }
-               if (strncmp(p, "graceful-shutdown", strlen("graceful-shutdown"))
-                   == 0) {
-                       *val = COMMUNITY_GSHUT;
-                       *token = community_token_gshut;
-                       p += strlen("graceful-shutdown");
+               if (strncmp(p, "no-peer", strlen("no-peer")) == 0) {
+                       *val = COMMUNITY_NO_PEER;
+                       *token = community_token_no_peer;
+                       p += strlen("no-peer");
                        return p;
                }
 
@@ -631,10 +852,20 @@ struct community *community_str2com(const char *str)
 
                switch (token) {
                case community_token_val:
+               case community_token_gshut:
+               case community_token_accept_own:
+               case community_token_route_filter_translated_v4:
+               case community_token_route_filter_v4:
+               case community_token_route_filter_translated_v6:
+               case community_token_route_filter_v6:
+               case community_token_llgr_stale:
+               case community_token_no_llgr:
+               case community_token_accept_own_nexthop:
+               case community_token_blackhole:
                case community_token_no_export:
                case community_token_no_advertise:
                case community_token_local_as:
-               case community_token_gshut:
+               case community_token_no_peer:
                        if (com == NULL) {
                                com = community_new();
                                com->json = NULL;
index c180bea465de02a4002b92ec9cc55f890e2d72df..61af9f038ca88351f5f781f889c7cb9168be1476 100644 (file)
@@ -43,12 +43,22 @@ struct community {
 };
 
 /* Well-known communities value.  */
-#define COMMUNITY_INTERNET              0x0
-#define COMMUNITY_NO_EXPORT             0xFFFFFF01
-#define COMMUNITY_NO_ADVERTISE          0xFFFFFF02
-#define COMMUNITY_NO_EXPORT_SUBCONFED   0xFFFFFF03
-#define COMMUNITY_LOCAL_AS              0xFFFFFF03
-#define COMMUNITY_GSHUT                 0xFFFF0000
+#define COMMUNITY_INTERNET                      0x0
+#define COMMUNITY_GSHUT                         0xFFFF0000
+#define COMMUNITY_ACCEPT_OWN                    0xFFFF0001
+#define COMMUNITY_ROUTE_FILTER_TRANSLATED_v4    0xFFFF0002
+#define COMMUNITY_ROUTE_FILTER_v4               0xFFFF0003
+#define COMMUNITY_ROUTE_FILTER_TRANSLATED_v6    0xFFFF0004
+#define COMMUNITY_ROUTE_FILTER_v6               0xFFFF0005
+#define COMMUNITY_LLGR_STALE                    0xFFFF0006
+#define COMMUNITY_NO_LLGR                       0xFFFF0007
+#define COMMUNITY_ACCEPT_OWN_NEXTHOP            0xFFFF0008
+#define COMMUNITY_BLACKHOLE                     0xFFFF029A
+#define COMMUNITY_NO_EXPORT                     0xFFFFFF01
+#define COMMUNITY_NO_ADVERTISE                  0xFFFFFF02
+#define COMMUNITY_NO_EXPORT_SUBCONFED           0xFFFFFF03
+#define COMMUNITY_LOCAL_AS                      0xFFFFFF03
+#define COMMUNITY_NO_PEER                       0xFFFFFF04
 
 /* Macros of community attribute.  */
 #define com_length(X)    ((X)->size * 4)