Neigh update can have router_flag change, from unset to set and
viceversa. This is the case where MAC, IP and VLAN are same but
entry's flag moved from R to not R bit and reverse case.
Router flag change needs to trigger bgpd to inform all evpn peers
to remove from the evpn route.
Testing Done:
Send GARP with and without R bit from host and validate neigh entry
and evpn neigh and mac-ip route entry in zebra and bgpd.
Check Peer VTEP evpn route entry where router flag is (un)set.
With R-bit
Route [2]:[0]:[0]:[48]:[00:1f:2f:db:45:a6]:[128]:[2006:33:33:2::10]
VNI 1001
Imported from
27.0.0.16:5:[2]:[0]:[0]:[48]:[00:1f:2f:db:45:a6]:[128]:[2006:33:33:2::10]
4435 5551
27.0.0.16 from MSP1(uplink-1) (27.0.0.9)
Origin IGP, valid, external, bestpath-from-AS 4435, best
Extended Community: RT:5551:1001 ET:8 ND:Router
Flag
AddPath ID: RX 0, TX 1261
Last update: Wed Aug 15 20:52:14 2018
Without R-bit
Route [2]:[0]:[0]:[48]:[00:1f:2f:db:45:a6]:[128]:[2006:33:33:2::10]
VNI 1001
Imported from
27.0.0.16:5:[2]:[0]:[0]:[48]:[00:1f:2f:db:45:a6]:[128]:[2006:33:33:2::10]
4435 5551
27.0.0.16 from MSP2(uplink-2) (27.0.0.10)
Origin IGP, valid, external, bestpath-from-AS 4435, best
Extended Community: RT:5551:1001 ET:8
AddPath ID: RX 0, TX 1263
Last update: Wed Aug 15 20:53:10 2018
Signed-off-by: Chirag Shah <chirag@cumulusnetworks.com>
char buf2[INET6_ADDRSTRLEN];
zebra_neigh_t *n = NULL;
zebra_mac_t *zmac = NULL, *old_zmac = NULL;
char buf2[INET6_ADDRSTRLEN];
zebra_neigh_t *n = NULL;
zebra_mac_t *zmac = NULL, *old_zmac = NULL;
+ bool check_rbit = false;
/* create a dummy MAC if the MAC is not already present */
zmac = zvni_mac_lookup(zvni, macaddr);
/* create a dummy MAC if the MAC is not already present */
zmac = zvni_mac_lookup(zvni, macaddr);
n = zvni_neigh_lookup(zvni, ip);
if (n) {
if (CHECK_FLAG(n->flags, ZEBRA_NEIGH_LOCAL)) {
n = zvni_neigh_lookup(zvni, ip);
if (n) {
if (CHECK_FLAG(n->flags, ZEBRA_NEIGH_LOCAL)) {
+
+ if (router_flag !=
+ (CHECK_FLAG(n->flags, ZEBRA_NEIGH_ROUTER_FLAG)
+ ? 1 : 0))
+ check_rbit = true;
+
if (memcmp(n->emac.octet, macaddr->octet,
ETH_ALEN) == 0) {
/* Update any params and return - client doesn't
* care about a purely local change.
*/
n->ifindex = ifp->ifindex;
if (memcmp(n->emac.octet, macaddr->octet,
ETH_ALEN) == 0) {
/* Update any params and return - client doesn't
* care about a purely local change.
*/
n->ifindex = ifp->ifindex;
- /* If the MAC has changed,
- * need to issue a delete first
- * as this means a different MACIP route.
- * Also, need to do some unlinking/relinking.
- */
- zvni_neigh_send_del_to_client(zvni->vni, &n->ip,
+ /* If the MAC has changed,
+ * need to issue a delete first
+ * as this means a different MACIP route.
+ * Also, need to do some unlinking/relinking.
+ */
+ zvni_neigh_send_del_to_client(zvni->vni, &n->ip,
- old_zmac = zvni_mac_lookup(zvni, &n->emac);
- if (old_zmac) {
- listnode_delete(old_zmac->neigh_list, n);
- zvni_deref_ip2mac(zvni, old_zmac, 0);
- }
+ old_zmac = zvni_mac_lookup(zvni, &n->emac);
+ if (old_zmac) {
+ listnode_delete(old_zmac->neigh_list, n);
+ zvni_deref_ip2mac(zvni, old_zmac, 0);
+ }
- /* Update the forwarding info. */
- n->ifindex = ifp->ifindex;
- memcpy(&n->emac, macaddr, ETH_ALEN);
+ /* Update the forwarding info. */
+ n->ifindex = ifp->ifindex;
+ memcpy(&n->emac, macaddr, ETH_ALEN);
- /* Link to new MAC */
- listnode_add_sort(zmac->neigh_list, n);
+ /* Link to new MAC */
+ listnode_add_sort(zmac->neigh_list, n);
+ }
} else
/* Neighbor has moved from remote to local. */
} else
/* Neighbor has moved from remote to local. */
n->r_vtep_ip.s_addr = 0;
SET_FLAG(n->flags, ZEBRA_NEIGH_LOCAL);
n->ifindex = ifp->ifindex;
n->r_vtep_ip.s_addr = 0;
SET_FLAG(n->flags, ZEBRA_NEIGH_LOCAL);
n->ifindex = ifp->ifindex;
}
} else {
/* New neighbor - create */
}
} else {
/* New neighbor - create */
/* Set "local" forwarding info. */
SET_FLAG(n->flags, ZEBRA_NEIGH_LOCAL);
n->ifindex = ifp->ifindex;
/* Set "local" forwarding info. */
SET_FLAG(n->flags, ZEBRA_NEIGH_LOCAL);
n->ifindex = ifp->ifindex;
}
/*Mark Router flag (R-bit) */
}
/*Mark Router flag (R-bit) */
if (!CHECK_FLAG(zmac->flags, ZEBRA_MAC_LOCAL)) {
if (IS_ZEBRA_DEBUG_VXLAN)
zlog_debug(
if (!CHECK_FLAG(zmac->flags, ZEBRA_MAC_LOCAL)) {
if (IS_ZEBRA_DEBUG_VXLAN)
zlog_debug(
- "Skipping neigh %s add to client as MAC %s is not local on VNI %u",
+ "Skipping neigh %s add to client as MAC %s is not local on VNI %u with flags 0x%x",
ipaddr2str(ip, buf2, sizeof(buf2)),
prefix_mac2str(macaddr, buf, sizeof(buf)),
ipaddr2str(ip, buf2, sizeof(buf2)),
prefix_mac2str(macaddr, buf, sizeof(buf)),
+ zvni->vni, n->flags);
+
+ return 0;
+ }
+ if (!check_rbit) {
+ if (IS_ZEBRA_DEBUG_VXLAN)
+ zlog_debug(
+ "Skipping neigh %s with MAC %s on VNI %u add to client as router flag is not set.",
+ ipaddr2str(ip, buf2, sizeof(buf2)),
+ prefix_mac2str(macaddr, buf, sizeof(buf)),
+ zvni->vni);