mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-08-02 13:23:44 +00:00
bgpd: add 'match community-list any' function
There is no match mechanism to match one community from the incoming community-list. Add the 'any' keyword to the 'match route-map' command of communit-list and large-community-list. > match community-list AAA any > match large-community-list AAA any Signed-off-by: Philippe Guibert <philippe.guibert@6wind.com>
This commit is contained in:
parent
3651803221
commit
aa511000e0
@ -735,6 +735,27 @@ bool community_list_exact_match(struct community *com,
|
||||
return false;
|
||||
}
|
||||
|
||||
bool community_list_any_match(struct community *com, struct community_list *list)
|
||||
{
|
||||
struct community_entry *entry;
|
||||
uint32_t val;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < com->size; i++) {
|
||||
val = community_val_get(com, i);
|
||||
|
||||
for (entry = list->head; entry; entry = entry->next) {
|
||||
if (entry->style == COMMUNITY_LIST_STANDARD &&
|
||||
community_include(entry->u.com, val))
|
||||
return entry->direct == COMMUNITY_PERMIT;
|
||||
if ((entry->style == COMMUNITY_LIST_EXPANDED) &&
|
||||
community_regexp_include(entry->reg, com, i))
|
||||
return entry->direct == COMMUNITY_PERMIT;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Delete all permitted communities in the list from com. */
|
||||
struct community *community_list_match_delete(struct community *com,
|
||||
struct community_list *list)
|
||||
@ -922,6 +943,28 @@ int community_list_unset(struct community_list_handler *ch, const char *name,
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool lcommunity_list_any_match(struct lcommunity *lcom,
|
||||
struct community_list *list)
|
||||
{
|
||||
struct community_entry *entry;
|
||||
uint8_t *ptr;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < lcom->size; i++) {
|
||||
ptr = lcom->val + (i * LCOMMUNITY_SIZE);
|
||||
|
||||
for (entry = list->head; entry; entry = entry->next) {
|
||||
if ((entry->style == LARGE_COMMUNITY_LIST_STANDARD) &&
|
||||
lcommunity_include(entry->u.lcom, ptr))
|
||||
return entry->direct == COMMUNITY_PERMIT;
|
||||
if ((entry->style == LARGE_COMMUNITY_LIST_EXPANDED) &&
|
||||
lcommunity_regexp_include(entry->reg, lcom, i))
|
||||
return entry->direct == COMMUNITY_PERMIT;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Delete all permitted large communities in the list from com. */
|
||||
struct lcommunity *lcommunity_list_match_delete(struct lcommunity *lcom,
|
||||
struct community_list *list)
|
||||
|
@ -158,8 +158,12 @@ extern bool community_list_exact_match(struct community *com,
|
||||
struct community_list *list);
|
||||
extern bool lcommunity_list_exact_match(struct lcommunity *lcom,
|
||||
struct community_list *list);
|
||||
extern bool community_list_any_match(struct community *com,
|
||||
struct community_list *list);
|
||||
extern struct community *
|
||||
community_list_match_delete(struct community *com, struct community_list *list);
|
||||
extern bool lcommunity_list_any_match(struct lcommunity *lcom,
|
||||
struct community_list *list);
|
||||
extern struct lcommunity *
|
||||
lcommunity_list_match_delete(struct lcommunity *lcom,
|
||||
struct community_list *list);
|
||||
|
@ -1528,7 +1528,8 @@ static const struct route_map_rule_cmd route_match_aspath_cmd = {
|
||||
struct rmap_community {
|
||||
char *name;
|
||||
uint32_t name_hash;
|
||||
int exact;
|
||||
bool exact;
|
||||
bool any;
|
||||
};
|
||||
|
||||
/* Match function for community match. */
|
||||
@ -1551,6 +1552,12 @@ route_match_community(void *rule, const struct prefix *prefix, void *object)
|
||||
if (community_list_exact_match(
|
||||
bgp_attr_get_community(path->attr), list))
|
||||
return RMAP_MATCH;
|
||||
} else if (rcom->any) {
|
||||
if (!bgp_attr_get_community(path->attr))
|
||||
return RMAP_OKAY;
|
||||
if (community_list_any_match(bgp_attr_get_community(path->attr),
|
||||
list))
|
||||
return RMAP_MATCH;
|
||||
} else {
|
||||
if (community_list_match(bgp_attr_get_community(path->attr),
|
||||
list))
|
||||
@ -1574,10 +1581,15 @@ static void *route_match_community_compile(const char *arg)
|
||||
len = p - arg;
|
||||
rcom->name = XCALLOC(MTYPE_ROUTE_MAP_COMPILED, len + 1);
|
||||
memcpy(rcom->name, arg, len);
|
||||
rcom->exact = 1;
|
||||
p++;
|
||||
if (*p == 'e')
|
||||
rcom->exact = true;
|
||||
else
|
||||
rcom->any = true;
|
||||
} else {
|
||||
rcom->name = XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
|
||||
rcom->exact = 0;
|
||||
rcom->exact = false;
|
||||
rcom->any = false;
|
||||
}
|
||||
|
||||
rcom->name_hash = bgp_clist_hash_key(rcom->name);
|
||||
@ -1637,6 +1649,12 @@ route_match_lcommunity(void *rule, const struct prefix *prefix, void *object)
|
||||
if (lcommunity_list_exact_match(
|
||||
bgp_attr_get_lcommunity(path->attr), list))
|
||||
return RMAP_MATCH;
|
||||
} else if (rcom->any) {
|
||||
if (!bgp_attr_get_lcommunity(path->attr))
|
||||
return RMAP_OKAY;
|
||||
if (lcommunity_list_any_match(bgp_attr_get_lcommunity(path->attr),
|
||||
list))
|
||||
return RMAP_MATCH;
|
||||
} else {
|
||||
if (lcommunity_list_match(bgp_attr_get_lcommunity(path->attr),
|
||||
list))
|
||||
@ -1660,10 +1678,15 @@ static void *route_match_lcommunity_compile(const char *arg)
|
||||
len = p - arg;
|
||||
rcom->name = XCALLOC(MTYPE_ROUTE_MAP_COMPILED, len + 1);
|
||||
memcpy(rcom->name, arg, len);
|
||||
rcom->exact = 1;
|
||||
p++;
|
||||
if (*p == 'e')
|
||||
rcom->exact = true;
|
||||
else
|
||||
rcom->any = true;
|
||||
} else {
|
||||
rcom->name = XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
|
||||
rcom->exact = 0;
|
||||
rcom->exact = false;
|
||||
rcom->any = false;
|
||||
}
|
||||
|
||||
rcom->name_hash = bgp_clist_hash_key(rcom->name);
|
||||
@ -5493,15 +5516,15 @@ DEFUN_YANG(no_match_alias, no_match_alias_cmd, "no match alias [ALIAS_NAME]",
|
||||
return nb_cli_apply_changes(vty, NULL);
|
||||
}
|
||||
|
||||
DEFPY_YANG (match_community,
|
||||
match_community_cmd,
|
||||
"match community <(1-99)|(100-500)|COMMUNITY_LIST_NAME> [exact-match]",
|
||||
MATCH_STR
|
||||
"Match BGP community list\n"
|
||||
"Community-list number (standard)\n"
|
||||
"Community-list number (expanded)\n"
|
||||
"Community-list name\n"
|
||||
"Do exact matching of communities\n")
|
||||
DEFPY_YANG(
|
||||
match_community, match_community_cmd,
|
||||
"match community <(1-99)|(100-500)|COMMUNITY_LIST_NAME> [<exact-match$exact|any$any>]",
|
||||
MATCH_STR "Match BGP community list\n"
|
||||
"Community-list number (standard)\n"
|
||||
"Community-list number (expanded)\n"
|
||||
"Community-list name\n"
|
||||
"Do exact matching of communities\n"
|
||||
"Do matching of any community\n")
|
||||
{
|
||||
const char *xpath =
|
||||
"./match-condition[condition='frr-bgp-route-map:match-community']";
|
||||
@ -5517,35 +5540,35 @@ DEFPY_YANG (match_community,
|
||||
xpath);
|
||||
nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, argv[idx_comm_list]->arg);
|
||||
|
||||
if (argc == 4) {
|
||||
snprintf(
|
||||
xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
snprintf(xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
if (exact)
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY,
|
||||
"true");
|
||||
} else {
|
||||
snprintf(
|
||||
xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY,
|
||||
"false");
|
||||
}
|
||||
else
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "false");
|
||||
|
||||
snprintf(xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any",
|
||||
xpath);
|
||||
if (any)
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "true");
|
||||
else
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "false");
|
||||
|
||||
return nb_cli_apply_changes(vty, NULL);
|
||||
}
|
||||
|
||||
DEFUN_YANG (no_match_community,
|
||||
no_match_community_cmd,
|
||||
"no match community [<(1-99)|(100-500)|COMMUNITY_LIST_NAME> [exact-match]]",
|
||||
NO_STR
|
||||
MATCH_STR
|
||||
"Match BGP community list\n"
|
||||
"Community-list number (standard)\n"
|
||||
"Community-list number (expanded)\n"
|
||||
"Community-list name\n"
|
||||
"Do exact matching of communities\n")
|
||||
DEFUN_YANG(
|
||||
no_match_community, no_match_community_cmd,
|
||||
"no match community [<(1-99)|(100-500)|COMMUNITY_LIST_NAME> [<exact-match$exact|any$any>]]",
|
||||
NO_STR MATCH_STR "Match BGP community list\n"
|
||||
"Community-list number (standard)\n"
|
||||
"Community-list number (expanded)\n"
|
||||
"Community-list name\n"
|
||||
"Do exact matching of communities\n"
|
||||
"Do matching of any community\n")
|
||||
{
|
||||
const char *xpath =
|
||||
"./match-condition[condition='frr-bgp-route-map:match-community']";
|
||||
@ -5554,15 +5577,15 @@ DEFUN_YANG (no_match_community,
|
||||
return nb_cli_apply_changes(vty, NULL);
|
||||
}
|
||||
|
||||
DEFPY_YANG (match_lcommunity,
|
||||
match_lcommunity_cmd,
|
||||
"match large-community <(1-99)|(100-500)|LCOMMUNITY_LIST_NAME> [exact-match]",
|
||||
MATCH_STR
|
||||
"Match BGP large community list\n"
|
||||
"Large Community-list number (standard)\n"
|
||||
"Large Community-list number (expanded)\n"
|
||||
"Large Community-list name\n"
|
||||
"Do exact matching of communities\n")
|
||||
DEFPY_YANG(
|
||||
match_lcommunity, match_lcommunity_cmd,
|
||||
"match large-community <(1-99)|(100-500)|LCOMMUNITY_LIST_NAME> [<exact-match$exact|any$any>]",
|
||||
MATCH_STR "Match BGP large community list\n"
|
||||
"Large Community-list number (standard)\n"
|
||||
"Large Community-list number (expanded)\n"
|
||||
"Large Community-list name\n"
|
||||
"Do exact matching of communities\n"
|
||||
"Do matching of any community\n")
|
||||
{
|
||||
const char *xpath =
|
||||
"./match-condition[condition='frr-bgp-route-map:match-large-community']";
|
||||
@ -5578,35 +5601,35 @@ DEFPY_YANG (match_lcommunity,
|
||||
xpath);
|
||||
nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, argv[idx_lcomm_list]->arg);
|
||||
|
||||
if (argc == 4) {
|
||||
snprintf(
|
||||
xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
snprintf(xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
if (exact)
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY,
|
||||
"true");
|
||||
} else {
|
||||
snprintf(
|
||||
xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match",
|
||||
xpath);
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY,
|
||||
"false");
|
||||
}
|
||||
else
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "false");
|
||||
|
||||
snprintf(xpath_match, sizeof(xpath_match),
|
||||
"%s/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any",
|
||||
xpath);
|
||||
if (any)
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "true");
|
||||
else
|
||||
nb_cli_enqueue_change(vty, xpath_match, NB_OP_MODIFY, "false");
|
||||
|
||||
return nb_cli_apply_changes(vty, NULL);
|
||||
}
|
||||
|
||||
DEFUN_YANG (no_match_lcommunity,
|
||||
no_match_lcommunity_cmd,
|
||||
"no match large-community [<(1-99)|(100-500)|LCOMMUNITY_LIST_NAME> [exact-match]]",
|
||||
NO_STR
|
||||
MATCH_STR
|
||||
"Match BGP large community list\n"
|
||||
"Large Community-list number (standard)\n"
|
||||
"Large Community-list number (expanded)\n"
|
||||
"Large Community-list name\n"
|
||||
"Do exact matching of communities\n")
|
||||
DEFUN_YANG(
|
||||
no_match_lcommunity, no_match_lcommunity_cmd,
|
||||
"no match large-community [<(1-99)|(100-500)|LCOMMUNITY_LIST_NAME> [<exact-match|any>]]",
|
||||
NO_STR MATCH_STR "Match BGP large community list\n"
|
||||
"Large Community-list number (standard)\n"
|
||||
"Large Community-list number (expanded)\n"
|
||||
"Large Community-list name\n"
|
||||
"Do exact matching of communities\n"
|
||||
"Do matching of any community\n")
|
||||
{
|
||||
const char *xpath =
|
||||
"./match-condition[condition='frr-bgp-route-map:match-large-community']";
|
||||
|
@ -164,6 +164,13 @@ const struct frr_yang_module_info frr_bgp_route_map_info = {
|
||||
.destroy = lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_exact_match_destroy,
|
||||
}
|
||||
},
|
||||
{
|
||||
.xpath = "/frr-route-map:lib/route-map/entry/match-condition/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any",
|
||||
.cbs = {
|
||||
.modify = lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_modify,
|
||||
.destroy = lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_destroy,
|
||||
}
|
||||
},
|
||||
{
|
||||
.xpath = "/frr-route-map:lib/route-map/entry/match-condition/rmap-match-condition/frr-bgp-route-map:ipv4-address",
|
||||
.cbs = {
|
||||
|
@ -65,6 +65,10 @@ int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_destroy(struct nb_cb_destroy_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_exact_match_modify(struct nb_cb_modify_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_exact_match_destroy(struct nb_cb_destroy_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_modify(
|
||||
struct nb_cb_modify_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_destroy(
|
||||
struct nb_cb_destroy_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_ipv4_address_modify(struct nb_cb_modify_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_ipv4_address_destroy(struct nb_cb_destroy_args *args);
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_ipv6_address_modify(struct nb_cb_modify_args *args);
|
||||
|
@ -1127,6 +1127,7 @@ lib_route_map_entry_match_condition_rmap_match_condition_comm_list_finish(
|
||||
struct routemap_hook_context *rhc;
|
||||
const char *value;
|
||||
bool exact_match = false;
|
||||
bool any = false;
|
||||
char *argstr;
|
||||
const char *condition;
|
||||
route_map_event_t event;
|
||||
@ -1140,12 +1141,21 @@ lib_route_map_entry_match_condition_rmap_match_condition_comm_list_finish(
|
||||
exact_match = yang_dnode_get_bool(
|
||||
args->dnode, "./comm-list-name-exact-match");
|
||||
|
||||
if (yang_dnode_exists(args->dnode, "./comm-list-name-any"))
|
||||
any = yang_dnode_get_bool(args->dnode, "./comm-list-name-any");
|
||||
|
||||
if (exact_match) {
|
||||
argstr = XMALLOC(MTYPE_ROUTE_MAP_COMPILED,
|
||||
strlen(value) + strlen("exact-match") + 2);
|
||||
|
||||
snprintf(argstr, (strlen(value) + strlen("exact-match") + 2),
|
||||
"%s exact-match", value);
|
||||
} else if (any) {
|
||||
argstr = XMALLOC(MTYPE_ROUTE_MAP_COMPILED,
|
||||
strlen(value) + strlen("any") + 2);
|
||||
|
||||
snprintf(argstr, (strlen(value) + strlen("any") + 2), "%s any",
|
||||
value);
|
||||
} else
|
||||
argstr = (char *)value;
|
||||
|
||||
@ -1217,6 +1227,39 @@ lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_nam
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
* XPath:
|
||||
* /frr-route-map:lib/route-map/entry/match-condition/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any
|
||||
*/
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_modify(
|
||||
struct nb_cb_modify_args *args)
|
||||
{
|
||||
switch (args->event) {
|
||||
case NB_EV_VALIDATE:
|
||||
case NB_EV_PREPARE:
|
||||
case NB_EV_ABORT:
|
||||
case NB_EV_APPLY:
|
||||
break;
|
||||
}
|
||||
|
||||
return NB_OK;
|
||||
}
|
||||
|
||||
int lib_route_map_entry_match_condition_rmap_match_condition_comm_list_comm_list_name_any_destroy(
|
||||
struct nb_cb_destroy_args *args)
|
||||
{
|
||||
switch (args->event) {
|
||||
case NB_EV_VALIDATE:
|
||||
case NB_EV_PREPARE:
|
||||
case NB_EV_ABORT:
|
||||
break;
|
||||
case NB_EV_APPLY:
|
||||
return lib_route_map_entry_match_destroy(args);
|
||||
}
|
||||
|
||||
return NB_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* XPath: /frr-route-map:lib/route-map/entry/match-condition/rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match
|
||||
*/
|
||||
|
@ -729,6 +729,10 @@ void route_map_condition_show(struct vty *vty, const struct lyd_node *dnode,
|
||||
dnode,
|
||||
"./rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match"))
|
||||
vty_out(vty, " exact-match");
|
||||
if (yang_dnode_get_bool(
|
||||
dnode,
|
||||
"./rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any"))
|
||||
vty_out(vty, " any");
|
||||
vty_out(vty, "\n");
|
||||
} else if (IS_MATCH_LCOMMUNITY(condition)) {
|
||||
vty_out(vty, " match large-community %s",
|
||||
@ -739,6 +743,10 @@ void route_map_condition_show(struct vty *vty, const struct lyd_node *dnode,
|
||||
dnode,
|
||||
"./rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-exact-match"))
|
||||
vty_out(vty, " exact-match");
|
||||
if (yang_dnode_get_bool(
|
||||
dnode,
|
||||
"./rmap-match-condition/frr-bgp-route-map:comm-list/comm-list-name-any"))
|
||||
vty_out(vty, " any");
|
||||
vty_out(vty, "\n");
|
||||
} else if (IS_MATCH_EXTCOMMUNITY(condition)) {
|
||||
vty_out(vty, " match extcommunity %s\n",
|
||||
|
@ -11,6 +11,7 @@ router bgp 65001
|
||||
!
|
||||
ip prefix-list p1 seq 5 permit 172.16.255.1/32
|
||||
ip prefix-list p3 seq 5 permit 172.16.255.3/32
|
||||
ip prefix-list p4 seq 5 permit 172.16.255.4/32
|
||||
!
|
||||
route-map r2 permit 10
|
||||
match ip address prefix-list p1
|
||||
@ -19,5 +20,9 @@ route-map r2 permit 20
|
||||
match ip address prefix-list p3
|
||||
set community 65001:3
|
||||
route-map r2 permit 30
|
||||
match ip address prefix-list p4
|
||||
set community 65001:10 65001:12 65001:13
|
||||
exit
|
||||
route-map r2 permit 40
|
||||
exit
|
||||
!
|
||||
|
@ -3,6 +3,7 @@ interface lo
|
||||
ip address 172.16.255.1/32
|
||||
ip address 172.16.255.2/32
|
||||
ip address 172.16.255.3/32
|
||||
ip address 172.16.255.4/32
|
||||
!
|
||||
interface r1-eth0
|
||||
ip address 192.168.0.1/24
|
||||
|
@ -6,6 +6,9 @@ router bgp 65002
|
||||
neighbor 192.168.0.1 remote-as external
|
||||
neighbor 192.168.0.1 timers 1 3
|
||||
neighbor 192.168.0.1 timers connect 1
|
||||
neighbor 192.168.1.3 remote-as external
|
||||
neighbor 192.168.1.3 timers 1 3
|
||||
neighbor 192.168.1.3 timers connect 1
|
||||
address-family ipv4
|
||||
neighbor 192.168.0.1 route-map r1 in
|
||||
neighbor 192.168.0.1 soft-reconfiguration inbound
|
||||
|
@ -2,5 +2,8 @@
|
||||
interface r2-eth0
|
||||
ip address 192.168.0.2/24
|
||||
!
|
||||
interface r2-eth1
|
||||
ip address 192.168.1.2/24
|
||||
!
|
||||
ip forwarding
|
||||
!
|
||||
|
21
tests/topotests/bgp_comm_list_match/r3/bgpd.conf
Normal file
21
tests/topotests/bgp_comm_list_match/r3/bgpd.conf
Normal file
@ -0,0 +1,21 @@
|
||||
!
|
||||
!debug bgp updates
|
||||
!
|
||||
router bgp 65003
|
||||
no bgp ebgp-requires-policy
|
||||
neighbor 192.168.1.2 remote-as external
|
||||
neighbor 192.168.1.2 timers 1 3
|
||||
neighbor 192.168.1.2 timers connect 1
|
||||
address-family ipv4
|
||||
neighbor 192.168.1.2 route-map r1 in
|
||||
neighbor 192.168.1.2 soft-reconfiguration inbound
|
||||
exit-address-family
|
||||
!
|
||||
bgp community-list 2 seq 10 permit 65001:12
|
||||
!
|
||||
route-map r1 deny 10
|
||||
match community 2 any
|
||||
exit
|
||||
route-map r1 permit 20
|
||||
exit
|
||||
!
|
6
tests/topotests/bgp_comm_list_match/r3/zebra.conf
Normal file
6
tests/topotests/bgp_comm_list_match/r3/zebra.conf
Normal file
@ -0,0 +1,6 @@
|
||||
!
|
||||
interface r3-eth0
|
||||
ip address 192.168.1.3/24
|
||||
!
|
||||
ip forwarding
|
||||
!
|
@ -39,12 +39,15 @@ pytestmark = [pytest.mark.bgpd]
|
||||
|
||||
|
||||
def build_topo(tgen):
|
||||
for routern in range(1, 3):
|
||||
for routern in range(1, 4):
|
||||
tgen.add_router("r{}".format(routern))
|
||||
|
||||
switch = tgen.add_switch("s1")
|
||||
switch.add_link(tgen.gears["r1"])
|
||||
switch.add_link(tgen.gears["r2"])
|
||||
switch = tgen.add_switch("s2")
|
||||
switch.add_link(tgen.gears["r3"])
|
||||
switch.add_link(tgen.gears["r2"])
|
||||
|
||||
|
||||
def setup_module(mod):
|
||||
@ -95,12 +98,41 @@ def test_bgp_comm_list_match():
|
||||
}
|
||||
return topotest.json_cmp(output, expected)
|
||||
|
||||
step("Initial BGP converge")
|
||||
step("Initial BGP converge between R1 and R2")
|
||||
test_func = functools.partial(_bgp_converge)
|
||||
_, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5)
|
||||
assert result is None, "Failed to filter BGP UPDATES with community-list on R2"
|
||||
|
||||
|
||||
def test_bgp_comm_list_match_any():
|
||||
tgen = get_topogen()
|
||||
|
||||
if tgen.routers_have_failure():
|
||||
pytest.skip(tgen.errors)
|
||||
|
||||
router = tgen.gears["r3"]
|
||||
|
||||
def _bgp_converge():
|
||||
output = json.loads(
|
||||
router.vtysh_cmd(
|
||||
"show bgp ipv4 unicast neighbors 192.168.1.2 filtered-routes json"
|
||||
)
|
||||
)
|
||||
expected = {
|
||||
"receivedRoutes": {
|
||||
"172.16.255.4/32": {
|
||||
"path": "65002 65001",
|
||||
},
|
||||
}
|
||||
}
|
||||
return topotest.json_cmp(output, expected)
|
||||
|
||||
step("Initial BGP converge between R3 and R2")
|
||||
test_func = functools.partial(_bgp_converge)
|
||||
_, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5)
|
||||
assert result is None, "Failed to filter BGP UPDATES with community-list on R3"
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
args = ["-s"] + sys.argv[1:]
|
||||
sys.exit(pytest.main(args))
|
||||
|
@ -777,6 +777,13 @@ identity set-extcommunity-color {
|
||||
description
|
||||
"Do exact matching of communities";
|
||||
}
|
||||
|
||||
leaf comm-list-name-any {
|
||||
type boolean;
|
||||
description
|
||||
"Do matching of any community";
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user