diff options
| -rw-r--r-- | zebra/zebra_evpn_mac.c | 28 | 
1 files changed, 20 insertions, 8 deletions
diff --git a/zebra/zebra_evpn_mac.c b/zebra/zebra_evpn_mac.c index e38766bc6b..74043e521c 100644 --- a/zebra/zebra_evpn_mac.c +++ b/zebra/zebra_evpn_mac.c @@ -1141,14 +1141,6 @@ int zebra_evpn_mac_del(struct zebra_evpn *zevpn, struct zebra_mac *mac)  							  sizeof(mac_buf)));  	} -	/* If the MAC is freed before the neigh we will end up -	 * with a stale pointer against the neigh -	 */ -	if (!list_isempty(mac->neigh_list)) -		zlog_warn("%s: MAC %pEA flags 0x%x neigh list not empty %d", -			  __func__, &mac->macaddr, mac->flags, -			  listcount(mac->neigh_list)); -  	/* force de-ref any ES entry linked to the MAC */  	zebra_evpn_es_mac_deref_entry(mac); @@ -1161,6 +1153,26 @@ int zebra_evpn_mac_del(struct zebra_evpn *zevpn, struct zebra_mac *mac)  	/* Cancel auto recovery */  	THREAD_OFF(mac->dad_mac_auto_recovery_timer); +	/* If the MAC is freed before the neigh we will end up +	 * with a stale pointer against the neigh. +	 * The situation can arise when a MAC is in remote state +	 * and its associated neigh is local state. +	 * zebra_evpn_cfg_cleanup() cleans up remote neighs and MACs. +	 * Instead of deleting remote MAC, if its neigh list is non-empty +	 * (associated to local neighs), mark the MAC as AUTO. +	 */ +	if (!list_isempty(mac->neigh_list)) { +		if (IS_ZEBRA_DEBUG_VXLAN) +			zlog_debug( +				"MAC %pEA (flags 0x%x vni %u) has non-empty neigh list " +				"count %u, mark MAC as AUTO", +				&mac->macaddr, mac->flags, zevpn->vni, +				listcount(mac->neigh_list)); + +		SET_FLAG(mac->flags, ZEBRA_MAC_AUTO); +		return 0; +	} +  	list_delete(&mac->neigh_list);  	/* Free the VNI hash entry and allocated memory. */  | 
