mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-07-27 13:46:45 +00:00
Merge pull request #17652 from pguibert6WIND/topotest_bgp_evpn_rt5
bgpd, tests: bgp_evpn_rt5, add test with match evpn vni command
This commit is contained in:
commit
f19b843e9e
@ -4923,6 +4923,7 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
bool force_evpn_import = false;
|
bool force_evpn_import = false;
|
||||||
safi_t orig_safi = safi;
|
safi_t orig_safi = safi;
|
||||||
struct bgp_labels bgp_labels = {};
|
struct bgp_labels bgp_labels = {};
|
||||||
|
struct bgp_route_evpn *p_evpn = evpn;
|
||||||
uint8_t i;
|
uint8_t i;
|
||||||
|
|
||||||
if (frrtrace_enabled(frr_bgp, process_update)) {
|
if (frrtrace_enabled(frr_bgp, process_update)) {
|
||||||
@ -4964,11 +4965,9 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
* will not be interned. In which case, it is ok to update the
|
* will not be interned. In which case, it is ok to update the
|
||||||
* attr->evpn_overlay, so that, this can be stored in adj_in.
|
* attr->evpn_overlay, so that, this can be stored in adj_in.
|
||||||
*/
|
*/
|
||||||
if (evpn) {
|
if (evpn && afi == AFI_L2VPN) {
|
||||||
if (afi == AFI_L2VPN)
|
|
||||||
bgp_attr_set_evpn_overlay(attr, evpn);
|
bgp_attr_set_evpn_overlay(attr, evpn);
|
||||||
else
|
p_evpn = NULL;
|
||||||
evpn_overlay_free(evpn);
|
|
||||||
}
|
}
|
||||||
bgp_adj_in_set(dest, peer, attr, addpath_id, &bgp_labels);
|
bgp_adj_in_set(dest, peer, attr, addpath_id, &bgp_labels);
|
||||||
}
|
}
|
||||||
@ -5141,11 +5140,9 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
* attr->evpn_overlay with evpn directly. Instead memcpy
|
* attr->evpn_overlay with evpn directly. Instead memcpy
|
||||||
* evpn to new_atr.evpn_overlay before it is interned.
|
* evpn to new_atr.evpn_overlay before it is interned.
|
||||||
*/
|
*/
|
||||||
if (soft_reconfig && evpn) {
|
if (soft_reconfig && evpn && afi == AFI_L2VPN) {
|
||||||
if (afi == AFI_L2VPN)
|
|
||||||
bgp_attr_set_evpn_overlay(&new_attr, evpn);
|
bgp_attr_set_evpn_overlay(&new_attr, evpn);
|
||||||
else
|
p_evpn = NULL;
|
||||||
evpn_overlay_free(evpn);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Apply incoming route-map.
|
/* Apply incoming route-map.
|
||||||
@ -5314,7 +5311,8 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
|
|
||||||
bgp_dest_unlock_node(dest);
|
bgp_dest_unlock_node(dest);
|
||||||
bgp_attr_unintern(&attr_new);
|
bgp_attr_unintern(&attr_new);
|
||||||
|
if (p_evpn)
|
||||||
|
evpn_overlay_free(p_evpn);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5479,6 +5477,8 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
ret = bgp_damp_update(pi, dest, afi, safi);
|
ret = bgp_damp_update(pi, dest, afi, safi);
|
||||||
if (ret == BGP_DAMP_SUPPRESSED) {
|
if (ret == BGP_DAMP_SUPPRESSED) {
|
||||||
bgp_dest_unlock_node(dest);
|
bgp_dest_unlock_node(dest);
|
||||||
|
if (p_evpn)
|
||||||
|
evpn_overlay_free(p_evpn);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -5565,6 +5565,8 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
type, sub_type, NULL);
|
type, sub_type, NULL);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
if (p_evpn)
|
||||||
|
evpn_overlay_free(p_evpn);
|
||||||
return;
|
return;
|
||||||
} // End of implicit withdraw
|
} // End of implicit withdraw
|
||||||
|
|
||||||
@ -5659,6 +5661,8 @@ void bgp_update(struct peer *peer, const struct prefix *p, uint32_t addpath_id,
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (p_evpn)
|
||||||
|
evpn_overlay_free(p_evpn);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/* This BGP update is filtered. Log the reason then update BGP
|
/* This BGP update is filtered. Log the reason then update BGP
|
||||||
@ -5722,6 +5726,8 @@ filtered:
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (p_evpn)
|
||||||
|
evpn_overlay_free(p_evpn);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1499,13 +1499,12 @@ DEFUN_NOSH (router_bgp,
|
|||||||
int idx_asn = 2;
|
int idx_asn = 2;
|
||||||
int idx_view_vrf = 3;
|
int idx_view_vrf = 3;
|
||||||
int idx_vrf = 4;
|
int idx_vrf = 4;
|
||||||
int is_new_bgp = 0;
|
|
||||||
int idx_asnotation = 3;
|
int idx_asnotation = 3;
|
||||||
int idx_asnotation_kind = 4;
|
int idx_asnotation_kind = 4;
|
||||||
enum asnotation_mode asnotation = ASNOTATION_UNDEFINED;
|
enum asnotation_mode asnotation = ASNOTATION_UNDEFINED;
|
||||||
int ret;
|
int ret;
|
||||||
as_t as;
|
as_t as;
|
||||||
struct bgp *bgp;
|
struct bgp *bgp = NULL;
|
||||||
const char *name = NULL;
|
const char *name = NULL;
|
||||||
enum bgp_instance_type inst_type;
|
enum bgp_instance_type inst_type;
|
||||||
|
|
||||||
@ -1567,35 +1566,40 @@ DEFUN_NOSH (router_bgp,
|
|||||||
asnotation = ASNOTATION_PLAIN;
|
asnotation = ASNOTATION_PLAIN;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (inst_type == BGP_INSTANCE_TYPE_DEFAULT)
|
ret = bgp_lookup_by_as_name_type(&bgp, &as, argv[idx_asn]->arg, asnotation, name,
|
||||||
is_new_bgp = (bgp_lookup(as, name) == NULL);
|
inst_type, true);
|
||||||
|
if (bgp && ret == BGP_INSTANCE_EXISTS)
|
||||||
ret = bgp_get_vty(&bgp, &as, name, inst_type,
|
ret = CMD_SUCCESS;
|
||||||
argv[idx_asn]->arg, asnotation);
|
else if (bgp == NULL && ret == CMD_SUCCESS)
|
||||||
|
/* SUCCESS and bgp is NULL */
|
||||||
|
ret = bgp_get_vty(&bgp, &as, name, inst_type, argv[idx_asn]->arg,
|
||||||
|
asnotation);
|
||||||
switch (ret) {
|
switch (ret) {
|
||||||
case BGP_ERR_AS_MISMATCH:
|
case BGP_ERR_AS_MISMATCH:
|
||||||
vty_out(vty, "BGP is already running; AS is %s\n",
|
vty_out(vty, "BGP is already running; AS is %s\n",
|
||||||
bgp->as_pretty);
|
bgp ? bgp->as_pretty : "unknown");
|
||||||
return CMD_WARNING_CONFIG_FAILED;
|
return CMD_WARNING_CONFIG_FAILED;
|
||||||
case BGP_ERR_INSTANCE_MISMATCH:
|
case BGP_ERR_INSTANCE_MISMATCH:
|
||||||
vty_out(vty,
|
vty_out(vty,
|
||||||
"BGP instance name and AS number mismatch\n");
|
"BGP instance name and AS number mismatch\n");
|
||||||
vty_out(vty,
|
vty_out(vty, "BGP instance is already running; AS is %s\n",
|
||||||
"BGP instance is already running; AS is %s\n",
|
bgp ? bgp->as_pretty : "unknown");
|
||||||
bgp->as_pretty);
|
|
||||||
return CMD_WARNING_CONFIG_FAILED;
|
return CMD_WARNING_CONFIG_FAILED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!bgp) {
|
||||||
|
vty_out(vty, "BGP instance not found\n");
|
||||||
|
return CMD_WARNING_CONFIG_FAILED;
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* If we just instantiated the default instance, complete
|
* If we just instantiated the default instance, complete
|
||||||
* any pending VRF-VPN leaking that was configured via
|
* any pending VRF-VPN leaking that was configured via
|
||||||
* earlier "router bgp X vrf FOO" blocks.
|
* earlier "router bgp X vrf FOO" blocks.
|
||||||
*/
|
*/
|
||||||
if (is_new_bgp && inst_type == BGP_INSTANCE_TYPE_DEFAULT)
|
if (inst_type == BGP_INSTANCE_TYPE_DEFAULT)
|
||||||
vpn_leak_postchange_all();
|
vpn_leak_postchange_all();
|
||||||
|
|
||||||
if (inst_type == BGP_INSTANCE_TYPE_VRF ||
|
if (inst_type == BGP_INSTANCE_TYPE_VRF || IS_BGP_INSTANCE_HIDDEN(bgp)) {
|
||||||
IS_BGP_INSTANCE_HIDDEN(bgp)) {
|
|
||||||
bgp_vpn_leak_export(bgp);
|
bgp_vpn_leak_export(bgp);
|
||||||
UNSET_FLAG(bgp->flags, BGP_FLAG_INSTANCE_HIDDEN);
|
UNSET_FLAG(bgp->flags, BGP_FLAG_INSTANCE_HIDDEN);
|
||||||
UNSET_FLAG(bgp->flags, BGP_FLAG_DELETE_IN_PROGRESS);
|
UNSET_FLAG(bgp->flags, BGP_FLAG_DELETE_IN_PROGRESS);
|
||||||
@ -10559,7 +10563,7 @@ DEFPY(bgp_imexport_vrf, bgp_imexport_vrf_cmd,
|
|||||||
SET_FLAG(bgp_default->flags, BGP_FLAG_INSTANCE_HIDDEN);
|
SET_FLAG(bgp_default->flags, BGP_FLAG_INSTANCE_HIDDEN);
|
||||||
}
|
}
|
||||||
|
|
||||||
vrf_bgp = bgp_lookup_by_name(import_name);
|
vrf_bgp = bgp_lookup_by_name_filter(import_name, false);
|
||||||
if (!vrf_bgp) {
|
if (!vrf_bgp) {
|
||||||
if (strcmp(import_name, VRF_DEFAULT_NAME) == 0) {
|
if (strcmp(import_name, VRF_DEFAULT_NAME) == 0) {
|
||||||
vrf_bgp = bgp_default;
|
vrf_bgp = bgp_default;
|
||||||
|
22
bgpd/bgpd.c
22
bgpd/bgpd.c
@ -3634,13 +3634,13 @@ struct bgp *bgp_lookup(as_t as, const char *name)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Lookup BGP structure by view name. */
|
/* Lookup BGP structure by view name. */
|
||||||
struct bgp *bgp_lookup_by_name(const char *name)
|
struct bgp *bgp_lookup_by_name_filter(const char *name, bool filter_auto)
|
||||||
{
|
{
|
||||||
struct bgp *bgp;
|
struct bgp *bgp;
|
||||||
struct listnode *node, *nnode;
|
struct listnode *node, *nnode;
|
||||||
|
|
||||||
for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
|
for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
|
||||||
if (CHECK_FLAG(bgp->vrf_flags, BGP_VRF_AUTO))
|
if (filter_auto && CHECK_FLAG(bgp->vrf_flags, BGP_VRF_AUTO))
|
||||||
continue;
|
continue;
|
||||||
if ((bgp->name == NULL && name == NULL)
|
if ((bgp->name == NULL && name == NULL)
|
||||||
|| (bgp->name && name && strcmp(bgp->name, name) == 0))
|
|| (bgp->name && name && strcmp(bgp->name, name) == 0))
|
||||||
@ -3649,6 +3649,11 @@ struct bgp *bgp_lookup_by_name(const char *name)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct bgp *bgp_lookup_by_name(const char *name)
|
||||||
|
{
|
||||||
|
return bgp_lookup_by_name_filter(name, true);
|
||||||
|
}
|
||||||
|
|
||||||
/* Lookup BGP instance based on VRF id. */
|
/* Lookup BGP instance based on VRF id. */
|
||||||
/* Note: Only to be used for incoming messages from Zebra. */
|
/* Note: Only to be used for incoming messages from Zebra. */
|
||||||
struct bgp *bgp_lookup_by_vrf_id(vrf_id_t vrf_id)
|
struct bgp *bgp_lookup_by_vrf_id(vrf_id_t vrf_id)
|
||||||
@ -3734,10 +3739,9 @@ int bgp_handle_socket(struct bgp *bgp, struct vrf *vrf, vrf_id_t old_vrf_id,
|
|||||||
return bgp_check_main_socket(create, bgp);
|
return bgp_check_main_socket(create, bgp);
|
||||||
}
|
}
|
||||||
|
|
||||||
int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as,
|
int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as, const char *as_pretty,
|
||||||
const char *as_pretty,
|
|
||||||
enum asnotation_mode asnotation, const char *name,
|
enum asnotation_mode asnotation, const char *name,
|
||||||
enum bgp_instance_type inst_type)
|
enum bgp_instance_type inst_type, bool force_config)
|
||||||
{
|
{
|
||||||
struct bgp *bgp;
|
struct bgp *bgp;
|
||||||
struct peer *peer = NULL;
|
struct peer *peer = NULL;
|
||||||
@ -3746,7 +3750,7 @@ int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as,
|
|||||||
|
|
||||||
/* Multiple instance check. */
|
/* Multiple instance check. */
|
||||||
if (name)
|
if (name)
|
||||||
bgp = bgp_lookup_by_name(name);
|
bgp = bgp_lookup_by_name_filter(name, !force_config);
|
||||||
else
|
else
|
||||||
bgp = bgp_get_default();
|
bgp = bgp_get_default();
|
||||||
|
|
||||||
@ -3756,7 +3760,7 @@ int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as,
|
|||||||
/* Handle AS number change */
|
/* Handle AS number change */
|
||||||
if (bgp->as != *as) {
|
if (bgp->as != *as) {
|
||||||
if (hidden || CHECK_FLAG(bgp->vrf_flags, BGP_VRF_AUTO)) {
|
if (hidden || CHECK_FLAG(bgp->vrf_flags, BGP_VRF_AUTO)) {
|
||||||
if (hidden) {
|
if (force_config == false && hidden) {
|
||||||
bgp_create(as, name, inst_type,
|
bgp_create(as, name, inst_type,
|
||||||
as_pretty, asnotation, bgp,
|
as_pretty, asnotation, bgp,
|
||||||
hidden);
|
hidden);
|
||||||
@ -3764,6 +3768,7 @@ int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as,
|
|||||||
BGP_FLAG_INSTANCE_HIDDEN);
|
BGP_FLAG_INSTANCE_HIDDEN);
|
||||||
} else {
|
} else {
|
||||||
bgp->as = *as;
|
bgp->as = *as;
|
||||||
|
if (force_config == false)
|
||||||
UNSET_FLAG(bgp->vrf_flags, BGP_VRF_AUTO);
|
UNSET_FLAG(bgp->vrf_flags, BGP_VRF_AUTO);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3801,8 +3806,7 @@ int bgp_get(struct bgp **bgp_val, as_t *as, const char *name,
|
|||||||
struct vrf *vrf = NULL;
|
struct vrf *vrf = NULL;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
|
||||||
ret = bgp_lookup_by_as_name_type(bgp_val, as, as_pretty, asnotation,
|
ret = bgp_lookup_by_as_name_type(bgp_val, as, as_pretty, asnotation, name, inst_type, false);
|
||||||
name, inst_type);
|
|
||||||
if (ret || *bgp_val)
|
if (ret || *bgp_val)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
|
@ -2285,6 +2285,7 @@ extern void bgp_zclient_reset(void);
|
|||||||
extern struct bgp *bgp_get_default(void);
|
extern struct bgp *bgp_get_default(void);
|
||||||
extern struct bgp *bgp_lookup(as_t, const char *);
|
extern struct bgp *bgp_lookup(as_t, const char *);
|
||||||
extern struct bgp *bgp_lookup_by_name(const char *);
|
extern struct bgp *bgp_lookup_by_name(const char *);
|
||||||
|
extern struct bgp *bgp_lookup_by_name_filter(const char *name, bool filter_auto);
|
||||||
extern struct bgp *bgp_lookup_by_vrf_id(vrf_id_t);
|
extern struct bgp *bgp_lookup_by_vrf_id(vrf_id_t);
|
||||||
extern struct bgp *bgp_get_evpn(void);
|
extern struct bgp *bgp_get_evpn(void);
|
||||||
extern void bgp_set_evpn(struct bgp *bgp);
|
extern void bgp_set_evpn(struct bgp *bgp);
|
||||||
@ -2859,11 +2860,9 @@ extern struct peer *peer_new(struct bgp *bgp);
|
|||||||
|
|
||||||
extern struct peer *peer_lookup_in_view(struct vty *vty, struct bgp *bgp,
|
extern struct peer *peer_lookup_in_view(struct vty *vty, struct bgp *bgp,
|
||||||
const char *ip_str, bool use_json);
|
const char *ip_str, bool use_json);
|
||||||
extern int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as,
|
extern int bgp_lookup_by_as_name_type(struct bgp **bgp_val, as_t *as, const char *as_pretty,
|
||||||
const char *as_pretty,
|
enum asnotation_mode asnotation, const char *name,
|
||||||
enum asnotation_mode asnotation,
|
enum bgp_instance_type inst_type, bool force_config);
|
||||||
const char *name,
|
|
||||||
enum bgp_instance_type inst_type);
|
|
||||||
|
|
||||||
/* Hooks */
|
/* Hooks */
|
||||||
DECLARE_HOOK(bgp_vrf_status_changed, (struct bgp *bgp, struct interface *ifp),
|
DECLARE_HOOK(bgp_vrf_status_changed, (struct bgp *bgp, struct interface *ifp),
|
||||||
|
@ -78,7 +78,7 @@ def setup_module(mod):
|
|||||||
"tcpdump -nni r1-eth0 -s 0 -w {} &".format(pcap_file), stdout=None
|
"tcpdump -nni r1-eth0 -s 0 -w {} &".format(pcap_file), stdout=None
|
||||||
)
|
)
|
||||||
|
|
||||||
for rname, router in tgen.routers().items():
|
for _, (rname, router) in enumerate(tgen.routers().items(), 1):
|
||||||
logger.info("Loading router %s" % rname)
|
logger.info("Loading router %s" % rname)
|
||||||
router.load_frr_config(
|
router.load_frr_config(
|
||||||
os.path.join(CWD, "{}/frr.conf".format(rname)),
|
os.path.join(CWD, "{}/frr.conf".format(rname)),
|
||||||
|
@ -2,8 +2,8 @@
|
|||||||
"bgpLocalRouterId":"192.168.100.21",
|
"bgpLocalRouterId":"192.168.100.21",
|
||||||
"defaultLocPrf":100,
|
"defaultLocPrf":100,
|
||||||
"localAS":65000,
|
"localAS":65000,
|
||||||
"192.168.101.41:2":{
|
"65000:201":{
|
||||||
"rd":"192.168.101.41:2",
|
"rd":"65000:201",
|
||||||
"[5]:[0]:[32]:[192.168.101.41]":{
|
"[5]:[0]:[32]:[192.168.101.41]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
@ -65,8 +65,8 @@
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"192.168.102.21:2":{
|
"65000:101":{
|
||||||
"rd":"192.168.102.21:2",
|
"rd":"65000:101",
|
||||||
"[5]:[0]:[32]:[192.168.102.21]":{
|
"[5]:[0]:[32]:[192.168.102.21]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
|
@ -2,8 +2,8 @@
|
|||||||
"bgpLocalRouterId":"192.168.100.21",
|
"bgpLocalRouterId":"192.168.100.21",
|
||||||
"defaultLocPrf":100,
|
"defaultLocPrf":100,
|
||||||
"localAS":65000,
|
"localAS":65000,
|
||||||
"192.168.101.41:2":{
|
"65000:201":{
|
||||||
"rd":"192.168.101.41:2",
|
"rd":"65000:201",
|
||||||
"[5]:[0]:[32]:[192.168.101.41]":{
|
"[5]:[0]:[32]:[192.168.101.41]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
@ -125,8 +125,8 @@
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"192.168.102.21:2":{
|
"65000:101":{
|
||||||
"rd":"192.168.102.21:2",
|
"rd":"65000:101",
|
||||||
"[5]:[0]:[32]:[192.168.102.21]":{
|
"[5]:[0]:[32]:[192.168.102.21]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
|
@ -1,15 +1,36 @@
|
|||||||
|
! debug zebra vxlan
|
||||||
|
! debug zebra kernel
|
||||||
|
! debug zebra dplane
|
||||||
|
! debug zebra rib
|
||||||
! debug bgp neighbor-events
|
! debug bgp neighbor-events
|
||||||
! debug bgp updates
|
! debug bgp updates
|
||||||
! debug bgp zebra
|
! debug bgp zebra
|
||||||
|
vrf r1-vrf-101
|
||||||
|
vni 101
|
||||||
|
exit-vrf
|
||||||
|
!
|
||||||
|
interface r1-eth0
|
||||||
|
ip address 192.168.100.21/24
|
||||||
|
!
|
||||||
|
interface loop101 vrf r1-vrf-101
|
||||||
|
ip address 192.168.102.21/32
|
||||||
|
ipv6 address fd00::1/128
|
||||||
|
!
|
||||||
router bgp 65000
|
router bgp 65000
|
||||||
bgp router-id 192.168.100.21
|
bgp router-id 192.168.100.21
|
||||||
bgp log-neighbor-changes
|
bgp log-neighbor-changes
|
||||||
no bgp default ipv4-unicast
|
no bgp default ipv4-unicast
|
||||||
|
no bgp ebgp-requires-policy
|
||||||
neighbor 192.168.100.41 remote-as 65000
|
neighbor 192.168.100.41 remote-as 65000
|
||||||
neighbor 192.168.100.41 capability extended-nexthop
|
neighbor 192.168.100.41 capability extended-nexthop
|
||||||
|
neighbor 192.168.100.61 remote-as 65500
|
||||||
|
neighbor 192.168.100.61 capability extended-nexthop
|
||||||
!
|
!
|
||||||
address-family l2vpn evpn
|
address-family l2vpn evpn
|
||||||
neighbor 192.168.100.41 activate
|
neighbor 192.168.100.41 activate
|
||||||
|
neighbor 192.168.100.41 route-map rmap_r1 in
|
||||||
|
neighbor 192.168.100.61 activate
|
||||||
|
neighbor 192.168.100.61 route-map rmap_r3 in
|
||||||
advertise-all-vni
|
advertise-all-vni
|
||||||
exit-address-family
|
exit-address-family
|
||||||
!
|
!
|
||||||
@ -24,7 +45,17 @@ router bgp 65000 vrf r1-vrf-101
|
|||||||
network fd00::1/128
|
network fd00::1/128
|
||||||
exit-address-family
|
exit-address-family
|
||||||
address-family l2vpn evpn
|
address-family l2vpn evpn
|
||||||
|
rd 65000:101
|
||||||
|
route-target both 65:101
|
||||||
advertise ipv4 unicast
|
advertise ipv4 unicast
|
||||||
advertise ipv6 unicast
|
advertise ipv6 unicast
|
||||||
exit-address-family
|
exit-address-family
|
||||||
!
|
!
|
||||||
|
route-map rmap_r3 deny 1
|
||||||
|
match evpn vni 102
|
||||||
|
exit
|
||||||
|
route-map rmap_r1 permit 1
|
||||||
|
match evpn vni 101
|
||||||
|
exit
|
||||||
|
|
||||||
|
|
@ -1,23 +0,0 @@
|
|||||||
log stdout
|
|
||||||
|
|
||||||
hostname r1
|
|
||||||
password zebra
|
|
||||||
|
|
||||||
! debug zebra vxlan
|
|
||||||
! debug zebra kernel
|
|
||||||
! debug zebra dplane
|
|
||||||
! debug zebra rib
|
|
||||||
log stdout
|
|
||||||
vrf r1-vrf-101
|
|
||||||
vni 101
|
|
||||||
exit-vrf
|
|
||||||
!
|
|
||||||
interface r1-eth0
|
|
||||||
ip address 192.168.100.21/24
|
|
||||||
!
|
|
||||||
interface loop101 vrf r1-vrf-101
|
|
||||||
ip address 192.168.102.21/32
|
|
||||||
ipv6 address fd00::1/128
|
|
||||||
!
|
|
||||||
|
|
||||||
|
|
@ -2,8 +2,8 @@
|
|||||||
"bgpLocalRouterId":"192.168.100.41",
|
"bgpLocalRouterId":"192.168.100.41",
|
||||||
"defaultLocPrf":100,
|
"defaultLocPrf":100,
|
||||||
"localAS":65000,
|
"localAS":65000,
|
||||||
"192.168.101.41:2":{
|
"65000:201":{
|
||||||
"rd":"192.168.101.41:2",
|
"rd":"65000:201",
|
||||||
"[5]:[0]:[32]:[192.168.101.41]":{
|
"[5]:[0]:[32]:[192.168.101.41]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
"prefix":"[5]:[0]:[32]:[192.168.101.41]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
@ -63,8 +63,8 @@
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"192.168.102.21:2":{
|
"65000:101":{
|
||||||
"rd":"192.168.102.21:2",
|
"rd":"65000:101",
|
||||||
"[5]:[0]:[32]:[192.168.102.21]":{
|
"[5]:[0]:[32]:[192.168.102.21]":{
|
||||||
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
"prefix":"[5]:[0]:[32]:[192.168.102.21]",
|
||||||
"prefixLen":352,
|
"prefixLen":352,
|
||||||
|
@ -1,6 +1,19 @@
|
|||||||
|
! debug zebra vxlan
|
||||||
! debug bgp neighbor-events
|
! debug bgp neighbor-events
|
||||||
! debug bgp updates
|
! debug bgp updates
|
||||||
! debug bgp zebra
|
! debug bgp zebra
|
||||||
|
|
||||||
|
vrf r2-vrf-101
|
||||||
|
vni 101
|
||||||
|
exit-vrf
|
||||||
|
!
|
||||||
|
interface loop101 vrf r2-vrf-101
|
||||||
|
ip address 192.168.101.41/32
|
||||||
|
ipv6 address fd00::2/128
|
||||||
|
!
|
||||||
|
interface r2-eth0
|
||||||
|
ip address 192.168.100.41/24
|
||||||
|
!
|
||||||
router bgp 65000
|
router bgp 65000
|
||||||
bgp router-id 192.168.100.41
|
bgp router-id 192.168.100.41
|
||||||
bgp log-neighbor-changes
|
bgp log-neighbor-changes
|
||||||
@ -27,6 +40,8 @@ router bgp 65000 vrf r2-vrf-101
|
|||||||
network fd00::3/128
|
network fd00::3/128
|
||||||
exit-address-family
|
exit-address-family
|
||||||
address-family l2vpn evpn
|
address-family l2vpn evpn
|
||||||
|
rd 65000:201
|
||||||
|
route-target both 65:101
|
||||||
advertise ipv4 unicast route-map rmap4
|
advertise ipv4 unicast route-map rmap4
|
||||||
advertise ipv6 unicast route-map rmap6
|
advertise ipv6 unicast route-map rmap6
|
||||||
exit-address-family
|
exit-address-family
|
||||||
@ -47,3 +62,4 @@ exit
|
|||||||
route-map rmap6 deny 2
|
route-map rmap6 deny 2
|
||||||
match ipv6 address acl6_2
|
match ipv6 address acl6_2
|
||||||
exit
|
exit
|
||||||
|
|
@ -1,19 +0,0 @@
|
|||||||
log stdout
|
|
||||||
|
|
||||||
hostname r2
|
|
||||||
password zebra
|
|
||||||
|
|
||||||
! debug zebra vxlan
|
|
||||||
|
|
||||||
vrf r2-vrf-101
|
|
||||||
vni 101
|
|
||||||
exit-vrf
|
|
||||||
!
|
|
||||||
interface loop101 vrf r2-vrf-101
|
|
||||||
ip address 192.168.101.41/32
|
|
||||||
ipv6 address fd00::2/128
|
|
||||||
!
|
|
||||||
interface r2-eth0
|
|
||||||
ip address 192.168.100.41/24
|
|
||||||
!
|
|
||||||
|
|
46
tests/topotests/bgp_evpn_rt5/r3/frr.conf
Normal file
46
tests/topotests/bgp_evpn_rt5/r3/frr.conf
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
! debug bgp neighbor-events
|
||||||
|
! debug bgp updates
|
||||||
|
! debug bgp zebra
|
||||||
|
vrf r3-vrf-102
|
||||||
|
vni 102
|
||||||
|
exit-vrf
|
||||||
|
!
|
||||||
|
interface r3-eth0
|
||||||
|
ip address 192.168.100.61/24
|
||||||
|
!
|
||||||
|
interface loop102 vrf r3-vrf-102
|
||||||
|
ip address 192.168.102.61/32
|
||||||
|
ipv6 address fd00:6::1/128
|
||||||
|
!
|
||||||
|
router bgp 65500
|
||||||
|
bgp router-id 192.168.100.61
|
||||||
|
bgp log-neighbor-changes
|
||||||
|
no bgp default ipv4-unicast
|
||||||
|
no bgp ebgp-requires-policy
|
||||||
|
neighbor 192.168.100.21 remote-as 65000
|
||||||
|
neighbor 192.168.100.21 capability extended-nexthop
|
||||||
|
!
|
||||||
|
address-family l2vpn evpn
|
||||||
|
neighbor 192.168.100.21 activate
|
||||||
|
advertise-all-vni
|
||||||
|
exit-address-family
|
||||||
|
!
|
||||||
|
router bgp 65000 vrf r3-vrf-102
|
||||||
|
bgp router-id 192.168.100.61
|
||||||
|
bgp log-neighbor-changes
|
||||||
|
no bgp network import-check
|
||||||
|
address-family ipv4 unicast
|
||||||
|
network 192.168.102.102/32
|
||||||
|
exit-address-family
|
||||||
|
address-family ipv6 unicast
|
||||||
|
network fd00:102::1/128
|
||||||
|
exit-address-family
|
||||||
|
address-family l2vpn evpn
|
||||||
|
rd 65000:302
|
||||||
|
route-target both 65:101
|
||||||
|
advertise ipv4 unicast
|
||||||
|
advertise ipv6 unicast
|
||||||
|
exit-address-family
|
||||||
|
!
|
||||||
|
|
||||||
|
|
@ -42,10 +42,12 @@ def build_topo(tgen):
|
|||||||
|
|
||||||
tgen.add_router("r1")
|
tgen.add_router("r1")
|
||||||
tgen.add_router("r2")
|
tgen.add_router("r2")
|
||||||
|
tgen.add_router("r3")
|
||||||
|
|
||||||
switch = tgen.add_switch("s1")
|
switch = tgen.add_switch("s1")
|
||||||
switch.add_link(tgen.gears["r1"])
|
switch.add_link(tgen.gears["r1"])
|
||||||
switch.add_link(tgen.gears["r2"])
|
switch.add_link(tgen.gears["r2"])
|
||||||
|
switch.add_link(tgen.gears["r3"])
|
||||||
|
|
||||||
switch = tgen.add_switch("s2")
|
switch = tgen.add_switch("s2")
|
||||||
switch.add_link(tgen.gears["r1"])
|
switch.add_link(tgen.gears["r1"])
|
||||||
@ -53,6 +55,9 @@ def build_topo(tgen):
|
|||||||
switch = tgen.add_switch("s3")
|
switch = tgen.add_switch("s3")
|
||||||
switch.add_link(tgen.gears["r2"])
|
switch.add_link(tgen.gears["r2"])
|
||||||
|
|
||||||
|
switch = tgen.add_switch("s4")
|
||||||
|
switch.add_link(tgen.gears["r3"])
|
||||||
|
|
||||||
|
|
||||||
def setup_module(mod):
|
def setup_module(mod):
|
||||||
"Sets up the pytest environment"
|
"Sets up the pytest environment"
|
||||||
@ -71,16 +76,16 @@ def setup_module(mod):
|
|||||||
)
|
)
|
||||||
return pytest.skip("Skipping BGP EVPN RT5 NETNS Test. Kernel not supported")
|
return pytest.skip("Skipping BGP EVPN RT5 NETNS Test. Kernel not supported")
|
||||||
|
|
||||||
# create VRF vrf-101 on R1 and R2
|
# create VRF vrf-101 on R1, R2, R3
|
||||||
# create loop101
|
# create loop101
|
||||||
cmds_vrflite = [
|
cmds_vrflite = [
|
||||||
"ip link add {}-vrf-101 type vrf table 101",
|
"ip link add {0}-vrf-{1} type vrf table {1}",
|
||||||
"ip ru add oif {}-vrf-101 table 101",
|
"ip ru add oif {0}-vrf-{1} table {1}",
|
||||||
"ip ru add iif {}-vrf-101 table 101",
|
"ip ru add iif {0}-vrf-{1} table {1}",
|
||||||
"ip link set dev {}-vrf-101 up",
|
"ip link set dev {0}-vrf-{1} up",
|
||||||
"ip link add loop101 type dummy",
|
"ip link add loop{1} type dummy",
|
||||||
"ip link set dev loop101 master {}-vrf-101",
|
"ip link set dev loop{1} master {0}-vrf-{1}",
|
||||||
"ip link set dev loop101 up",
|
"ip link set dev loop{1} up",
|
||||||
]
|
]
|
||||||
|
|
||||||
cmds_r2 = [ # config routing 101
|
cmds_r2 = [ # config routing 101
|
||||||
@ -92,6 +97,15 @@ def setup_module(mod):
|
|||||||
"ip link set vxlan-101 up type bridge_slave learning off flood off mcast_flood off",
|
"ip link set vxlan-101 up type bridge_slave learning off flood off mcast_flood off",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
cmds_r3 = [ # config routing 102
|
||||||
|
"ip link add name bridge-102 up type bridge stp_state 0",
|
||||||
|
"ip link set bridge-102 master {}-vrf-102",
|
||||||
|
"ip link set dev bridge-102 up",
|
||||||
|
"ip link add name vxlan-102 type vxlan id 102 dstport 4789 dev r3-eth0 local 192.168.100.61",
|
||||||
|
"ip link set dev vxlan-102 master bridge-102",
|
||||||
|
"ip link set vxlan-102 up type bridge_slave learning off flood off mcast_flood off",
|
||||||
|
]
|
||||||
|
|
||||||
# cmds_r1_netns_method3 = [
|
# cmds_r1_netns_method3 = [
|
||||||
# "ip link add name vxlan-{1} type vxlan id {1} dstport 4789 dev {0}-eth0 local 192.168.100.21",
|
# "ip link add name vxlan-{1} type vxlan id {1} dstport 4789 dev {0}-eth0 local 192.168.100.21",
|
||||||
# "ip link set dev vxlan-{1} netns {0}-vrf-{1}",
|
# "ip link set dev vxlan-{1} netns {0}-vrf-{1}",
|
||||||
@ -111,8 +125,8 @@ def setup_module(mod):
|
|||||||
|
|
||||||
router = tgen.gears["r2"]
|
router = tgen.gears["r2"]
|
||||||
for cmd in cmds_vrflite:
|
for cmd in cmds_vrflite:
|
||||||
logger.info("cmd to r2: " + cmd.format("r2"))
|
logger.info("cmd to r2: " + cmd.format("r2", 101))
|
||||||
output = router.cmd_raises(cmd.format("r2"))
|
output = router.cmd_raises(cmd.format("r2", 101))
|
||||||
logger.info("result: " + output)
|
logger.info("result: " + output)
|
||||||
|
|
||||||
for cmd in cmds_r2:
|
for cmd in cmds_r2:
|
||||||
@ -120,6 +134,17 @@ def setup_module(mod):
|
|||||||
output = router.cmd_raises(cmd.format("r2"))
|
output = router.cmd_raises(cmd.format("r2"))
|
||||||
logger.info("result: " + output)
|
logger.info("result: " + output)
|
||||||
|
|
||||||
|
router = tgen.gears["r3"]
|
||||||
|
for cmd in cmds_vrflite:
|
||||||
|
logger.info("cmd to r3: " + cmd.format("r3", 102))
|
||||||
|
output = router.cmd_raises(cmd.format("r3", 102))
|
||||||
|
logger.info("result: " + output)
|
||||||
|
|
||||||
|
for cmd in cmds_r3:
|
||||||
|
logger.info("cmd to r3: " + cmd.format("r3"))
|
||||||
|
output = router.cmd_raises(cmd.format("r3"))
|
||||||
|
logger.info("result: " + output)
|
||||||
|
|
||||||
tgen.net["r1"].cmd_raises(
|
tgen.net["r1"].cmd_raises(
|
||||||
"ip link add name vxlan-101 type vxlan id 101 dstport 4789 dev r1-eth0 local 192.168.100.21"
|
"ip link add name vxlan-101 type vxlan id 101 dstport 4789 dev r1-eth0 local 192.168.100.21"
|
||||||
)
|
)
|
||||||
@ -134,19 +159,13 @@ def setup_module(mod):
|
|||||||
tgen.net["r1"].cmd_raises("ip -n r1-vrf-101 link set bridge-101 up")
|
tgen.net["r1"].cmd_raises("ip -n r1-vrf-101 link set bridge-101 up")
|
||||||
tgen.net["r1"].cmd_raises("ip -n r1-vrf-101 link set vxlan-101 up")
|
tgen.net["r1"].cmd_raises("ip -n r1-vrf-101 link set vxlan-101 up")
|
||||||
|
|
||||||
for rname, router in router_list.items():
|
for rname, router in tgen.routers().items():
|
||||||
|
logger.info("Loading router %s" % rname)
|
||||||
if rname == "r1":
|
if rname == "r1":
|
||||||
router.use_netns_vrf()
|
router.use_netns_vrf()
|
||||||
router.load_config(
|
router.load_frr_config(os.path.join(CWD, "{}/frr.conf".format(rname)))
|
||||||
TopoRouter.RD_ZEBRA, os.path.join(CWD, "{}/zebra.conf".format(rname))
|
|
||||||
)
|
|
||||||
else:
|
else:
|
||||||
router.load_config(
|
router.load_frr_config(os.path.join(CWD, "{}/frr.conf".format(rname)))
|
||||||
TopoRouter.RD_ZEBRA, os.path.join(CWD, "{}/zebra.conf".format(rname))
|
|
||||||
)
|
|
||||||
router.load_config(
|
|
||||||
TopoRouter.RD_BGP, os.path.join(CWD, "{}/bgpd.conf".format(rname))
|
|
||||||
)
|
|
||||||
|
|
||||||
# Initialize all routers.
|
# Initialize all routers.
|
||||||
tgen.start_router()
|
tgen.start_router()
|
||||||
|
Loading…
Reference in New Issue
Block a user