Mailing List Archive

[PATCH 49/57] bgpd: enhance reception of bgp ext. community default gateway
This fix permits processing of default gateway extended
community if present. This option, if router mac option is not
present, will replace it.
Also, when exporting route entry to VRF RIB, if VRF is layer 2
type, then the ecommunity related to mac address and router mac
are stripped.

Signed-off-by: Philippe Guibert <philippe.guibert@6wind.com>
---
bgpd/bgp_ecommunity.c | 57 +++++++++++++++++++++++++++++++++++++++++++++------
bgpd/bgp_ecommunity.h | 11 ++++++++--
bgpd/bgp_route.c | 24 ++++++++++++++++++----
3 files changed, 80 insertions(+), 12 deletions(-)

diff --git a/bgpd/bgp_ecommunity.c b/bgpd/bgp_ecommunity.c
index de3bce41783c..27f19fa31201 100644
--- a/bgpd/bgp_ecommunity.c
+++ b/bgpd/bgp_ecommunity.c
@@ -34,7 +34,7 @@ Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
static struct hash *ecomhash;

/* Allocate a new ecommunities. */
-static struct ecommunity *
+struct ecommunity *
ecommunity_new (void)
{
return (struct ecommunity *) XCALLOC (MTYPE_ECOMMUNITY,
@@ -807,19 +807,64 @@ ecommunity_match (const struct ecommunity *ecom1,
}

/* return first occurence of type */
-extern struct ecommunity_val *ecommunity_lookup (const struct ecommunity *ecom, uint8_t type)
+extern struct ecommunity_val *ecommunity_lookup (const struct ecommunity *ecom, uint8_t type, uint8_t subtype)
{
u_int8_t *p;
int c;
- struct ecommunity_val *ecom_val;

+ if(ecom == NULL)
+ return NULL;
/* If the value already exists in the structure return 0. */
c = 0;
for (p = ecom->val; c < ecom->size; p += ECOMMUNITY_SIZE, c++)
{
- ecom_val = (struct ecommunity_val *)p;
- if(ecom_val->val[0] == type)
- return ecom_val;
+ if(p == NULL)
+ {
+ continue;
+ }
+ if(p[0] == type && p[1] == subtype)
+ return (struct ecommunity_val *)p;
}
return NULL;
}
+
+/* remove ext. community matching type and subtype
+ * return 1 on success ( removed ), 0 otherwise (not present)
+ */
+extern int ecommunity_strip (struct ecommunity *ecom, uint8_t type, uint8_t subtype)
+{
+ u_int8_t *p;
+ int c, found = 0;
+ /* When this is fist value, just add it. */
+ if (ecom == NULL || ecom->val == NULL)
+ {
+ return 0;
+ }
+
+ /* If the value already exists in the structure return 0. */
+ c = 0;
+ for (p = ecom->val; c < ecom->size; p += ECOMMUNITY_SIZE, c++)
+ {
+ if (p[0] == type && p[1] == subtype)
+ {
+ found = 1;
+ break;
+ }
+ }
+ if (found == 0)
+ return 0;
+ /* Strip The selected value */
+ ecom->size--;
+ /* size is reduced. no memmove to do */
+ p = XMALLOC (MTYPE_ECOMMUNITY_VAL, ecom->size * ECOMMUNITY_SIZE);
+ if (c != 0)
+ memcpy(p, ecom->val, c * ECOMMUNITY_SIZE);
+ if( (ecom->size - c) != 0)
+ memcpy(p + (c) * ECOMMUNITY_SIZE,
+ ecom->val + (c +1)* ECOMMUNITY_SIZE,
+ (ecom->size - c) * ECOMMUNITY_SIZE);
+ /* shift last ecommunities */
+ XFREE (MTYPE_ECOMMUNITY, ecom->val);
+ ecom->val = p;
+ return 1;
+}
diff --git a/bgpd/bgp_ecommunity.h b/bgpd/bgp_ecommunity.h
index 05ae932a44c4..79040318b744 100644
--- a/bgpd/bgp_ecommunity.h
+++ b/bgpd/bgp_ecommunity.h
@@ -32,6 +32,12 @@ Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
#define ECOMMUNITY_ROUTE_TARGET 0x02
#define ECOMMUNITY_SITE_ORIGIN 0x03

+#define ECOMMUNITY_EVPN_SUBTYPE_MACMOBILITY 0x00
+#define ECOMMUNITY_EVPN_SUBTYPE_ESI_LABEL 0x01
+#define ECOMMUNITY_EVPN_SUBTYPE_ES_IMPORT_RT 0x02
+#define ECOMMUNITY_EVPN_SUBTYPE_ROUTERMAC 0x03
+#define ECOMMUNITY_EVPN_SUBTYPE_DEF_GW 0x0d
+
/* Low-order octet of the Extended Communities type field for OPAQUE types */
#define ECOMMUNITY_OPAQUE_SUBTYPE_ENCAP 0x0c

@@ -85,7 +91,8 @@ extern struct ecommunity *ecommunity_str2com (const char *, int, int);
extern char *ecommunity_ecom2str (struct ecommunity *, int, int);
extern int ecommunity_match (const struct ecommunity *, const struct ecommunity *);
extern char *ecommunity_str (struct ecommunity *);
-extern struct ecommunity_val *ecommunity_lookup (const struct ecommunity *, uint8_t );
+extern struct ecommunity_val *ecommunity_lookup (const struct ecommunity *, uint8_t, uint8_t );
extern int ecommunity_add_val (struct ecommunity *ecom, struct ecommunity_val *eval);
-
+extern int ecommunity_strip (struct ecommunity *ecom, uint8_t type, uint8_t subtype);
+struct ecommunity *ecommunity_new (void);
#endif /* _QUAGGA_BGP_ECOMMUNITY_H */
diff --git a/bgpd/bgp_route.c b/bgpd/bgp_route.c
index 571dcbdcf1f3..17b6d94a6caa 100644
--- a/bgpd/bgp_route.c
+++ b/bgpd/bgp_route.c
@@ -4764,19 +4764,23 @@ bgp_static_update_safi (struct bgp *bgp, struct prefix *p,
if(afi == AFI_INTERNAL_L2VPN)
{
struct bgp_encap_type_vxlan bet;
+ struct attr_extra *extra;

memset(&bet, 0, sizeof(struct bgp_encap_type_vxlan));
if(bgp_static->eth_t_id)
bet.vnid = bgp_static->eth_t_id;
bgp_encap_type_vxlan_to_tlv(&bet, &attr);
- if(bgp_static->router_mac)
+ extra = bgp_attr_extra_get (&attr);
+ if(bgp_static->router_mac)
{
struct ecommunity_val routermac;
memset(&routermac, 0, sizeof(struct ecommunity_val));
routermac.val[0] = ECOMMUNITY_ENCODE_EVPN;
routermac.val[1] = ECOMMUNITY_SITE_ORIGIN;
memcpy(&routermac.val[2], bgp_static->router_mac, MAC_LEN);
- ecommunity_add_val(bgp_attr_extra_get (&attr)->ecommunity,&routermac);
+ if(!extra->ecommunity)
+ extra->ecommunity = ecommunity_new ();
+ ecommunity_add_val(extra->ecommunity,&routermac);
}
if (bgp_static->igpnexthop.s_addr)
{
@@ -7259,9 +7263,21 @@ route_vty_out_overlay (struct vty *vty, struct prefix *p,
}
if(attr->extra->ecommunity)
{
- struct ecommunity_val *routermac = ecommunity_lookup (attr->extra->ecommunity, ECOMMUNITY_ENCODE_EVPN);
-
+ char *mac = NULL;
+ struct ecommunity_val *routermac = ecommunity_lookup (attr->extra->ecommunity,
+ ECOMMUNITY_ENCODE_EVPN,
+ ECOMMUNITY_EVPN_SUBTYPE_ROUTERMAC);
if(routermac)
+ mac = ecom_mac2str((char *)routermac->val);
+ else
+ {
+ if(ecommunity_lookup (attr->extra->ecommunity,
+ ECOMMUNITY_ENCODE_EVPN,
+ ECOMMUNITY_EVPN_SUBTYPE_ROUTERMAC))
+ if ((p->u).prefix_macip.mac_len == 8*ETHER_ADDR_LEN)
+ mac = ecom_mac2str((char *)&(p->u).prefix_macip.mac);
+ }
+ if(mac)
{
char *mac = ecom_mac2str(routermac->val);
vty_out (vty, "/%s",(char *)mac);
--
2.1.4


_______________________________________________
Quagga-dev mailing list
Quagga-dev@lists.quagga.net
https://lists.quagga.net/mailman/listinfo/quagga-dev