Commit c89c8e4fbd for frr
commit c89c8e4fbdf00950a58a1149281a9071daf70a48
Author: Philippe Guibert <philippe.guibert@6wind.com>
Date: Tue Nov 10 11:47:43 2026 +0100
bgpd: keep the color of evpn routes imported in a vrf
The SR-TE color set by a route-map on EVPN type-5 routes is lost when
these routes are imported in a VRF. With 'set sr-te color 1' applied on
the EVPN routes received from a neighbor, the matching IPv4 or IPv6
routes in the VRF are installed in zebra without color, and do not use
the SR policy of that color.
Since commit 9d23a3a58a, the SR-TE color is stored in the
bgp_path_info_extra structure of the path, and no more in the
attribute. bgp_create_evpn_bgp_path_info() builds the VRF path from the
EVPN path attribute and labels, but does not copy the color from the
EVPN path extra data. install_evpn_route_entry_in_vrf() does not copy
it either when the VRF path is updated, and only compares the
attributes to detect a change, so a color change made by a route-map
is not seen. bgp_path_info_get_srte_color() then only finds the Color
extended community, when present in the attribute.
Fix this by copying the color from the EVPN path when the VRF path is
created or updated, and by comparing the colors to detect a change, as
leak_update() does for the routes leaked between VRFs.
Fixes: 9d23a3a58a ("bgpd: Move srte_color from attr struct to bgp_path_info_extra")
Signed-off-by: Philippe Guibert <philippe.guibert@6wind.com>
diff --git a/bgpd/bgp_evpn.c b/bgpd/bgp_evpn.c
index b09a334e29..bfd8b45aef 100644
--- a/bgpd/bgp_evpn.c
+++ b/bgpd/bgp_evpn.c
@@ -3418,6 +3418,8 @@ bgp_create_evpn_bgp_path_info(struct bgp_path_info *parent_pi,
if (BGP_PATH_INFO_NUM_LABELS(parent_pi))
pi->extra->labels = bgp_labels_intern(parent_pi->extra->labels);
+ bgp_path_info_extra_propagate(pi, parent_pi);
+
bgp_path_info_add(dest, pi);
return pi;
@@ -3573,7 +3575,8 @@ static int install_evpn_route_entry_in_vrf(struct bgp *bgp_vrf,
pi = bgp_create_evpn_bgp_path_info(parent_pi, dest, &attr);
new_pi = true;
} else {
- if (!CHECK_FLAG(pi->flags, BGP_PATH_REMOVED) && attrhash_cmp(pi->attr, &attr)) {
+ if (!CHECK_FLAG(pi->flags, BGP_PATH_REMOVED) && attrhash_cmp(pi->attr, &attr) &&
+ bgp_path_info_extra_same(pi, parent_pi)) {
bgp_dest_unlock_node(dest);
bgp_attr_extra_discard(&attr);
return 0;
@@ -3605,6 +3608,7 @@ static int install_evpn_route_entry_in_vrf(struct bgp *bgp_vrf,
bgp_attr_unintern(&pi->attr);
pi->attr = attr_new;
pi->uptime = monotime(NULL);
+ bgp_path_info_extra_propagate(pi, parent_pi);
}
bgp_dest_set_defer_flag(dest, false);