{
struct bgp *bgp = NULL;
- bgp = bgp_get_default();
+ bgp = bgp_get_evpn();
return bgp ? bgp->advertise_all_vni : 0;
}
static void evpn_set_advertise_all_vni(struct bgp *bgp)
{
bgp->advertise_all_vni = 1;
+ bgp_set_evpn(bgp);
bgp_zebra_advertise_all_vni(bgp, bgp->advertise_all_vni);
}
static void evpn_unset_advertise_all_vni(struct bgp *bgp)
{
bgp->advertise_all_vni = 0;
+ bgp_set_evpn(bgp_get_default());
bgp_zebra_advertise_all_vni(bgp, bgp->advertise_all_vni);
bgp_evpn_cleanup_on_disable(bgp);
}
"Advertise All local VNIs\n")
{
struct bgp *bgp = VTY_GET_CONTEXT(bgp);
+ struct bgp *bgp_evpn = NULL;
if (!bgp)
return CMD_WARNING;
+
+ bgp_evpn = bgp_get_evpn();
+ if (bgp_evpn && bgp_evpn != bgp) {
+ vty_out(vty, "%% Please unconfigure EVPN in VRF %s\n",
+ bgp_evpn->name);
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
evpn_set_advertise_all_vni(bgp);
return CMD_SUCCESS;
}
*/
static __attribute__((__noreturn__)) void bgp_exit(int status)
{
- struct bgp *bgp, *bgp_default;
+ struct bgp *bgp, *bgp_default, *bgp_evpn;
struct listnode *node, *nnode;
/* it only makes sense for this to be called on a clean exit */
bgp_close();
bgp_default = bgp_get_default();
+ bgp_evpn = bgp_get_evpn();
/* reverse bgp_master_init */
for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
- if (bgp_default == bgp)
+ if (bgp_default == bgp || bgp_evpn == bgp)
continue;
bgp_delete(bgp);
}
+ if (bgp_evpn && bgp_evpn != bgp_default)
+ bgp_delete(bgp_evpn);
if (bgp_default)
bgp_delete(bgp_default);
return CMD_WARNING;
#if ENABLE_BGP_VNC
- if (bgp->vrf_id == VRF_DEFAULT
+ if (bgp->advertise_all_vni
&& type == ZEBRA_ROUTE_VNC_DIRECT) {
vnc_export_bgp_enable(
bgp, afi); /* only enables if mode bits cfg'd */
* status. red lookup fails if there is no zebra connection.
*/
#if ENABLE_BGP_VNC
- if (bgp->vrf_id == VRF_DEFAULT && type == ZEBRA_ROUTE_VNC_DIRECT) {
+ if (bgp->advertise_all_vni && type == ZEBRA_ROUTE_VNC_DIRECT) {
vnc_export_bgp_disable(bgp, afi);
}
#endif
/* Register for router-id, interfaces, redistributed routes. */
zclient_send_reg_requests(zclient, bgp->vrf_id);
- /* For default instance, register to learn about VNIs, if appropriate.
- */
- if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT && is_evpn_enabled())
+ /* For EVPN instance, register to learn about VNIs, if appropriate. */
+ if (bgp->advertise_all_vni)
bgp_zebra_advertise_all_vni(bgp, 1);
bgp_nht_register_nexthops(bgp);
if (BGP_DEBUG(zebra, ZEBRA))
zlog_debug("Deregistering VRF %u", bgp->vrf_id);
- /* For default instance, unregister learning about VNIs, if appropriate.
- */
- if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT && is_evpn_enabled())
+ /* For EVPN instance, unregister learning about VNIs, if appropriate. */
+ if (bgp->advertise_all_vni)
bgp_zebra_advertise_all_vni(bgp, 0);
/* Deregister for router-id, interfaces, redistributed routes. */
name, *as);
}
+ /* Default the EVPN VRF to the default one */
+ if (inst_type == BGP_INSTANCE_TYPE_DEFAULT && !bgp_master.bgp_evpn) {
+ bgp_lock(bgp);
+ bm->bgp_evpn = bgp;
+ }
+
bgp_lock(bgp);
bgp->heuristic_coalesce = true;
bgp->inst_type = inst_type;
return (vrf->info) ? (struct bgp *)vrf->info : NULL;
}
+/* Sets the BGP instance where EVPN is enabled */
+void bgp_set_evpn(struct bgp *bgp)
+{
+ if (bm->bgp_evpn == bgp)
+ return;
+
+ /* First, release the reference count we hold on the instance */
+ if (bm->bgp_evpn)
+ bgp_unlock(bm->bgp_evpn);
+
+ bm->bgp_evpn = bgp;
+
+ /* Increase the reference count on this new VRF */
+ if (bm->bgp_evpn)
+ bgp_lock(bm->bgp_evpn);
+}
+
+/* Returns the BGP instance where EVPN is enabled, if any */
+struct bgp *bgp_get_evpn(void)
+{
+ return bm->bgp_evpn;
+}
+
/* handle socket creation or deletion, if necessary
* this is called for all new BGP instances
*/
if (vrf)
bgp_vrf_unlink(bgp, vrf);
+ /* Update EVPN VRF pointer */
+ if (bm->bgp_evpn == bgp) {
+ if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
+ bgp_set_evpn(NULL);
+ else
+ bgp_set_evpn(bgp_get_default());
+ }
+
thread_master_free_unused(bm->master);
bgp_unlock(bgp); /* initial reference */
/* dynamic mpls label allocation pool */
struct labelpool labelpool;
+ /* BGP-EVPN VRF ID. Defaults to default VRF (if any) */
+ struct bgp* bgp_evpn;
+
bool terminating; /* global flag that sigint terminate seen */
QOBJ_FIELDS
};
extern struct bgp *bgp_lookup(as_t, const char *);
extern struct bgp *bgp_lookup_by_name(const char *);
extern struct bgp *bgp_lookup_by_vrf_id(vrf_id_t);
+extern struct bgp *bgp_get_evpn(void);
+extern void bgp_set_evpn(struct bgp *bgp);
extern struct peer *peer_lookup(struct bgp *, union sockunion *);
extern struct peer *peer_lookup_by_conf_if(struct bgp *, const char *);
extern struct peer *peer_lookup_by_hostname(struct bgp *, const char *);