mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-08-07 10:49:24 +00:00
Merge pull request #6303 from dslicenc/stop-enhe-ras
bgpd: turn off RAs when numbered peers are deleted
This commit is contained in:
commit
37d6afef2a
@ -873,7 +873,7 @@ void bgp_nht_register_nexthops(struct bgp *bgp)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void bgp_nht_register_enhe_capability_interfaces(struct peer *peer)
|
void bgp_nht_reg_enhe_cap_intfs(struct peer *peer)
|
||||||
{
|
{
|
||||||
struct bgp *bgp;
|
struct bgp *bgp;
|
||||||
struct bgp_node *rn;
|
struct bgp_node *rn;
|
||||||
@ -891,9 +891,8 @@ void bgp_nht_register_enhe_capability_interfaces(struct peer *peer)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
if (!sockunion2hostprefix(&peer->su, &p)) {
|
if (!sockunion2hostprefix(&peer->su, &p)) {
|
||||||
if (BGP_DEBUG(nht, NHT))
|
zlog_warn("%s: Unable to convert sockunion to prefix for %s",
|
||||||
zlog_debug("%s: Unable to convert prefix to sockunion",
|
__func__, peer->host);
|
||||||
__func__);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -922,3 +921,48 @@ void bgp_nht_register_enhe_capability_interfaces(struct peer *peer)
|
|||||||
BGP_UNNUM_DEFAULT_RA_INTERVAL);
|
BGP_UNNUM_DEFAULT_RA_INTERVAL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void bgp_nht_dereg_enhe_cap_intfs(struct peer *peer)
|
||||||
|
{
|
||||||
|
struct bgp *bgp;
|
||||||
|
struct bgp_node *rn;
|
||||||
|
struct bgp_nexthop_cache *bnc;
|
||||||
|
struct nexthop *nhop;
|
||||||
|
struct interface *ifp;
|
||||||
|
struct prefix p;
|
||||||
|
|
||||||
|
if (peer->ifp)
|
||||||
|
return;
|
||||||
|
|
||||||
|
bgp = peer->bgp;
|
||||||
|
|
||||||
|
if (!bgp->nexthop_cache_table[AFI_IP6])
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!sockunion2hostprefix(&peer->su, &p)) {
|
||||||
|
zlog_warn("%s: Unable to convert sockunion to prefix for %s",
|
||||||
|
__func__, peer->host);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (p.family != AF_INET6)
|
||||||
|
return;
|
||||||
|
|
||||||
|
rn = bgp_node_lookup(bgp->nexthop_cache_table[AFI_IP6], &p);
|
||||||
|
if (!rn)
|
||||||
|
return;
|
||||||
|
|
||||||
|
bnc = bgp_node_get_bgp_nexthop_info(rn);
|
||||||
|
if (!bnc)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (peer != bnc->nht_info)
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (nhop = bnc->nexthop; nhop; nhop = nhop->next) {
|
||||||
|
ifp = if_lookup_by_index(nhop->ifindex, nhop->vrf_id);
|
||||||
|
|
||||||
|
zclient_send_interface_radv_req(zclient, nhop->vrf_id, ifp, 0,
|
||||||
|
0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -87,6 +87,7 @@ extern void bgp_nht_register_nexthops(struct bgp *bgp);
|
|||||||
* this code can walk the registered nexthops and
|
* this code can walk the registered nexthops and
|
||||||
* register the important ones with zebra for RA.
|
* register the important ones with zebra for RA.
|
||||||
*/
|
*/
|
||||||
extern void bgp_nht_register_enhe_capability_interfaces(struct peer *peer);
|
extern void bgp_nht_reg_enhe_cap_intfs(struct peer *peer);
|
||||||
|
extern void bgp_nht_dereg_enhe_cap_intfs(struct peer *peer);
|
||||||
|
|
||||||
#endif /* _BGP_NHT_H */
|
#endif /* _BGP_NHT_H */
|
||||||
|
@ -3822,6 +3822,10 @@ DEFUN (no_neighbor,
|
|||||||
}
|
}
|
||||||
|
|
||||||
other = peer->doppelganger;
|
other = peer->doppelganger;
|
||||||
|
|
||||||
|
if (CHECK_FLAG(peer->flags, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
bgp_zebra_terminate_radv(peer->bgp, peer);
|
||||||
|
|
||||||
peer_notify_unconfig(peer);
|
peer_notify_unconfig(peer);
|
||||||
peer_delete(peer);
|
peer_delete(peer);
|
||||||
if (other && other->status != Deleted) {
|
if (other && other->status != Deleted) {
|
||||||
@ -4242,6 +4246,9 @@ DEFUN (no_neighbor_set_peer_group,
|
|||||||
return CMD_WARNING_CONFIG_FAILED;
|
return CMD_WARNING_CONFIG_FAILED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (CHECK_FLAG(peer->flags, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
bgp_zebra_terminate_radv(peer->bgp, peer);
|
||||||
|
|
||||||
peer_notify_unconfig(peer);
|
peer_notify_unconfig(peer);
|
||||||
ret = peer_delete(peer);
|
ret = peer_delete(peer);
|
||||||
|
|
||||||
|
@ -1939,8 +1939,14 @@ void bgp_zebra_initiate_radv(struct bgp *bgp, struct peer *peer)
|
|||||||
zlog_debug("%u: Initiating RA for peer %s", bgp->vrf_id,
|
zlog_debug("%u: Initiating RA for peer %s", bgp->vrf_id,
|
||||||
peer->host);
|
peer->host);
|
||||||
|
|
||||||
zclient_send_interface_radv_req(zclient, bgp->vrf_id, peer->ifp, 1,
|
/*
|
||||||
ra_interval);
|
* If unnumbered peer (peer->ifp) call thru zapi to start RAs.
|
||||||
|
* If we don't have an ifp pointer, call function to find the
|
||||||
|
* ifps for a numbered enhe peer to turn RAs on.
|
||||||
|
*/
|
||||||
|
peer->ifp ? zclient_send_interface_radv_req(zclient, bgp->vrf_id,
|
||||||
|
peer->ifp, 1, ra_interval)
|
||||||
|
: bgp_nht_reg_enhe_cap_intfs(peer);
|
||||||
}
|
}
|
||||||
|
|
||||||
void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer)
|
void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer)
|
||||||
@ -1953,7 +1959,14 @@ void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer)
|
|||||||
zlog_debug("%u: Terminating RA for peer %s", bgp->vrf_id,
|
zlog_debug("%u: Terminating RA for peer %s", bgp->vrf_id,
|
||||||
peer->host);
|
peer->host);
|
||||||
|
|
||||||
zclient_send_interface_radv_req(zclient, bgp->vrf_id, peer->ifp, 0, 0);
|
/*
|
||||||
|
* If unnumbered peer (peer->ifp) call thru zapi to stop RAs.
|
||||||
|
* If we don't have an ifp pointer, call function to find the
|
||||||
|
* ifps for a numbered enhe peer to turn RAs off.
|
||||||
|
*/
|
||||||
|
peer->ifp ? zclient_send_interface_radv_req(zclient, bgp->vrf_id,
|
||||||
|
peer->ifp, 0, 0)
|
||||||
|
: bgp_nht_dereg_enhe_cap_intfs(peer);
|
||||||
}
|
}
|
||||||
|
|
||||||
int bgp_zebra_advertise_subnet(struct bgp *bgp, int advertise, vni_t vni)
|
int bgp_zebra_advertise_subnet(struct bgp *bgp, int advertise, vni_t vni)
|
||||||
|
35
bgpd/bgpd.c
35
bgpd/bgpd.c
@ -2490,6 +2490,11 @@ static void peer_group2peer_config_copy(struct peer_group *group,
|
|||||||
: BGP_DEFAULT_EBGP_ROUTEADV;
|
: BGP_DEFAULT_EBGP_ROUTEADV;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* capability extended-nexthop apply */
|
||||||
|
if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
if (CHECK_FLAG(conf->flags, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
SET_FLAG(peer->flags, PEER_FLAG_CAPABILITY_ENHE);
|
||||||
|
|
||||||
/* password apply */
|
/* password apply */
|
||||||
if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_PASSWORD))
|
if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_PASSWORD))
|
||||||
PEER_STR_ATTR_INHERIT(peer, group, password,
|
PEER_STR_ATTR_INHERIT(peer, group, password,
|
||||||
@ -2577,6 +2582,10 @@ int peer_group_delete(struct peer_group *group)
|
|||||||
|
|
||||||
for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
|
for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
|
||||||
other = peer->doppelganger;
|
other = peer->doppelganger;
|
||||||
|
|
||||||
|
if (CHECK_FLAG(peer->flags, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
bgp_zebra_terminate_radv(bgp, peer);
|
||||||
|
|
||||||
peer_delete(peer);
|
peer_delete(peer);
|
||||||
if (other && other->status != Deleted) {
|
if (other && other->status != Deleted) {
|
||||||
other->group = NULL;
|
other->group = NULL;
|
||||||
@ -2621,6 +2630,9 @@ int peer_group_remote_as_delete(struct peer_group *group)
|
|||||||
for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
|
for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
|
||||||
other = peer->doppelganger;
|
other = peer->doppelganger;
|
||||||
|
|
||||||
|
if (CHECK_FLAG(peer->flags, PEER_FLAG_CAPABILITY_ENHE))
|
||||||
|
bgp_zebra_terminate_radv(peer->bgp, peer);
|
||||||
|
|
||||||
peer_delete(peer);
|
peer_delete(peer);
|
||||||
|
|
||||||
if (other && other->status != Deleted) {
|
if (other && other->status != Deleted) {
|
||||||
@ -4065,8 +4077,22 @@ static int peer_flag_modify(struct peer *peer, uint32_t flag, int set)
|
|||||||
/* Update flag override state accordingly. */
|
/* Update flag override state accordingly. */
|
||||||
COND_FLAG(peer->flags_override, flag, set != invert);
|
COND_FLAG(peer->flags_override, flag, set != invert);
|
||||||
|
|
||||||
if (set && flag == PEER_FLAG_CAPABILITY_ENHE)
|
/*
|
||||||
bgp_nht_register_enhe_capability_interfaces(peer);
|
* For the extended next-hop encoding flag we need to turn RAs
|
||||||
|
* on if flag is being set, but only turn RAs off if the flag
|
||||||
|
* is being unset on this peer and if this peer is a member of a
|
||||||
|
* peer-group, the peer-group also doesn't have the flag set.
|
||||||
|
*/
|
||||||
|
if (flag == PEER_FLAG_CAPABILITY_ENHE) {
|
||||||
|
if (set) {
|
||||||
|
bgp_zebra_initiate_radv(peer->bgp, peer);
|
||||||
|
} else if (peer_group_active(peer)) {
|
||||||
|
if (!CHECK_FLAG(peer->group->conf->flags, flag))
|
||||||
|
bgp_zebra_terminate_radv(peer->bgp,
|
||||||
|
peer);
|
||||||
|
} else
|
||||||
|
bgp_zebra_terminate_radv(peer->bgp, peer);
|
||||||
|
}
|
||||||
|
|
||||||
/* Execute flag action on peer. */
|
/* Execute flag action on peer. */
|
||||||
if (action.type == peer_change_reset)
|
if (action.type == peer_change_reset)
|
||||||
@ -4099,8 +4125,9 @@ static int peer_flag_modify(struct peer *peer, uint32_t flag, int set)
|
|||||||
/* Update flag on peer-group member. */
|
/* Update flag on peer-group member. */
|
||||||
COND_FLAG(member->flags, flag, set != member_invert);
|
COND_FLAG(member->flags, flag, set != member_invert);
|
||||||
|
|
||||||
if (set && flag == PEER_FLAG_CAPABILITY_ENHE)
|
if (flag == PEER_FLAG_CAPABILITY_ENHE)
|
||||||
bgp_nht_register_enhe_capability_interfaces(member);
|
set ? bgp_zebra_initiate_radv(member->bgp, member)
|
||||||
|
: bgp_zebra_terminate_radv(member->bgp, member);
|
||||||
|
|
||||||
/* Execute flag action on peer-group member. */
|
/* Execute flag action on peer-group member. */
|
||||||
if (action.type == peer_change_reset)
|
if (action.type == peer_change_reset)
|
||||||
|
Loading…
Reference in New Issue
Block a user