diff options
author | Madhuri Kuruganti <k.madhuri@samsung.com> | 2020-10-07 14:10:00 +0200 |
---|---|---|
committer | Madhuri Kuruganti <k.madhuri@samsung.com> | 2020-10-27 11:45:36 +0100 |
commit | cf2ad4d8a6d72885aff7487dffc68cfad65b9a07 (patch) | |
tree | e3d4178c056292315eb904db6f0c17e07dd297d2 | |
parent | bgpd: conditional advertisement - other match rules support (diff) | |
download | frr-cf2ad4d8a6d72885aff7487dffc68cfad65b9a07.tar.xz frr-cf2ad4d8a6d72885aff7487dffc68cfad65b9a07.zip |
bgpd: conditional advertisement - comments addressed
Signed-off-by: Madhuri Kuruganti <k.madhuri@samsung.com>
-rw-r--r-- | bgpd/bgp_conditional_adv.c | 2 | ||||
-rw-r--r-- | bgpd/bgp_route.c | 1 | ||||
-rw-r--r-- | bgpd/bgp_vty.c | 106 | ||||
-rw-r--r-- | bgpd/bgpd.c | 186 | ||||
-rw-r--r-- | bgpd/bgpd.h | 26 |
5 files changed, 126 insertions, 195 deletions
diff --git a/bgpd/bgp_conditional_adv.c b/bgpd/bgp_conditional_adv.c index 999326d9c..89ee71df8 100644 --- a/bgpd/bgp_conditional_adv.c +++ b/bgpd/bgp_conditional_adv.c @@ -54,7 +54,7 @@ bgp_check_rmap_prefixes_in_bgp_table(struct bgp_table *table, static void bgp_conditional_adv_routes(struct peer *peer, afi_t afi, safi_t safi, struct bgp_table *table, struct route_map *rmap, - enum advertise advertise) + enum update_type advertise) { int addpath_capable; const struct prefix *dest_p; diff --git a/bgpd/bgp_route.c b/bgpd/bgp_route.c index 1b611ebe7..307453147 100644 --- a/bgpd/bgp_route.c +++ b/bgpd/bgp_route.c @@ -2039,6 +2039,7 @@ bool subgroup_announce_check(struct bgp_dest *dest, struct bgp_path_info *pi, || CONDITION_MAP_NAME(filter)) { struct peer *temp_peer; struct listnode *temp_node, *temp_nnode = NULL; + for (ALL_LIST_ELEMENTS(bgp->peer, temp_node, temp_nnode, temp_peer)) { if (!CHECK_FLAG(peer->flags, diff --git a/bgpd/bgp_vty.c b/bgpd/bgp_vty.c index 5bfda7d57..765d27c24 100644 --- a/bgpd/bgp_vty.c +++ b/bgpd/bgp_vty.c @@ -7046,8 +7046,9 @@ ALIAS_HIDDEN(no_neighbor_filter_list, no_neighbor_filter_list_hidden_cmd, /* Set advertise-map to the peer. */ static int peer_advertise_map_set_vty(struct vty *vty, const char *ip_str, afi_t afi, safi_t safi, - const char *advertise_str, bool condition, - const char *condition_str) + const char *advertise_str, + const char *condition_str, bool condition, + bool set) { int ret = CMD_WARNING_CONFIG_FAILED; struct peer *peer; @@ -7061,42 +7062,22 @@ static int peer_advertise_map_set_vty(struct vty *vty, const char *ip_str, condition_map = route_map_lookup_warn_noexist(vty, condition_str); advertise_map = route_map_lookup_warn_noexist(vty, advertise_str); - ret = peer_advertise_map_set(peer, afi, safi, advertise_str, - advertise_map, condition, condition_str, - condition_map); - - return bgp_vty_return(vty, ret); -} - -static int peer_advertise_map_unset_vty(struct vty *vty, const char *ip_str, - afi_t afi, safi_t safi, - const char *advertise_str, - bool condition, - const char *condition_str) -{ - int ret = CMD_WARNING_CONFIG_FAILED; - struct peer *peer; - struct route_map *advertise_map; - struct route_map *condition_map; - - - peer = peer_and_group_lookup_vty(vty, ip_str); - if (!peer) - return ret; - - condition_map = route_map_lookup_warn_noexist(vty, condition_str); - advertise_map = route_map_lookup_warn_noexist(vty, advertise_str); - - ret = peer_advertise_map_unset(peer, afi, safi, advertise_str, - advertise_map, condition, condition_str, - condition_map); + if (set) + ret = peer_advertise_map_set(peer, afi, safi, advertise_str, + advertise_map, condition_str, + condition_map, condition); + else + ret = peer_advertise_map_unset(peer, afi, safi, advertise_str, + advertise_map, condition_str, + condition_map, condition); return bgp_vty_return(vty, ret); } -DEFUN (neighbor_advertise_map, +DEFPY (neighbor_advertise_map, neighbor_advertise_map_cmd, - "neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", + "[no$no] neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", + NO_STR NEIGHBOR_STR NEIGHBOR_ADDR_STR2 "Route-map to conditionally advertise routes\n" @@ -7112,55 +7093,23 @@ DEFUN (neighbor_advertise_map, int idx_condition_word = 5; bool condition = CONDITION_EXIST; + if (no) { + idx_peer++; + idx_advertise_word++; + idx_condition_word++; + } + if (argv_find(argv, argc, "non-exist-map", &idx)) condition = CONDITION_NON_EXIST; return peer_advertise_map_set_vty( vty, argv[idx_peer]->arg, bgp_node_afi(vty), bgp_node_safi(vty), - argv[idx_advertise_word]->arg, condition, - argv[idx_condition_word]->arg); + argv[idx_advertise_word]->arg, argv[idx_condition_word]->arg, + condition, !no); } ALIAS_HIDDEN(neighbor_advertise_map, neighbor_advertise_map_hidden_cmd, - "neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", - NEIGHBOR_STR NEIGHBOR_ADDR_STR2 - "Route-map to conditionally advertise routes\n" - "Name of advertise map\n" - "Advertise routes only if prefixes in exist-map are installed in BGP table\n" - "Name of the exist map\n" - "Advertise routes only if prefixes in non-exist-map are not installed in BGP table\n" - "Name of the non exist map\n") - -DEFUN (no_neighbor_advertise_map, - no_neighbor_advertise_map_cmd, - "no neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", - NO_STR - NEIGHBOR_STR - NEIGHBOR_ADDR_STR2 - "Route-map to conditionally advertise routes\n" - "Name of advertise map\n" - "Advertise routes only if prefixes in exist-map are installed in BGP table\n" - "Name of the exist map\n" - "Advertise routes only if prefixes in non-exist-map are not installed in BGP table\n" - "Name of the non exist map\n") -{ - int idx = 0; - int idx_peer = 2; - int idx_advertise_word = 4; - int idx_condition_word = 6; - bool condition = CONDITION_EXIST; - - if (argv_find(argv, argc, "non-exist-map", &idx)) - condition = CONDITION_NON_EXIST; - - return peer_advertise_map_unset_vty( - vty, argv[idx_peer]->arg, bgp_node_afi(vty), bgp_node_safi(vty), - argv[idx_advertise_word]->arg, condition, - argv[idx_condition_word]->arg); -} - -ALIAS_HIDDEN(no_neighbor_advertise_map, no_neighbor_advertise_map_hidden_cmd, - "no neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", + "[no$no] neighbor <A.B.C.D|X:X::X:X|WORD> advertise-map WORD <exist-map WORD|non-exist-map WORD>", NO_STR NEIGHBOR_STR NEIGHBOR_ADDR_STR2 "Route-map to conditionally advertise routes\n" "Name of advertise map\n" @@ -17543,23 +17492,14 @@ void bgp_vty_init(void) /* "neighbor advertise-map" commands. */ install_element(BGP_NODE, &neighbor_advertise_map_hidden_cmd); - install_element(BGP_NODE, &no_neighbor_advertise_map_hidden_cmd); install_element(BGP_IPV4_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV4_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_IPV4M_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV4M_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_IPV4L_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV4L_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_IPV6_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV6_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_IPV6M_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV6M_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_IPV6L_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_IPV6L_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_VPNV4_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_VPNV4_NODE, &no_neighbor_advertise_map_cmd); install_element(BGP_VPNV6_NODE, &neighbor_advertise_map_cmd); - install_element(BGP_VPNV6_NODE, &no_neighbor_advertise_map_cmd); /* neighbor maximum-prefix-out commands. */ install_element(BGP_NODE, &neighbor_maximum_prefix_out_cmd); diff --git a/bgpd/bgpd.c b/bgpd/bgpd.c index 194049f01..fd4595274 100644 --- a/bgpd/bgpd.c +++ b/bgpd/bgpd.c @@ -6586,6 +6586,59 @@ int peer_unsuppress_map_unset(struct peer *peer, afi_t afi, safi_t safi) return 0; } +static void peer_update_rmap_filter_data(struct peer *peer, afi_t afi, + safi_t safi, const char *rmap_name1, + struct route_map *rmap1, + const char *rmap_name2, + struct route_map *rmap2, + uint8_t config_flags) +{ + struct bgp_filter *filter; + bool filter_exists = false; + + filter = &peer->filter[afi][safi]; + + if (CHECK_FLAG(config_flags, BGP_PEER_ADVERTISE_MAP)) { + /* advertise-map is already configured. */ + if (filter->advmap.aname) { + filter_exists = true; + XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.aname); + XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.cname); + } + route_map_counter_decrement(filter->advmap.amap); + + /* Removed advertise-map configuration */ + if (!CHECK_FLAG(config_flags, BGP_PEER_RMAP_SET)) { + memset(filter, 0, sizeof(struct bgp_filter)); + + /* decrement condition_filter_count delete timer if last + * one */ + if (filter_exists) + bgp_conditional_adv_disable(peer, afi, safi); + + return; + } + + /* Update filter data with newly configured values. */ + filter->advmap.aname = + XSTRDUP(MTYPE_BGP_FILTER_NAME, rmap_name1); + filter->advmap.cname = + XSTRDUP(MTYPE_BGP_FILTER_NAME, rmap_name2); + filter->advmap.amap = rmap1; + filter->advmap.cmap = rmap2; + filter->advmap.condition = + CHECK_FLAG(config_flags, BGP_PEER_CONDITION_EXIST); + route_map_counter_increment(filter->advmap.amap); + peer->advmap_config_change[afi][safi] = true; + + /* Increment condition_filter_count and/or create timer. */ + if (!filter_exists) { + filter->advmap.advertise = ADVERTISE; + bgp_conditional_adv_enable(peer, afi, safi); + } + } +} + /* Set advertise-map to the peer but do not process peer route updates here. * * Hold filter changes until the conditional routes polling thread is called * * AS we need to advertise/withdraw prefixes (in advertise-map) based on the * @@ -6595,50 +6648,29 @@ int peer_unsuppress_map_unset(struct peer *peer, afi_t afi, safi_t safi) */ int peer_advertise_map_set(struct peer *peer, afi_t afi, safi_t safi, const char *advertise_name, - struct route_map *advertise_map, bool condition, + struct route_map *advertise_map, const char *condition_name, - struct route_map *condition_map) + struct route_map *condition_map, bool condition) { - bool filter_exists = false; + uint8_t config_flags = 0; struct peer *member; - struct bgp_filter *filter; struct listnode *node, *nnode; - /* Set configuration on peer. */ - filter = &peer->filter[afi][safi]; - - if (filter->advmap.aname) { - /* advertise-map filter is already configured on this peer */ - filter_exists = true; + SET_FLAG(config_flags, BGP_PEER_RMAP_SET); + SET_FLAG(config_flags, BGP_PEER_ADVERTISE_MAP); + if (condition) + SET_FLAG(config_flags, BGP_PEER_CONDITION_EXIST); - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.aname); - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.cname); - filter->advmap.condition = CONDITION_NON_EXIST; - } - - route_map_counter_decrement(filter->advmap.amap); - filter->advmap.aname = XSTRDUP(MTYPE_BGP_FILTER_NAME, advertise_name); - filter->advmap.cname = XSTRDUP(MTYPE_BGP_FILTER_NAME, condition_name); - filter->advmap.amap = advertise_map; - filter->advmap.cmap = condition_map; - filter->advmap.condition = condition; - route_map_counter_increment(advertise_map); - peer->advmap_config_change[afi][safi] = true; + /* Set configuration on peer. */ + peer_update_rmap_filter_data(peer, afi, safi, advertise_name, + advertise_map, condition_name, + condition_map, config_flags); - /* Check if handling a regular peer. */ + /* Check if handling a regular peer & Skip peer-group mechanics. */ if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) { /* Set override-flag and process peer route updates. */ SET_FLAG(peer->filter_override[afi][safi][RMAP_OUT], PEER_FT_ADVERTISE_MAP); - - /* Hold peer_on_policy_change() until timer thread is called. - * Increment condition_filter_count and/or create timer. - */ - if (!filter_exists) { - filter->advmap.advertise = ADVERTISE; - bgp_conditional_adv_enable(peer, afi, safi); - } - /* Skip peer-group mechanics for regular peers. */ return 0; } @@ -6653,31 +6685,9 @@ int peer_advertise_map_set(struct peer *peer, afi_t afi, safi_t safi, continue; /* Set configuration on peer-group member. */ - filter = &member->filter[afi][safi]; - if (filter->advmap.aname) { - /* advertise-map filter is already configured. */ - filter_exists = true; - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.aname); - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.cname); - filter->advmap.condition = CONDITION_NON_EXIST; - } - route_map_counter_decrement(filter->advmap.amap); - filter->advmap.aname = - XSTRDUP(MTYPE_BGP_FILTER_NAME, advertise_name); - filter->advmap.amap = advertise_map; - filter->advmap.cname = - XSTRDUP(MTYPE_BGP_FILTER_NAME, condition_name); - filter->advmap.cmap = condition_map; - filter->advmap.condition = condition; - route_map_counter_increment(advertise_map); - - /* Hold peer_on_policy_change() until timer thread is called. - * Increment condition_filter_count, create timer if 1st one - */ - if (!filter_exists) { - filter->advmap.advertise = ADVERTISE; - bgp_conditional_adv_enable(member, afi, safi); - } + peer_update_rmap_filter_data(member, afi, safi, advertise_name, + advertise_map, condition_name, + condition_map, config_flags); } return 0; @@ -6686,15 +6696,18 @@ int peer_advertise_map_set(struct peer *peer, afi_t afi, safi_t safi, /* Unset advertise-map from the peer. */ int peer_advertise_map_unset(struct peer *peer, afi_t afi, safi_t safi, const char *advertise_name, - struct route_map *advertise_map, bool condition, + struct route_map *advertise_map, const char *condition_name, - struct route_map *condition_map) + struct route_map *condition_map, bool condition) { - bool filter_exists = false; + uint8_t config_flags = 0; struct peer *member; - struct bgp_filter *filter; struct listnode *node, *nnode; + SET_FLAG(config_flags, BGP_PEER_ADVERTISE_MAP); + if (condition) + SET_FLAG(config_flags, BGP_PEER_CONDITION_EXIST); + /* Unset override-flag unconditionally. */ UNSET_FLAG(peer->filter_override[afi][safi][RMAP_OUT], PEER_FT_ADVERTISE_MAP); @@ -6706,33 +6719,15 @@ int peer_advertise_map_unset(struct peer *peer, afi_t afi, safi_t safi, MTYPE_BGP_FILTER_NAME); PEER_ATTR_INHERIT(peer, peer->group, filter[afi][safi].advmap.amap); - } else { - /* Otherwise remove configuration from peer. */ - filter = &peer->filter[afi][safi]; - if (filter->advmap.aname) { - /* advertise-map filter is already configured. */ - filter_exists = true; - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.aname); - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.cname); - } - route_map_counter_decrement(filter->advmap.amap); - filter->advmap.aname = NULL; - filter->advmap.amap = NULL; - filter->advmap.cname = NULL; - filter->advmap.cmap = NULL; - filter->advmap.condition = CONDITION_NON_EXIST; - } + } else + peer_update_rmap_filter_data(peer, afi, safi, advertise_name, + advertise_map, condition_name, + condition_map, config_flags); - /* Check if handling a regular peer. */ + /* Check if handling a regular peer and skip peer-group mechanics. */ if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) { /* Process peer route updates. */ peer_on_policy_change(peer, afi, safi, 1); - - /* decrement condition_filter_count delete timer if last one */ - if (filter_exists) - bgp_conditional_adv_disable(peer, afi, safi); - - /* Skip peer-group mechanics for regular peers. */ return 0; } @@ -6745,25 +6740,10 @@ int peer_advertise_map_unset(struct peer *peer, afi_t afi, safi_t safi, if (CHECK_FLAG(member->filter_override[afi][safi][RMAP_OUT], PEER_FT_ADVERTISE_MAP)) continue; - /* Remove configuration on peer-group member. */ - filter = &member->filter[afi][safi]; - if (filter->advmap.aname) { - /* advertise-map filter is already configured. */ - filter_exists = true; - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.aname); - XFREE(MTYPE_BGP_FILTER_NAME, filter->advmap.cname); - } - route_map_counter_decrement(filter->advmap.amap); - filter->advmap.aname = NULL; - filter->advmap.amap = NULL; - filter->advmap.cname = NULL; - filter->advmap.cmap = NULL; - filter->advmap.condition = CONDITION_NON_EXIST; - - /* decrement condition_filter_count delete timer if last one */ - if (filter_exists) - bgp_conditional_adv_disable(peer, afi, safi); + peer_update_rmap_filter_data(member, afi, safi, advertise_name, + advertise_map, condition_name, + condition_map, config_flags); /* Process peer route updates. */ peer_on_policy_change(member, afi, safi, 1); diff --git a/bgpd/bgpd.h b/bgpd/bgpd.h index 05fe2330b..39efab289 100644 --- a/bgpd/bgpd.h +++ b/bgpd/bgpd.h @@ -764,10 +764,18 @@ struct bgp_nexthop { #define BGP_GTSM_HOPS_CONNECTED 1 /* Advertise map */ -#define CONDITION_NON_EXIST false -#define CONDITION_EXIST true +#define CONDITION_NON_EXIST false +#define CONDITION_EXIST true -enum advertise { WITHDRAW, ADVERTISE }; +/* BGP peer RMAP options */ +#define BGP_PEER_ADVERTISE_MAP (1 << 0) +#define BGP_PEER_ROUTE_MAP (1 << 1) +#define BGP_PEER_UNSUPPRESS_MAP (1 << 2) +#define BGP_PEER_CONDITION_EXIST (1 << 3) +#define BGP_PEER_RMAP_DIRECTION (1 << 4) +#define BGP_PEER_RMAP_SET (1 << 5) + +enum update_type { WITHDRAW, ADVERTISE }; #include "filter.h" @@ -813,7 +821,7 @@ struct bgp_filter { char *cname; struct route_map *cmap; - enum advertise advertise; + enum update_type advertise; } advmap; }; @@ -1970,8 +1978,9 @@ extern int peer_unsuppress_map_set(struct peer *peer, afi_t afi, safi_t safi, extern int peer_advertise_map_set(struct peer *peer, afi_t afi, safi_t safi, const char *advertise_name, struct route_map *advertise_map, - bool condition, const char *condition_name, - struct route_map *condition_map); + const char *condition_name, + struct route_map *condition_map, + bool condition); extern int peer_password_set(struct peer *, const char *); extern int peer_password_unset(struct peer *); @@ -1981,8 +1990,9 @@ extern int peer_unsuppress_map_unset(struct peer *, afi_t, safi_t); extern int peer_advertise_map_unset(struct peer *peer, afi_t afi, safi_t safi, const char *advertise_name, struct route_map *advertise_map, - bool condition, const char *condition_name, - struct route_map *condition_map); + const char *condition_name, + struct route_map *condition_map, + bool condition); extern int peer_maximum_prefix_set(struct peer *, afi_t, safi_t, uint32_t, uint8_t, int, uint16_t, bool force); |