From 2c7cac91ed6e7db0f6937923d2b57f97dbdbc337 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 28 Apr 2024 11:53:30 +0200 Subject: Adding upstream version 8.4.4. Signed-off-by: Daniel Baumann --- tests/topotests/bgp_evpn_vxlan_topo1/P1/bgpd.conf | 1 + tests/topotests/bgp_evpn_vxlan_topo1/P1/ospfd.conf | 13 + tests/topotests/bgp_evpn_vxlan_topo1/P1/zebra.conf | 7 + tests/topotests/bgp_evpn_vxlan_topo1/PE1/bgpd.conf | 11 + .../bgp_evpn_vxlan_topo1/PE1/evpn.vni.json | 13 + .../topotests/bgp_evpn_vxlan_topo1/PE1/ospfd.conf | 9 + .../topotests/bgp_evpn_vxlan_topo1/PE1/zebra.conf | 8 + tests/topotests/bgp_evpn_vxlan_topo1/PE2/bgpd.conf | 12 + .../bgp_evpn_vxlan_topo1/PE2/evpn.vni.json | 12 + .../topotests/bgp_evpn_vxlan_topo1/PE2/ospfd.conf | 9 + .../topotests/bgp_evpn_vxlan_topo1/PE2/zebra.conf | 6 + tests/topotests/bgp_evpn_vxlan_topo1/__init__.py | 0 .../topotests/bgp_evpn_vxlan_topo1/host1/bgpd.conf | 1 + .../bgp_evpn_vxlan_topo1/host1/ospfd.conf | 1 + .../bgp_evpn_vxlan_topo1/host1/zebra.conf | 3 + .../topotests/bgp_evpn_vxlan_topo1/host2/bgpd.conf | 1 + .../bgp_evpn_vxlan_topo1/host2/ospfd.conf | 1 + .../bgp_evpn_vxlan_topo1/host2/zebra.conf | 3 + .../bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py | 440 +++++++++++++++++++++ 19 files changed, 551 insertions(+) create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/P1/bgpd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/P1/ospfd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/P1/zebra.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE1/bgpd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE1/evpn.vni.json create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE1/ospfd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE1/zebra.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE2/bgpd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE2/evpn.vni.json create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE2/ospfd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/PE2/zebra.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/__init__.py create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host1/bgpd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host1/ospfd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host1/zebra.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host2/bgpd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host2/ospfd.conf create mode 100644 tests/topotests/bgp_evpn_vxlan_topo1/host2/zebra.conf create mode 100755 tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py (limited to 'tests/topotests/bgp_evpn_vxlan_topo1') diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/P1/bgpd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/P1/bgpd.conf new file mode 100644 index 0000000..cdf4cb4 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/P1/bgpd.conf @@ -0,0 +1 @@ +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/P1/ospfd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/P1/ospfd.conf new file mode 100644 index 0000000..2db7edb --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/P1/ospfd.conf @@ -0,0 +1,13 @@ +! +router ospf + network 10.20.0.0/16 area 0 + network 10.20.20.20/32 area 0 +! +int P1-eth0 + ip ospf hello-interval 2 + ip ospf dead-interval 10 +! +int P1-eth1 + ip ospf hello-interval 2 + ip ospf dead-interval 10 +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/P1/zebra.conf b/tests/topotests/bgp_evpn_vxlan_topo1/P1/zebra.conf new file mode 100644 index 0000000..95b5da8 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/P1/zebra.conf @@ -0,0 +1,7 @@ +! +interface lo + ip address 10.20.20.20/32 +interface P1-eth0 + ip address 10.20.1.2/24 +interface P1-eth1 + ip address 10.20.2.2/24 diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE1/bgpd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/bgpd.conf new file mode 100644 index 0000000..991a1e7 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/bgpd.conf @@ -0,0 +1,11 @@ +router bgp 65000 + timers 3 9 + bgp router-id 10.10.10.10 + no bgp default ipv4-unicast + neighbor 10.30.30.30 remote-as 65000 + neighbor 10.30.30.30 update-source lo + neighbor 10.30.30.30 timers 3 10 + address-family l2vpn evpn + neighbor 10.30.30.30 activate + advertise-all-vni + advertise-svi-ip diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE1/evpn.vni.json b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/evpn.vni.json new file mode 100644 index 0000000..ce7915c --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/evpn.vni.json @@ -0,0 +1,13 @@ +{ + "vni":101, + "type":"L2", + "vrf":"default", + "vxlanInterface":"vxlan101", + "vtepIp":"10.10.10.10", + "mcastGroup":"0.0.0.0", + "advertiseGatewayMacip":"No", + "numRemoteVteps":[ + "10.30.30.30" + ] +} + diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE1/ospfd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/ospfd.conf new file mode 100644 index 0000000..f1c2b42 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/ospfd.conf @@ -0,0 +1,9 @@ +! +router ospf + network 10.20.0.0/16 area 0 + network 10.10.10.10/32 area 0 +! +int PE1-eth1 + ip ospf hello-interval 2 + ip ospf dead-interval 10 +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE1/zebra.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/zebra.conf new file mode 100644 index 0000000..e269947 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE1/zebra.conf @@ -0,0 +1,8 @@ +! +log file zebra.log +! +interface lo + ip address 10.10.10.10/32 +interface PE1-eth1 + ip address 10.20.1.1/24 +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE2/bgpd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/bgpd.conf new file mode 100644 index 0000000..52f8687 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/bgpd.conf @@ -0,0 +1,12 @@ +router bgp 65000 + timers bgp 3 9 + bgp router-id 10.30.30.30 + no bgp default ipv4-unicast + neighbor 10.10.10.10 remote-as 65000 + neighbor 10.10.10.10 update-source lo + neighbor 10.10.10.10 timers 3 10 + ! + address-family l2vpn evpn + neighbor 10.10.10.10 activate + advertise-all-vni + advertise-svi-ip diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE2/evpn.vni.json b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/evpn.vni.json new file mode 100644 index 0000000..6c69202 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/evpn.vni.json @@ -0,0 +1,12 @@ +{ + "vni":101, + "type":"L2", + "vrf":"default", + "vxlanInterface":"vxlan101", + "vtepIp":"10.30.30.30", + "mcastGroup":"0.0.0.0", + "advertiseGatewayMacip":"No", + "numRemoteVteps":[ + "10.10.10.10" + ] +} diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE2/ospfd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/ospfd.conf new file mode 100644 index 0000000..065c993 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/ospfd.conf @@ -0,0 +1,9 @@ +! +router ospf + network 10.20.0.0/16 area 0 + network 10.30.30.30/32 area 0 +! +int PE2-eth0 + ip ospf hello-interval 2 + ip ospf dead-interval 10 +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/PE2/zebra.conf b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/zebra.conf new file mode 100644 index 0000000..9738916 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/PE2/zebra.conf @@ -0,0 +1,6 @@ +! +interface lo + ip address 10.30.30.30/32 +interface PE2-eth0 + ip address 10.20.2.3/24 +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/__init__.py b/tests/topotests/bgp_evpn_vxlan_topo1/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host1/bgpd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host1/bgpd.conf new file mode 100644 index 0000000..cdf4cb4 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host1/bgpd.conf @@ -0,0 +1 @@ +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host1/ospfd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host1/ospfd.conf new file mode 100644 index 0000000..cdf4cb4 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host1/ospfd.conf @@ -0,0 +1 @@ +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host1/zebra.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host1/zebra.conf new file mode 100644 index 0000000..91fae9e --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host1/zebra.conf @@ -0,0 +1,3 @@ +! +int host1-eth0 + ip address 10.10.1.55/24 diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host2/bgpd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host2/bgpd.conf new file mode 100644 index 0000000..cdf4cb4 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host2/bgpd.conf @@ -0,0 +1 @@ +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host2/ospfd.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host2/ospfd.conf new file mode 100644 index 0000000..cdf4cb4 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host2/ospfd.conf @@ -0,0 +1 @@ +! diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/host2/zebra.conf b/tests/topotests/bgp_evpn_vxlan_topo1/host2/zebra.conf new file mode 100644 index 0000000..df9adeb --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/host2/zebra.conf @@ -0,0 +1,3 @@ +! +interface host2-eth0 + ip address 10.10.1.56/24 diff --git a/tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py b/tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py new file mode 100755 index 0000000..5d0a326 --- /dev/null +++ b/tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py @@ -0,0 +1,440 @@ +#!/usr/bin/env python + +# +# test_bgp_evpn_vxlan.py +# Part of NetDEF Topology Tests +# +# Copyright (c) 2020 by Volta Networks +# +# Permission to use, copy, modify, and/or distribute this software +# for any purpose with or without fee is hereby granted, provided +# that the above copyright notice and this permission notice appear +# in all copies. +# +# THE SOFTWARE IS PROVIDED "AS IS" AND NETDEF DISCLAIMS ALL WARRANTIES +# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL NETDEF BE LIABLE FOR +# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY +# DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, +# WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS +# ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE +# OF THIS SOFTWARE. +# + +""" +test_bgp_evpn_vxlan.py: Test VXLAN EVPN MAC a route signalling over BGP. +""" + +import os +import sys +import json +from functools import partial +from time import sleep +import pytest + +# Save the Current Working Directory to find configuration files. +CWD = os.path.dirname(os.path.realpath(__file__)) +sys.path.append(os.path.join(CWD, "../")) + +# pylint: disable=C0413 +# Import topogen and topotest helpers +from lib import topotest +from lib.topogen import Topogen, TopoRouter, get_topogen +from lib.topolog import logger + +# Required to instantiate the topology builder class. + +pytestmark = [pytest.mark.bgpd, pytest.mark.ospfd] + + +def build_topo(tgen): + "Build function" + + # This function only purpose is to define allocation and relationship + # between routers, switches and hosts. + # + # + # Create routers + tgen.add_router("P1") + tgen.add_router("PE1") + tgen.add_router("PE2") + tgen.add_router("host1") + tgen.add_router("host2") + + # Host1-PE1 + switch = tgen.add_switch("s1") + switch.add_link(tgen.gears["host1"]) + switch.add_link(tgen.gears["PE1"]) + + # PE1-P1 + switch = tgen.add_switch("s2") + switch.add_link(tgen.gears["PE1"]) + switch.add_link(tgen.gears["P1"]) + + # P1-PE2 + switch = tgen.add_switch("s3") + switch.add_link(tgen.gears["P1"]) + switch.add_link(tgen.gears["PE2"]) + + # PE2-host2 + switch = tgen.add_switch("s4") + switch.add_link(tgen.gears["PE2"]) + switch.add_link(tgen.gears["host2"]) + + +def setup_module(mod): + "Sets up the pytest environment" + # This function initiates the topology build with Topogen... + tgen = Topogen(build_topo, mod.__name__) + # ... and here it calls Mininet initialization functions. + tgen.start_topology() + + pe1 = tgen.gears["PE1"] + pe2 = tgen.gears["PE2"] + p1 = tgen.gears["P1"] + + # set up PE bridges with the EVPN member interfaces facing the CE hosts + pe1.run("ip link add name br101 type bridge stp_state 0") + pe1.run("ip addr add 10.10.1.1/24 dev br101") + pe1.run("ip link set dev br101 up") + pe1.run( + "ip link add vxlan101 type vxlan id 101 dstport 4789 local 10.10.10.10 nolearning" + ) + pe1.run("ip link set dev vxlan101 master br101") + pe1.run("ip link set up dev vxlan101") + pe1.run("ip link set dev PE1-eth0 master br101") + + pe2.run("ip link add name br101 type bridge stp_state 0") + pe2.run("ip addr add 10.10.1.3/24 dev br101") + pe2.run("ip link set dev br101 up") + pe2.run( + "ip link add vxlan101 type vxlan id 101 dstport 4789 local 10.30.30.30 nolearning" + ) + pe2.run("ip link set dev vxlan101 master br101") + pe2.run("ip link set up dev vxlan101") + pe2.run("ip link set dev PE2-eth1 master br101") + p1.run("sysctl -w net.ipv4.ip_forward=1") + + # This is a sample of configuration loading. + router_list = tgen.routers() + + # For all registered routers, load the zebra configuration file + for rname, router in router_list.items(): + router.load_config( + TopoRouter.RD_ZEBRA, os.path.join(CWD, "{}/zebra.conf".format(rname)) + ) + router.load_config( + TopoRouter.RD_OSPF, os.path.join(CWD, "{}/ospfd.conf".format(rname)) + ) + router.load_config( + TopoRouter.RD_BGP, os.path.join(CWD, "{}/bgpd.conf".format(rname)) + ) + + # After loading the configurations, this function loads configured daemons. + tgen.start_router() + + +def teardown_module(mod): + "Teardown the pytest environment" + tgen = get_topogen() + + # This function tears down the whole topology. + tgen.stop_topology() + + +def show_vni_json_elide_ifindex(pe, vni, expected): + output_json = pe.vtysh_cmd("show evpn vni {} json".format(vni), isjson=True) + + if "ifindex" in output_json: + output_json.pop("ifindex") + + return topotest.json_cmp(output_json, expected) + + +def check_vni_macs_present(tgen, router, vni, maclist): + result = router.vtysh_cmd("show evpn mac vni {} json".format(vni), isjson=True) + for rname, ifname in maclist: + m = tgen.net.macs[(rname, ifname)] + if m not in result["macs"]: + return "MAC ({}) for interface {} on {} missing on {} from {}".format( + m, ifname, rname, router.name, json.dumps(result, indent=4) + ) + return None + + +def test_pe1_converge_evpn(): + "Wait for protocol convergence" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + pe1 = tgen.gears["PE1"] + json_file = "{}/{}/evpn.vni.json".format(CWD, pe1.name) + expected = json.loads(open(json_file).read()) + + test_func = partial(show_vni_json_elide_ifindex, pe1, 101, expected) + _, result = topotest.run_and_expect(test_func, None, count=45, wait=1) + assertmsg = '"{}" JSON output mismatches'.format(pe1.name) + + test_func = partial( + check_vni_macs_present, + tgen, + pe1, + 101, + (("host1", "host1-eth0"), ("host2", "host2-eth0")), + ) + _, result = topotest.run_and_expect(test_func, None, count=30, wait=1) + if result: + logger.warning("%s", result) + assert None, '"{}" missing expected MACs'.format(pe1.name) + + +def test_pe2_converge_evpn(): + "Wait for protocol convergence" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + pe2 = tgen.gears["PE2"] + json_file = "{}/{}/evpn.vni.json".format(CWD, pe2.name) + expected = json.loads(open(json_file).read()) + + test_func = partial(show_vni_json_elide_ifindex, pe2, 101, expected) + _, result = topotest.run_and_expect(test_func, None, count=45, wait=1) + assertmsg = '"{}" JSON output mismatches'.format(pe2.name) + assert result is None, assertmsg + + test_func = partial( + check_vni_macs_present, + tgen, + pe2, + 101, + (("host1", "host1-eth0"), ("host2", "host2-eth0")), + ) + _, result = topotest.run_and_expect(test_func, None, count=30, wait=1) + if result: + logger.warning("%s", result) + assert None, '"{}" missing expected MACs'.format(pe2.name) + + +def mac_learn_test(host, local): + "check the host MAC gets learned by the VNI" + + host_output = host.vtysh_cmd("show interface {}-eth0".format(host.name)) + int_lines = host_output.splitlines() + for line in int_lines: + line_items = line.split(": ") + if "HWaddr" in line_items[0]: + mac = line_items[1] + break + + mac_output = local.vtysh_cmd("show evpn mac vni 101 mac {} json".format(mac)) + mac_output_json = json.loads(mac_output) + assertmsg = "Local MAC output does not match interface mac {}".format(mac) + assert mac_output_json[mac]["type"] == "local", assertmsg + + +def mac_test_local_remote(local, remote): + "test MAC transfer between local and remote" + + local_output = local.vtysh_cmd("show evpn mac vni all json") + remote_output = remote.vtysh_cmd("show evpn mac vni all json") + local_output_vni = local.vtysh_cmd("show evpn vni detail json") + local_output_json = json.loads(local_output) + remote_output_json = json.loads(remote_output) + local_output_vni_json = json.loads(local_output_vni) + + for vni in local_output_json: + mac_list = local_output_json[vni]["macs"] + for mac in mac_list: + if mac_list[mac]["type"] == "local" and mac_list[mac]["intf"] != "br101": + assertmsg = "JSON output mismatches local: {} remote: {}".format( + local_output_vni_json[0]["vtepIp"], + remote_output_json[vni]["macs"][mac]["remoteVtep"], + ) + assert ( + remote_output_json[vni]["macs"][mac]["remoteVtep"] + == local_output_vni_json[0]["vtepIp"] + ), assertmsg + + +def test_learning_pe1(): + "test MAC learning on PE1" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + host1 = tgen.gears["host1"] + pe1 = tgen.gears["PE1"] + mac_learn_test(host1, pe1) + + +def test_learning_pe2(): + "test MAC learning on PE2" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + host2 = tgen.gears["host2"] + pe2 = tgen.gears["PE2"] + mac_learn_test(host2, pe2) + + +def test_local_remote_mac_pe1(): + "Test MAC transfer PE1 local and PE2 remote" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + pe1 = tgen.gears["PE1"] + pe2 = tgen.gears["PE2"] + mac_test_local_remote(pe1, pe2) + + +def test_local_remote_mac_pe2(): + "Test MAC transfer PE2 local and PE1 remote" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + pe1 = tgen.gears["PE1"] + pe2 = tgen.gears["PE2"] + mac_test_local_remote(pe2, pe1) + + # Memory leak test template + + +def ip_learn_test(tgen, host, local, remote, ip_addr): + "check the host IP gets learned by the VNI" + host_output = host.vtysh_cmd("show interface {}-eth0".format(host.name)) + int_lines = host_output.splitlines() + for line in int_lines: + line_items = line.split(": ") + if "HWaddr" in line_items[0]: + mac = line_items[1] + break + print(host_output) + + # check we have a local association between the MAC and IP + local_output = local.vtysh_cmd("show evpn mac vni 101 mac {} json".format(mac)) + print(local_output) + local_output_json = json.loads(local_output) + mac_type = local_output_json[mac]["type"] + assertmsg = "Failed to learn local IP address on host {}".format(host.name) + assert local_output_json[mac]["neighbors"] != "none", assertmsg + learned_ip = local_output_json[mac]["neighbors"]["active"][0] + + assertmsg = "local learned mac wrong type: {} ".format(mac_type) + assert mac_type == "local", assertmsg + + assertmsg = ( + "learned address mismatch with configured address host: {} learned: {}".format( + ip_addr, learned_ip + ) + ) + assert ip_addr == learned_ip, assertmsg + + # now lets check the remote + count = 0 + converged = False + while count < 30: + remote_output = remote.vtysh_cmd( + "show evpn mac vni 101 mac {} json".format(mac) + ) + print(remote_output) + remote_output_json = json.loads(remote_output) + type = remote_output_json[mac]["type"] + if not remote_output_json[mac]["neighbors"] == "none": + # due to a kernel quirk, learned IPs can be inactive + if ( + remote_output_json[mac]["neighbors"]["active"] + or remote_output_json[mac]["neighbors"]["inactive"] + ): + converged = True + break + count += 1 + sleep(1) + + print("tries: {}".format(count)) + assertmsg = "{} remote learned mac no address: {} ".format(host.name, mac) + # some debug for this failure + if not converged == True: + log_output = remote.run("cat zebra.log") + print(log_output) + + assert converged == True, assertmsg + if remote_output_json[mac]["neighbors"]["active"]: + learned_ip = remote_output_json[mac]["neighbors"]["active"][0] + else: + learned_ip = remote_output_json[mac]["neighbors"]["inactive"][0] + assertmsg = "remote learned mac wrong type: {} ".format(type) + assert type == "remote", assertmsg + + assertmsg = "remote learned address mismatch with configured address host: {} learned: {}".format( + ip_addr, learned_ip + ) + assert ip_addr == learned_ip, assertmsg + + +def test_ip_pe1_learn(): + "run the IP learn test for PE1" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + host1 = tgen.gears["host1"] + pe1 = tgen.gears["PE1"] + pe2 = tgen.gears["PE2"] + pe2.vtysh_cmd("debug zebra vxlan") + pe2.vtysh_cmd("debug zebra kernel") + # lets populate that arp cache + host1.run("ping -c1 10.10.1.1") + ip_learn_test(tgen, host1, pe1, pe2, "10.10.1.55") + # tgen.mininet_cli() + + +def test_ip_pe2_learn(): + "run the IP learn test for PE2" + + tgen = get_topogen() + # Don't run this test if we have any failure. + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + host2 = tgen.gears["host2"] + pe1 = tgen.gears["PE1"] + pe2 = tgen.gears["PE2"] + pe1.vtysh_cmd("debug zebra vxlan") + pe1.vtysh_cmd("debug zebra kernel") + # lets populate that arp cache + host2.run("ping -c1 10.10.1.3") + ip_learn_test(tgen, host2, pe2, pe1, "10.10.1.56") + # tgen.mininet_cli() + + +def test_memory_leak(): + "Run the memory leak test and report results." + tgen = get_topogen() + if not tgen.is_memleak_enabled(): + pytest.skip("Memory leak test/report is disabled") + + tgen.report_memory_leaks() + + +if __name__ == "__main__": + args = ["-s"] + sys.argv[1:] + sys.exit(pytest.main(args)) -- cgit v1.2.3