Skip to content

Commit

Permalink
bgpd: fix flushing ipv6 flowspec entries when peering stops
Browse files Browse the repository at this point in the history
When a BGP flowspec peering stops, the BGP RIB entries for IPv6
flowspec entries are removed, but not the ZEBRA RIB IPv6 entries.

Actually, when calling bgp_zebra_withdraw() function call, only
the AFI_IP parameter is passed to the bgp_pbr_update_entry() function
in charge of the Flowspec add/delete in zebra. Fix this by passing
the AFI parameter to the bgp_zebra_withdraw() function.

Note that using topotest does not show up the problem as the
flowspec driver code is not present and was refused. Without that,
routes are not installed, and can not be uninstalled.

Fixes: 529efa2 ("bgpd: allow flowspec entries to be announced to zebra")
Link: #2025

Signed-off-by: Philippe Guibert <[email protected]>
  • Loading branch information
pguibert6WIND committed Feb 7, 2024
1 parent ab3d084 commit ec6e09c
Show file tree
Hide file tree
Showing 3 changed files with 16 additions and 13 deletions.
21 changes: 12 additions & 9 deletions bgpd/bgp_route.c
Original file line number Diff line number Diff line change
Expand Up @@ -3520,7 +3520,8 @@ static void bgp_process_main_one(struct bgp *bgp, struct bgp_dest *dest,
*/
if (old_select &&
is_route_parent_evpn(old_select))
bgp_zebra_withdraw(p, old_select, bgp, safi);
bgp_zebra_withdraw(p, old_select, bgp, afi,
safi);

bgp_zebra_announce(dest, p, new_select, bgp, afi, safi);
} else {
Expand All @@ -3530,7 +3531,8 @@ static void bgp_process_main_one(struct bgp *bgp, struct bgp_dest *dest,
|| old_select->sub_type == BGP_ROUTE_AGGREGATE
|| old_select->sub_type == BGP_ROUTE_IMPORTED))

bgp_zebra_withdraw(p, old_select, bgp, safi);
bgp_zebra_withdraw(p, old_select, bgp, afi,
safi);
}
}

Expand Down Expand Up @@ -4427,7 +4429,7 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
if (pi && pi->attr->rmap_table_id != new_attr.rmap_table_id) {
if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED))
/* remove from RIB previous entry */
bgp_zebra_withdraw(p, pi, bgp, safi);
bgp_zebra_withdraw(p, pi, bgp, afi, safi);
}

if (peer->sort == BGP_PEER_EBGP) {
Expand Down Expand Up @@ -6029,7 +6031,7 @@ bool bgp_inbound_policy_exists(struct peer *peer, struct bgp_filter *filter)
}

static void bgp_cleanup_table(struct bgp *bgp, struct bgp_table *table,
safi_t safi)
afi_t afi, safi_t safi)
{
struct bgp_dest *dest;
struct bgp_path_info *pi;
Expand All @@ -6053,7 +6055,8 @@ static void bgp_cleanup_table(struct bgp *bgp, struct bgp_table *table,
|| pi->sub_type == BGP_ROUTE_IMPORTED)) {

if (bgp_fibupd_safi(safi))
bgp_zebra_withdraw(p, pi, bgp, safi);
bgp_zebra_withdraw(p, pi, bgp, afi,
safi);
}

dest = bgp_path_info_reap(dest, pi);
Expand All @@ -6071,7 +6074,7 @@ void bgp_cleanup_routes(struct bgp *bgp)
for (afi = AFI_IP; afi < AFI_MAX; ++afi) {
if (afi == AFI_L2VPN)
continue;
bgp_cleanup_table(bgp, bgp->rib[afi][SAFI_UNICAST],
bgp_cleanup_table(bgp, bgp->rib[afi][SAFI_UNICAST], afi,
SAFI_UNICAST);
/*
* VPN and ENCAP and EVPN tables are two-level (RD is top level)
Expand All @@ -6083,7 +6086,7 @@ void bgp_cleanup_routes(struct bgp *bgp)
dest = bgp_route_next(dest)) {
table = bgp_dest_get_bgp_table_info(dest);
if (table != NULL) {
bgp_cleanup_table(bgp, table, safi);
bgp_cleanup_table(bgp, table, afi, safi);
bgp_table_finish(&table);
bgp_dest_set_bgp_table_info(dest, NULL);
dest = bgp_dest_unlock_node(dest);
Expand All @@ -6096,7 +6099,7 @@ void bgp_cleanup_routes(struct bgp *bgp)
dest = bgp_route_next(dest)) {
table = bgp_dest_get_bgp_table_info(dest);
if (table != NULL) {
bgp_cleanup_table(bgp, table, safi);
bgp_cleanup_table(bgp, table, afi, safi);
bgp_table_finish(&table);
bgp_dest_set_bgp_table_info(dest, NULL);
dest = bgp_dest_unlock_node(dest);
Expand All @@ -6110,7 +6113,7 @@ void bgp_cleanup_routes(struct bgp *bgp)
dest = bgp_route_next(dest)) {
table = bgp_dest_get_bgp_table_info(dest);
if (table != NULL) {
bgp_cleanup_table(bgp, table, SAFI_EVPN);
bgp_cleanup_table(bgp, table, afi, SAFI_EVPN);
bgp_table_finish(&table);
bgp_dest_set_bgp_table_info(dest, NULL);
dest = bgp_dest_unlock_node(dest);
Expand Down
6 changes: 3 additions & 3 deletions bgpd/bgp_zebra.c
Original file line number Diff line number Diff line change
Expand Up @@ -1724,7 +1724,7 @@ void bgp_zebra_announce_table_all_subtypes(struct bgp *bgp, afi_t afi,
}

void bgp_zebra_withdraw(const struct prefix *p, struct bgp_path_info *info,
struct bgp *bgp, safi_t safi)
struct bgp *bgp, afi_t afi, safi_t safi)
{
struct zapi_route api;
struct peer *peer;
Expand All @@ -1743,7 +1743,7 @@ void bgp_zebra_withdraw(const struct prefix *p, struct bgp_path_info *info,

if (safi == SAFI_FLOWSPEC) {
peer = info->peer;
bgp_pbr_update_entry(peer->bgp, p, info, AFI_IP, safi, false);
bgp_pbr_update_entry(peer->bgp, p, info, afi, safi, false);
return;
}

Expand Down Expand Up @@ -1784,7 +1784,7 @@ void bgp_zebra_withdraw_table_all_subtypes(struct bgp *bgp, afi_t afi, safi_t sa
if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED)
&& (pi->type == ZEBRA_ROUTE_BGP))
bgp_zebra_withdraw(bgp_dest_get_prefix(dest),
pi, bgp, safi);
pi, bgp, afi, safi);
}
}
}
Expand Down
2 changes: 1 addition & 1 deletion bgpd/bgp_zebra.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ extern void bgp_zebra_announce(struct bgp_dest *dest, const struct prefix *p,
extern void bgp_zebra_announce_table(struct bgp *bgp, afi_t afi, safi_t safi);
extern void bgp_zebra_withdraw(const struct prefix *p,
struct bgp_path_info *path, struct bgp *bgp,
safi_t safi);
afi_t afi, safi_t safi);

/* Announce routes of any bgp subtype of a table to zebra */
extern void bgp_zebra_announce_table_all_subtypes(struct bgp *bgp, afi_t afi,
Expand Down

0 comments on commit ec6e09c

Please sign in to comment.