diff options
Diffstat (limited to 'tests')
70 files changed, 5608 insertions, 329 deletions
diff --git a/tests/bgpd/test_aspath.c b/tests/bgpd/test_aspath.c index aaf3fd2aa4..c2d39752ab 100644 --- a/tests/bgpd/test_aspath.c +++ b/tests/bgpd/test_aspath.c @@ -469,7 +469,10 @@ static struct aspath_tests { 0, 0, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 10, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 10, }, COMMON_ATTR_SIZE + 3, }, @@ -482,7 +485,10 @@ static struct aspath_tests { -1, 0, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 8, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 8, }, COMMON_ATTR_SIZE + 3, }, @@ -495,7 +501,10 @@ static struct aspath_tests { -1, 0, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 12, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 12, }, COMMON_ATTR_SIZE + 3, }, @@ -510,7 +519,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS_PATH, 10, + BGP_ATTR_AS_PATH, + 10, }, COMMON_ATTR_SIZE + 3, }, @@ -525,7 +535,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS4_PATH, 10, + BGP_ATTR_AS4_PATH, + 10, }, COMMON_ATTR_SIZE + 3, }, @@ -540,7 +551,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS4_PATH, 10, + BGP_ATTR_AS4_PATH, + 10, }, COMMON_ATTR_SIZE + 3, }, @@ -553,7 +565,10 @@ static struct aspath_tests { 0, PEER_CAP_AS4_RCV | PEER_CAP_AS4_ADV, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 18, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 18, }, COMMON_ATTR_SIZE + 3, }, @@ -566,7 +581,10 @@ static struct aspath_tests { -1, PEER_CAP_AS4_RCV | PEER_CAP_AS4_ADV, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 16, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 16, }, COMMON_ATTR_SIZE + 3, }, @@ -579,7 +597,10 @@ static struct aspath_tests { -1, PEER_CAP_AS4_RCV | PEER_CAP_AS4_ADV, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 20, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 20, }, COMMON_ATTR_SIZE + 3, }, @@ -592,7 +613,10 @@ static struct aspath_tests { -1, PEER_CAP_AS4_RCV | PEER_CAP_AS4_ADV, { - COMMON_ATTRS, BGP_ATTR_FLAG_TRANS, BGP_ATTR_AS_PATH, 22, + COMMON_ATTRS, + BGP_ATTR_FLAG_TRANS, + BGP_ATTR_AS_PATH, + 22, }, COMMON_ATTR_SIZE + 3, }, @@ -607,7 +631,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS_PATH, 18, + BGP_ATTR_AS_PATH, + 18, }, COMMON_ATTR_SIZE + 3, }, @@ -622,7 +647,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS4_PATH, 14, + BGP_ATTR_AS4_PATH, + 14, }, COMMON_ATTR_SIZE + 3, }, @@ -637,7 +663,8 @@ static struct aspath_tests { { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS4_PATH, 14, + BGP_ATTR_AS4_PATH, + 14, }, COMMON_ATTR_SIZE + 3, &test_segments[0], @@ -648,12 +675,13 @@ static struct aspath_tests { &test_segments[28], "8466 3 52737 0 4096", AS4_DATA, - -1, + -2, PEER_CAP_AS4_RCV | PEER_CAP_AS4_ADV, { COMMON_ATTRS, BGP_ATTR_FLAG_TRANS | BGP_ATTR_FLAG_OPTIONAL, - BGP_ATTR_AS4_PATH, 22, + BGP_ATTR_AS4_PATH, + 22, }, COMMON_ATTR_SIZE + 3, }, diff --git a/tests/topotests/bgp_aspath_zero/__init__.py b/tests/topotests/bgp_aspath_zero/__init__.py new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/__init__.py diff --git a/tests/topotests/bgp_aspath_zero/exabgp.env b/tests/topotests/bgp_aspath_zero/exabgp.env new file mode 100644 index 0000000000..28e642360a --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/exabgp.env @@ -0,0 +1,53 @@ +[exabgp.api] +encoder = text +highres = false +respawn = false +socket = '' + +[exabgp.bgp] +openwait = 60 + +[exabgp.cache] +attributes = true +nexthops = true + +[exabgp.daemon] +daemonize = true +pid = '/var/run/exabgp/exabgp.pid' +user = 'exabgp' +##daemonize = false + +[exabgp.log] +all = false +configuration = true +daemon = true +destination = '/var/log/exabgp.log' +enable = true +level = INFO +message = false +network = true +packets = false +parser = false +processes = true +reactor = true +rib = false +routes = false +short = false +timers = false + +[exabgp.pdb] +enable = false + +[exabgp.profile] +enable = false +file = '' + +[exabgp.reactor] +speed = 1.0 + +[exabgp.tcp] +acl = false +bind = '' +delay = 0 +once = false +port = 179 diff --git a/tests/topotests/bgp_aspath_zero/peer1/exabgp.cfg b/tests/topotests/bgp_aspath_zero/peer1/exabgp.cfg new file mode 100644 index 0000000000..fe9ea01eca --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/peer1/exabgp.cfg @@ -0,0 +1,17 @@ +neighbor 10.0.0.1 { + router-id 10.0.0.2; + local-address 10.0.0.2; + local-as 65001; + peer-as 65534; + + static { + route 192.168.100.101/32 { + next-hop 10.0.0.2; + } + + route 192.168.100.102/32 { + as-path [65000 0 65001]; + next-hop 10.0.0.2; + } + } +} diff --git a/tests/topotests/bgp_aspath_zero/r1/bgpd.conf b/tests/topotests/bgp_aspath_zero/r1/bgpd.conf new file mode 100644 index 0000000000..002a5c78c0 --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/r1/bgpd.conf @@ -0,0 +1,6 @@ +! +router bgp 65534 + no bgp ebgp-requires-policy + neighbor 10.0.0.2 remote-as external + neighbor 10.0.0.2 timers 3 10 +! diff --git a/tests/topotests/bgp_aspath_zero/r1/zebra.conf b/tests/topotests/bgp_aspath_zero/r1/zebra.conf new file mode 100644 index 0000000000..22a26ac610 --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/r1/zebra.conf @@ -0,0 +1,6 @@ +! +interface r1-eth0 + ip address 10.0.0.1/24 +! +ip forwarding +! diff --git a/tests/topotests/bgp_aspath_zero/test_bgp_aspath_zero.py b/tests/topotests/bgp_aspath_zero/test_bgp_aspath_zero.py new file mode 100644 index 0000000000..903ab12a13 --- /dev/null +++ b/tests/topotests/bgp_aspath_zero/test_bgp_aspath_zero.py @@ -0,0 +1,121 @@ +#!/usr/bin/env python + +# +# Copyright (c) 2021 by +# Donatas Abraitis <donatas.abraitis@gmail.com> +# +# 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 if BGP UPDATE with AS-PATH attribute with value zero (0) +is threated as withdrawal. +""" + +import os +import sys +import json +import time +import pytest +import functools + +CWD = os.path.dirname(os.path.realpath(__file__)) +sys.path.append(os.path.join(CWD, "../")) + +# pylint: disable=C0413 +from lib import topotest +from lib.topogen import Topogen, TopoRouter, get_topogen +from lib.topolog import logger +from mininet.topo import Topo + +pytestmark = [pytest.mark.bgpd] + + +class BgpAggregatorAsnZero(Topo): + def build(self, *_args, **_opts): + tgen = get_topogen(self) + + r1 = tgen.add_router("r1") + peer1 = tgen.add_exabgp_peer( + "peer1", ip="10.0.0.2", defaultRoute="via 10.0.0.1" + ) + + switch = tgen.add_switch("s1") + switch.add_link(r1) + switch.add_link(peer1) + + +def setup_module(mod): + tgen = Topogen(BgpAggregatorAsnZero, mod.__name__) + tgen.start_topology() + + router = tgen.gears["r1"] + router.load_config(TopoRouter.RD_ZEBRA, os.path.join(CWD, "r1/zebra.conf")) + router.load_config(TopoRouter.RD_BGP, os.path.join(CWD, "r1/bgpd.conf")) + router.start() + + peer = tgen.gears["peer1"] + peer.start(os.path.join(CWD, "peer1"), os.path.join(CWD, "exabgp.env")) + + +def teardown_module(mod): + tgen = get_topogen() + tgen.stop_topology() + + +def test_bgp_aggregator_zero(): + tgen = get_topogen() + + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + def _bgp_converge(): + output = json.loads( + tgen.gears["r1"].vtysh_cmd("show ip bgp neighbor 10.0.0.2 json") + ) + expected = { + "10.0.0.2": { + "bgpState": "Established", + "addressFamilyInfo": {"ipv4Unicast": {"acceptedPrefixCounter": 1}}, + } + } + return topotest.json_cmp(output, expected) + + test_func = functools.partial(_bgp_converge) + success, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5) + assert result is None, "More than one prefix seen at r1, SHOULD be only one." + + def _bgp_has_correct_routes_without_asn_0(): + output = json.loads(tgen.gears["r1"].vtysh_cmd("show ip bgp json")) + expected = {"routes": {"192.168.100.101/32": [{"valid": True}]}} + return topotest.json_cmp(output, expected) + + test_func = functools.partial(_bgp_has_correct_routes_without_asn_0) + success, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5) + assert result is None, "Failed listing 192.168.100.101/32, SHOULD be accepted." + + +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)) diff --git a/tests/topotests/bgp_basic_functionality_topo1/test_bgp_basic_functionality.py b/tests/topotests/bgp_basic_functionality_topo1/test_bgp_basic_functionality.py index 374cce21f6..485a76c6b2 100644 --- a/tests/topotests/bgp_basic_functionality_topo1/test_bgp_basic_functionality.py +++ b/tests/topotests/bgp_basic_functionality_topo1/test_bgp_basic_functionality.py @@ -774,9 +774,9 @@ def test_BGP_attributes_with_vrf_default_keyword_p0(request): } result = verify_bgp_rib(tgen, addr_type, dut, input_dict) - assert result is True, "Testcase : Failed \n Error: {}".format(tc_name, result) + assert result is True, "Testcase {} : Failed \n Error: {}".format(tc_name, result) result = verify_rib(tgen, addr_type, dut, input_dict) - assert result is True, "Testcase : Failed \n Error: {}".format(tc_name, result) + assert result is True, "Testcase {} : Failed \n Error: {}".format(tc_name, result) for addr_type in ADDR_TYPES: dut = "r4" @@ -793,9 +793,9 @@ def test_BGP_attributes_with_vrf_default_keyword_p0(request): } result = verify_bgp_rib(tgen, addr_type, dut, input_dict) - assert result is True, "Testcase : Failed \n Error: {}".format(tc_name, result) + assert result is True, "Testcase {} : Failed \n Error: {}".format(tc_name, result) result = verify_rib(tgen, addr_type, dut, input_dict) - assert result is True, "Testcase : Failed \n Error: {}".format(tc_name, result) + assert result is True, "Testcase {} : Failed \n Error: {}".format(tc_name, result) input_dict_4 = {"largeCommunity": "500:500:500", "community": "500:500"} @@ -1134,15 +1134,10 @@ def test_bgp_with_loopback_with_same_subnet_p1(request): dut = "r1" protocol = "bgp" for addr_type in ADDR_TYPES: - result = verify_rib(tgen, addr_type, dut, input_dict_r1, protocol=protocol) - assert result is True, "Testcase {} :Failed \n Error: {}".format( - tc_name, result - ) - - result = verify_fib_routes(tgen, addr_type, dut, input_dict_r1, expected=False) - assert result is not True, "Testcase {} : Failed \n" + result = verify_fib_routes(tgen, addr_type, dut, input_dict_r1) + assert result is not True, "Testcase {} : Failed \n".format(tc_name) "Expected behavior: routes should not present in fib \n" - "Error: {}".format(tc_name, result) + "Error: {}".format(result) step("Verify Ipv4 and Ipv6 network installed in r3 RIB but not in FIB") input_dict_r3 = { @@ -1156,17 +1151,10 @@ def test_bgp_with_loopback_with_same_subnet_p1(request): dut = "r3" protocol = "bgp" for addr_type in ADDR_TYPES: - result = verify_rib( - tgen, addr_type, dut, input_dict_r3, protocol=protocol, fib=None - ) - assert result is True, "Testcase {} :Failed \n Error: {}".format( - tc_name, result - ) - - result = verify_fib_routes(tgen, addr_type, dut, input_dict_r1, expected=False) - assert result is not True, "Testcase {} : Failed \n" + result = verify_fib_routes(tgen, addr_type, dut, input_dict_r1) + assert result is not True, "Testcase {} : Failed \n".format(tc_name) "Expected behavior: routes should not present in fib \n" - "Error: {}".format(tc_name, result) + "Error: {}".format(result) write_test_footer(tc_name) diff --git a/tests/topotests/bgp_community_alias/r1/bgpd.conf b/tests/topotests/bgp_community_alias/r1/bgpd.conf index 06113bdd2a..a6366204e8 100644 --- a/tests/topotests/bgp_community_alias/r1/bgpd.conf +++ b/tests/topotests/bgp_community_alias/r1/bgpd.conf @@ -6,4 +6,17 @@ bgp community alias 65001:1:1 large-community-r2-1 router bgp 65001 no bgp ebgp-requires-policy neighbor 192.168.1.2 remote-as external + address-family ipv4 unicast + redistribute connected + neighbor 192.168.1.2 route-map r2 in + exit-address-family +! +route-map r2 permit 10 + match alias community-r2-1 + set tag 10 +route-map r2 permit 20 + match alias community-r2-2 + set tag 20 +route-map r2 permit 30 + set tag 100 ! diff --git a/tests/topotests/bgp_community_alias/r2/bgpd.conf b/tests/topotests/bgp_community_alias/r2/bgpd.conf index fc67ff2ad2..9276fe592d 100644 --- a/tests/topotests/bgp_community_alias/r2/bgpd.conf +++ b/tests/topotests/bgp_community_alias/r2/bgpd.conf @@ -8,6 +8,7 @@ router bgp 65002 ! ip prefix-list p1 permit 172.16.16.1/32 ip prefix-list p2 permit 172.16.16.2/32 +ip prefix-list p3 permit 172.16.16.3/32 ! route-map r1 permit 10 match ip address prefix-list p1 @@ -16,4 +17,6 @@ route-map r1 permit 10 route-map r1 permit 20 match ip address prefix-list p2 set community 65002:1 65002:2 +route-map r1 permit 30 + match ip address prefix-list p3 ! diff --git a/tests/topotests/bgp_community_alias/r2/zebra.conf b/tests/topotests/bgp_community_alias/r2/zebra.conf index a806628a8e..b8cb9baf3c 100644 --- a/tests/topotests/bgp_community_alias/r2/zebra.conf +++ b/tests/topotests/bgp_community_alias/r2/zebra.conf @@ -2,6 +2,7 @@ int lo ip address 172.16.16.1/32 ip address 172.16.16.2/32 + ip address 172.16.16.3/32 ! int r2-eth0 ip address 192.168.1.2/24 diff --git a/tests/topotests/bgp_community_alias/test_bgp-community-alias.py b/tests/topotests/bgp_community_alias/test_bgp-community-alias.py index 90eeaaa731..c41ba810f1 100644 --- a/tests/topotests/bgp_community_alias/test_bgp-community-alias.py +++ b/tests/topotests/bgp_community_alias/test_bgp-community-alias.py @@ -84,39 +84,57 @@ def test_bgp_community_alias(): router = tgen.gears["r1"] def _bgp_converge(router): - output = json.loads( - router.vtysh_cmd("show bgp ipv4 unicast 172.16.16.1/32 json") - ) + output = json.loads(router.vtysh_cmd("show ip route json")) expected = { - "paths": [ + "172.16.16.1/32": [ + { + "tag": 10, + "communities": "community-r2-1 65001:2", + "largeCommunities": "large-community-r2-1 65001:1:2", + } + ], + "172.16.16.2/32": [ + { + "tag": 20, + "communities": "65002:1 community-r2-2", + "largeCommunities": "", + } + ], + "172.16.16.3/32": [ { - "community": {"string": "community-r2-1 65001:2"}, - "largeCommunity": {"string": "large-community-r2-1 65001:1:2"}, + "tag": 100, + "communities": "", + "largeCommunities": "", } - ] + ], } return topotest.json_cmp(output, expected) test_func = functools.partial(_bgp_converge, router) success, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5) - assert result is None, 'Cannot see BGP community aliases "{}"'.format(router) + assert result is None, "Cannot see BGP community aliases at r1" def _bgp_show_prefixes_by_alias(router): output = json.loads( - router.vtysh_cmd("show bgp ipv4 unicast alias community-r2-2 json detail") + router.vtysh_cmd( + "show bgp ipv4 unicast alias large-community-r2-1 json detail" + ) ) expected = { "routes": { - "172.16.16.2/32": [{"community": {"string": "65002:1 community-r2-2"}}] + "172.16.16.1/32": [ + { + "community": {"string": "community-r2-1 65001:2"}, + "largeCommunity": {"string": "large-community-r2-1 65001:1:2"}, + } + ] } } return topotest.json_cmp(output, expected) test_func = functools.partial(_bgp_show_prefixes_by_alias, router) success, result = topotest.run_and_expect(test_func, None, count=60, wait=0.5) - assert result is None, 'Cannot see BGP prefixes by community alias "{}"'.format( - router - ) + assert result is None, "Cannot see BGP prefixes by community alias at r1" if __name__ == "__main__": diff --git a/tests/topotests/bgp_conditional_advertisement/r1/bgpd.conf b/tests/topotests/bgp_conditional_advertisement/r1/bgpd.conf index 633d1832fd..293b38c7e8 100644 --- a/tests/topotests/bgp_conditional_advertisement/r1/bgpd.conf +++ b/tests/topotests/bgp_conditional_advertisement/r1/bgpd.conf @@ -17,6 +17,7 @@ route-map DEF permit 10 ! router bgp 1 bgp log-neighbor-changes + bgp conditional-advertisement timer 5 no bgp ebgp-requires-policy neighbor 10.10.10.2 remote-as 2 ! diff --git a/tests/topotests/bgp_conditional_advertisement/r2/bgpd.conf b/tests/topotests/bgp_conditional_advertisement/r2/bgpd.conf index c6147fe658..82525fac64 100644 --- a/tests/topotests/bgp_conditional_advertisement/r2/bgpd.conf +++ b/tests/topotests/bgp_conditional_advertisement/r2/bgpd.conf @@ -32,6 +32,7 @@ route-map RMAP-2 deny 10 ! router bgp 2 bgp log-neighbor-changes + bgp conditional-advertisement timer 5 no bgp ebgp-requires-policy neighbor 10.10.10.1 remote-as 1 neighbor 10.10.20.3 remote-as 3 diff --git a/tests/topotests/bgp_conditional_advertisement/r3/bgpd.conf b/tests/topotests/bgp_conditional_advertisement/r3/bgpd.conf index 2f4f5068d8..f389f309a6 100644 --- a/tests/topotests/bgp_conditional_advertisement/r3/bgpd.conf +++ b/tests/topotests/bgp_conditional_advertisement/r3/bgpd.conf @@ -1,6 +1,7 @@ ! router bgp 3 bgp log-neighbor-changes + bgp conditional-advertisement timer 5 no bgp ebgp-requires-policy neighbor 10.10.20.2 remote-as 2 ! diff --git a/tests/topotests/bgp_default_route/r2/bgpd.conf b/tests/topotests/bgp_default_route/r2/bgpd.conf index 00c96cc58b..6d1080c119 100644 --- a/tests/topotests/bgp_default_route/r2/bgpd.conf +++ b/tests/topotests/bgp_default_route/r2/bgpd.conf @@ -2,7 +2,4 @@ router bgp 65001 no bgp ebgp-requires-policy neighbor 192.168.255.1 remote-as 65000 neighbor 192.168.255.1 timers 3 10 - address-family ipv4 unicast - redistribute connected - exit-address-family ! diff --git a/tests/topotests/bgp_default_route/test_bgp_default-originate.py b/tests/topotests/bgp_default_route/test_bgp_default-originate.py index d8de0f0ac6..19632162b4 100644 --- a/tests/topotests/bgp_default_route/test_bgp_default-originate.py +++ b/tests/topotests/bgp_default_route/test_bgp_default-originate.py @@ -79,10 +79,10 @@ def test_bgp_default_originate_route_map(): if tgen.routers_have_failure(): pytest.skip(tgen.errors) - router = tgen.gears["r2"] - - def _bgp_converge(router): - output = json.loads(router.vtysh_cmd("show ip bgp neighbor 192.168.255.1 json")) + def _bgp_check_if_received(): + output = json.loads( + tgen.gears["r2"].vtysh_cmd("show ip bgp neighbor 192.168.255.1 json") + ) expected = { "192.168.255.1": { "bgpState": "Established", @@ -91,22 +91,27 @@ def test_bgp_default_originate_route_map(): } return topotest.json_cmp(output, expected) + def _bgp_check_if_originated(): + output = json.loads(tgen.gears["r1"].vtysh_cmd("show ip bgp summary json")) + expected = {"ipv4Unicast": {"peers": {"192.168.255.2": {"pfxSnt": 1}}}} + return topotest.json_cmp(output, expected) + def _bgp_default_route_is_valid(router): output = json.loads(router.vtysh_cmd("show ip bgp 0.0.0.0/0 json")) expected = {"paths": [{"valid": True}]} return topotest.json_cmp(output, expected) - test_func = functools.partial(_bgp_converge, router) + test_func = functools.partial(_bgp_check_if_received) success, result = topotest.run_and_expect(test_func, None, count=30, wait=0.5) + assert result is None, "No 0.0.0.0/0 at r2 from r1" - assert result is None, 'Failed to see bgp convergence in "{}"'.format(router) - - test_func = functools.partial(_bgp_default_route_is_valid, router) + test_func = functools.partial(_bgp_check_if_originated) success, result = topotest.run_and_expect(test_func, None, count=30, wait=0.5) + assert result is None, "No 0.0.0.0/0 from r1 to r2" - assert ( - result is None - ), 'Failed to see applied metric for default route in "{}"'.format(router) + test_func = functools.partial(_bgp_default_route_is_valid, tgen.gears["r2"]) + success, result = topotest.run_and_expect(test_func, None, count=30, wait=0.5) + assert result is None, "Failed to see 0.0.0.0/0 in r2" if __name__ == "__main__": 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 index 086bad6481..fd5bb38b98 100755 --- a/tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py +++ b/tests/topotests/bgp_evpn_vxlan_topo1/test_bgp_evpn_vxlan.py @@ -365,6 +365,10 @@ 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"] @@ -380,6 +384,10 @@ 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"] diff --git a/tests/topotests/conftest.py b/tests/topotests/conftest.py index e57db7471c..d119b0931b 100755 --- a/tests/topotests/conftest.py +++ b/tests/topotests/conftest.py @@ -26,6 +26,12 @@ def pytest_addoption(parser): only run the setup_module() to setup the topology without running any tests. """ parser.addoption( + "--asan-abort", + action="store_true", + help="Configure address sanitizer to abort process on error", + ) + + parser.addoption( "--gdb-breakpoints", metavar="SYMBOL[,SYMBOL...]", help="Comma-separated list of functions to set gdb breakpoints on", @@ -68,6 +74,12 @@ def pytest_addoption(parser): ) parser.addoption( + "--strace-daemons", + metavar="DAEMON[,DAEMON...]", + help="Comma-separated list of daemons to strace, or 'all'", + ) + + parser.addoption( "--topology-only", action="store_true", default=False, @@ -167,6 +179,9 @@ def pytest_configure(config): if not diagnose_env(): pytest.exit("environment has errors, please read the logs") + asan_abort = config.getoption("--asan-abort") + topotest_extra_config["asan_abort"] = asan_abort + gdb_routers = config.getoption("--gdb-routers") gdb_routers = gdb_routers.split(",") if gdb_routers else [] topotest_extra_config["gdb_routers"] = gdb_routers @@ -185,6 +200,9 @@ def pytest_configure(config): shell = config.getoption("--shell") topotest_extra_config["shell"] = shell.split(",") if shell else [] + strace = config.getoption("--strace-daemons") + topotest_extra_config["strace_daemons"] = strace.split(",") if strace else [] + pause_after = config.getoption("--pause-after") shell_on_error = config.getoption("--shell-on-error") @@ -244,6 +262,11 @@ def pytest_runtest_makereport(item, call): ) ) + # We want to pause, if requested, on any error not just test cases + # (e.g., call.when == "setup") + if not pause: + pause = topotest_extra_config["pause_after"] + # (topogen) Set topology error to avoid advancing in the test. tgen = get_topogen() if tgen is not None: diff --git a/tests/topotests/docker/frr-topotests.sh b/tests/topotests/docker/frr-topotests.sh index 9ef59b3bbc..1eaaea2971 100755 --- a/tests/topotests/docker/frr-topotests.sh +++ b/tests/topotests/docker/frr-topotests.sh @@ -145,7 +145,15 @@ if [ "${TOPOTEST_PULL:-1}" = "1" ]; then docker pull frrouting/topotests:latest fi +if [[ -n "$TMUX" ]]; then + TMUX_OPTIONS="-v $(dirname $TMUX):$(dirname $TMUX) -e TMUX=$TMUX -e TMUX_PANE=$TMUX_PANE" +fi + +if [[ -n "$STY" ]]; then + SCREEN_OPTIONS="-v /run/screen:/run/screen -e STY=$STY" +fi set -- --rm -i \ + -v "$HOME:$HOME:ro" \ -v "$TOPOTEST_LOGS:/tmp" \ -v "$TOPOTEST_FRR:/root/host-frr:ro" \ -v "$TOPOTEST_BUILDCACHE:/root/persist" \ @@ -154,6 +162,8 @@ set -- --rm -i \ -e "TOPOTEST_DOC=$TOPOTEST_DOC" \ -e "TOPOTEST_SANITIZER=$TOPOTEST_SANITIZER" \ --privileged \ + $SCREEN_OPTINS \ + $TMUX_OPTIONS \ $TOPOTEST_OPTIONS \ frrouting/topotests:latest "$@" diff --git a/tests/topotests/evpn_type5_test_topo1/evpn_type5_topo1.json b/tests/topotests/evpn_type5_test_topo1/evpn_type5_topo1.json index 14842da326..dd412708bb 100644 --- a/tests/topotests/evpn_type5_test_topo1/evpn_type5_topo1.json +++ b/tests/topotests/evpn_type5_test_topo1/evpn_type5_topo1.json @@ -41,7 +41,10 @@ "neighbor": { "e1": { "dest_link": { - "r1": {} + "r1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -55,7 +58,10 @@ "neighbor": { "e1": { "dest_link": { - "r1": {} + "r1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -106,7 +112,10 @@ "neighbor": { "e1": { "dest_link": { - "r2-link1": {} + "r2-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -120,7 +129,10 @@ "neighbor": { "e1": { "dest_link": { - "r2-link1": {} + "r2-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -140,7 +152,10 @@ "neighbor": { "e1": { "dest_link": { - "r2-link2": {} + "r2-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -154,7 +169,10 @@ "neighbor": { "e1": { "dest_link": { - "r2-link2": {} + "r2-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -222,7 +240,10 @@ "neighbor": { "r1": { "dest_link": { - "e1": {} + "e1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -233,7 +254,10 @@ "neighbor": { "r1": { "dest_link": { - "e1": {} + "e1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -262,7 +286,10 @@ "neighbor": { "r2": { "dest_link": { - "e1-link1": {} + "e1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -273,7 +300,10 @@ "neighbor": { "r2": { "dest_link": { - "e1-link1": {} + "e1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -302,7 +332,10 @@ "neighbor": { "r2": { "dest_link": { - "e1-link2": {} + "e1-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -313,7 +346,10 @@ "neighbor": { "r2": { "dest_link": { - "e1-link2": {} + "e1-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -342,6 +378,8 @@ "d1": { "dest_link": { "e1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3, "deactivate": "ipv4" } } @@ -349,6 +387,8 @@ "d2": { "dest_link": { "e1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3, "deactivate": "ipv4" } } @@ -412,6 +452,8 @@ "e1": { "dest_link": { "d1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3, "deactivate": "ipv4" } } @@ -442,7 +484,10 @@ "neighbor": { "r3": { "dest_link": { - "d1": {} + "d1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -453,7 +498,10 @@ "neighbor": { "r3": { "dest_link": { - "d1": {} + "d1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -482,7 +530,10 @@ "neighbor": { "r4": { "dest_link": { - "d1-link1": {} + "d1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -493,7 +544,10 @@ "neighbor": { "r4": { "dest_link": { - "d1-link1": {} + "d1-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -522,7 +576,10 @@ "neighbor": { "r4": { "dest_link": { - "d1-link2": {} + "d1-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -533,7 +590,10 @@ "neighbor": { "r4": { "dest_link": { - "d1-link2": {} + "d1-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -590,7 +650,9 @@ "e1": { "dest_link": { "d2-link1": { - "deactivate": "ipv4" + "deactivate": "ipv4", + "keepalivetimer": 1, + "holddowntimer": 3 } } } @@ -620,7 +682,10 @@ "neighbor": { "r3": { "dest_link": { - "d2": {} + "d2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -631,7 +696,10 @@ "neighbor": { "r3": { "dest_link": { - "d2": {} + "d2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -660,7 +728,10 @@ "neighbor": { "r4": { "dest_link": { - "d2-link1": {} + "d2-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -671,7 +742,10 @@ "neighbor": { "r4": { "dest_link": { - "d2-link1": {} + "d2-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -700,7 +774,10 @@ "neighbor": { "r4": { "dest_link": { - "d2-link2": {} + "d2-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -711,7 +788,10 @@ "neighbor": { "r4": { "dest_link": { - "d2-link2": {} + "d2-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -755,12 +835,18 @@ "neighbor": { "d1": { "dest_link": { - "r3": {} + "r3": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r3": {} + "r3": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -771,12 +857,18 @@ "neighbor": { "d1": { "dest_link": { - "r3": {} + "r3": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r3": {} + "r3": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -814,12 +906,18 @@ "neighbor": { "d1": { "dest_link": { - "r4-link1": {} + "r4-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r4-link1": {} + "r4-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -830,12 +928,18 @@ "neighbor": { "d1": { "dest_link": { - "r4-link1": {} + "r4-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r4-link1": {} + "r4-link1": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -852,12 +956,18 @@ "neighbor": { "d1": { "dest_link": { - "r4-link2": {} + "r4-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r4-link2": {} + "r4-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -868,12 +978,18 @@ "neighbor": { "d1": { "dest_link": { - "r4-link2": {} + "r4-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } }, "d2": { "dest_link": { - "r4-link2": {} + "r4-link2": { + "keepalivetimer": 1, + "holddowntimer": 3 + } } } } @@ -885,3 +1001,4 @@ } } } + diff --git a/tests/topotests/lib/bgp.py b/tests/topotests/lib/bgp.py index a236a916b5..2f1f67439f 100644 --- a/tests/topotests/lib/bgp.py +++ b/tests/topotests/lib/bgp.py @@ -44,6 +44,7 @@ from lib.common_config import ( FRRCFG_FILE, retry, get_ipv6_linklocal_address, + get_frr_ipv6_linklocal ) LOGDIR = "/tmp/topotests/" @@ -265,6 +266,11 @@ def __create_bgp_global(tgen, input_dict, router, build=False): config_data.append("bgp router-id {}".format(router_id)) config_data.append("no bgp network import-check") + bgp_peer_grp_data = bgp_data.setdefault("peer-group", {}) + + if "peer-group" in bgp_data and bgp_peer_grp_data: + peer_grp_data = __create_bgp_peer_group(tgen, bgp_peer_grp_data, router) + config_data.extend(peer_grp_data) bst_path = bgp_data.setdefault("bestpath", None) if bst_path: @@ -380,6 +386,7 @@ def __create_bgp_unicast_neighbor( addr_data = addr_dict["unicast"] if addr_data: config_data.append("address-family {} unicast".format(addr_type)) + advertise_network = addr_data.setdefault("advertise_networks", []) for advertise_network_dict in advertise_network: network = advertise_network_dict["network"] @@ -404,14 +411,29 @@ def __create_bgp_unicast_neighbor( config_data.append(cmd) + import_cmd = addr_data.setdefault("import", {}) + if import_cmd: + try: + if import_cmd["delete"]: + config_data.append("no import vrf {}".format(import_cmd["vrf"])) + except KeyError: + config_data.append("import vrf {}".format(import_cmd["vrf"])) + max_paths = addr_data.setdefault("maximum_paths", {}) if max_paths: ibgp = max_paths.setdefault("ibgp", None) ebgp = max_paths.setdefault("ebgp", None) + del_cmd = max_paths.setdefault("delete", False) if ibgp: - config_data.append("maximum-paths ibgp {}".format(ibgp)) + if del_cmd: + config_data.append("no maximum-paths ibgp {}".format(ibgp)) + else: + config_data.append("maximum-paths ibgp {}".format(ibgp)) if ebgp: - config_data.append("maximum-paths {}".format(ebgp)) + if del_cmd: + config_data.append("no maximum-paths {}".format(ebgp)) + else: + config_data.append("maximum-paths {}".format(ebgp)) aggregate_addresses = addr_data.setdefault("aggregate_address", []) for aggregate_address in aggregate_addresses: @@ -649,6 +671,38 @@ def __create_l2vpn_evpn_address_family( return config_data +def __create_bgp_peer_group(topo, input_dict, router): + """ + Helper API to create neighbor specific configuration + + Parameters + ---------- + * `topo` : json file data + * `input_dict` : Input dict data, required when configuring from testcase + * `router` : router id to be configured + """ + config_data = [] + logger.debug("Entering lib API: __create_bgp_peer_group()") + + for grp, grp_dict in input_dict.items(): + config_data.append("neighbor {} peer-group".format(grp)) + neigh_cxt = "neighbor {} ".format(grp) + update_source = grp_dict.setdefault("update-source", None) + remote_as = grp_dict.setdefault("remote-as", None) + capability = grp_dict.setdefault("capability", None) + if update_source: + config_data.append("{} update-source {}".format(neigh_cxt, update_source)) + + if remote_as: + config_data.append("{} remote-as {}".format(neigh_cxt, remote_as)) + + if capability: + config_data.append("{} capability {}".format(neigh_cxt, capability)) + + logger.debug("Exiting lib API: __create_bgp_peer_group()") + return config_data + + def __create_bgp_neighbor(topo, input_dict, router, addr_type, add_neigh=True): """ Helper API to create neighbor specific configuration @@ -660,10 +714,9 @@ def __create_bgp_neighbor(topo, input_dict, router, addr_type, add_neigh=True): * `input_dict` : Input dict data, required when configuring from testcase * `router` : router id to be configured """ - config_data = [] logger.debug("Entering lib API: {}".format(sys._getframe().f_code.co_name)) - + tgen = get_topogen() bgp_data = input_dict["address_family"] neigh_data = bgp_data[addr_type]["unicast"]["neighbor"] @@ -672,35 +725,91 @@ def __create_bgp_neighbor(topo, input_dict, router, addr_type, add_neigh=True): nh_details = topo[name] if "vrfs" in topo[router] or type(nh_details["bgp"]) is list: - remote_as = nh_details["bgp"][0]["local_as"] + for vrf_data in nh_details["bgp"]: + if "vrf" in nh_details["links"][dest_link] and "vrf" in vrf_data: + if nh_details["links"][dest_link]["vrf"] == vrf_data["vrf"]: + remote_as = vrf_data["local_as"] + break + else: + if "vrf" not in vrf_data: + remote_as = vrf_data["local_as"] + break + else: remote_as = nh_details["bgp"]["local_as"] update_source = None - if dest_link in nh_details["links"].keys(): - ip_addr = nh_details["links"][dest_link][addr_type].split("/")[0] - # Loopback interface - if "source_link" in peer and peer["source_link"] == "lo": - update_source = topo[router]["links"]["lo"][addr_type].split("/")[0] + if "neighbor_type" in peer and peer["neighbor_type"] == "unnumbered": + ip_addr = nh_details["links"][dest_link]["peer-interface"] + elif "neighbor_type" in peer and peer["neighbor_type"] == "link-local": + intf = topo[name]["links"][dest_link]["interface"] + ip_addr = get_frr_ipv6_linklocal(tgen, name, intf) + elif dest_link in nh_details["links"].keys(): + try: + ip_addr = nh_details["links"][dest_link][addr_type].split("/")[0] + except KeyError: + intf = topo[name]["links"][dest_link]["interface"] + ip_addr = get_frr_ipv6_linklocal(tgen, name, intf) + if "delete" in peer and peer["delete"]: + neigh_cxt = "no neighbor {}".format(ip_addr) + config_data.append("{}".format(neigh_cxt)) + return config_data + else: + neigh_cxt = "neighbor {}".format(ip_addr) - neigh_cxt = "neighbor {}".format(ip_addr) + if "peer-group" in peer: + config_data.append( + "neighbor {} interface peer-group {}".format( + ip_addr, peer["peer-group"] + ) + ) + + # Loopback interface + if "source_link" in peer: + if peer["source_link"] == "lo": + update_source = topo[router]["links"]["lo"][addr_type].split("/")[0] + else: + update_source = topo[router]["links"][peer["source_link"]][ + "interface" + ] + if "peer-group" not in peer: + if "neighbor_type" in peer and peer["neighbor_type"] == "unnumbered": + config_data.append( + "{} interface remote-as {}".format(neigh_cxt, remote_as) + ) + elif add_neigh: + config_data.append("{} remote-as {}".format(neigh_cxt, remote_as)) - if add_neigh: - config_data.append("{} remote-as {}".format(neigh_cxt, remote_as)) if addr_type == "ipv6": config_data.append("address-family ipv6 unicast") config_data.append("{} activate".format(neigh_cxt)) + if "neighbor_type" in peer and peer["neighbor_type"] == "link-local": + config_data.append( + "{} update-source {}".format( + neigh_cxt, nh_details["links"][dest_link]["peer-interface"] + ) + ) + config_data.append( + "{} interface {}".format( + neigh_cxt, nh_details["links"][dest_link]["peer-interface"] + ) + ) + disable_connected = peer.setdefault("disable_connected_check", False) keep_alive = peer.setdefault("keepalivetimer", 3) hold_down = peer.setdefault("holddowntimer", 10) password = peer.setdefault("password", None) no_password = peer.setdefault("no_password", None) + capability = peer.setdefault("capability", None) max_hop_limit = peer.setdefault("ebgp_multihop", 1) + graceful_restart = peer.setdefault("graceful-restart", None) graceful_restart_helper = peer.setdefault("graceful-restart-helper", None) graceful_restart_disable = peer.setdefault("graceful-restart-disable", None) + if capability: + config_data.append("{} capability {}".format(neigh_cxt, capability)) if update_source: config_data.append( @@ -718,7 +827,6 @@ def __create_bgp_neighbor(topo, input_dict, router, addr_type, add_neigh=True): config_data.append( "{} timers {} {}".format(neigh_cxt, keep_alive, hold_down) ) - if graceful_restart: config_data.append("{} graceful-restart".format(neigh_cxt)) elif graceful_restart == False: @@ -768,7 +876,7 @@ def __create_bgp_unicast_address_family( config_data = [] logger.debug("Entering lib API: {}".format(sys._getframe().f_code.co_name)) - + tgen = get_topogen() bgp_data = input_dict["address_family"] neigh_data = bgp_data[addr_type]["unicast"]["neighbor"] @@ -784,16 +892,34 @@ def __create_bgp_unicast_address_family( for destRouterLink, data in sorted(nh_details["links"].items()): if "type" in data and data["type"] == "loopback": if dest_link == destRouterLink: - ip_addr = nh_details["links"][destRouterLink][ - addr_type - ].split("/")[0] + ip_addr = ( + nh_details["links"][destRouterLink][addr_type] + .split("/")[0] + .lower() + ) # Physical interface else: - if dest_link in nh_details["links"].keys(): - - ip_addr = nh_details["links"][dest_link][addr_type].split("/")[0] - if addr_type == "ipv4" and bgp_data["ipv6"]: + # check the neighbor type if un numbered nbr, use interface. + if "neighbor_type" in peer and peer["neighbor_type"] == "unnumbered": + ip_addr = nh_details["links"][dest_link]["peer-interface"] + elif "neighbor_type" in peer and peer["neighbor_type"] == "link-local": + intf = topo[peer_name]["links"][dest_link]["interface"] + ip_addr = get_frr_ipv6_linklocal(tgen, peer_name, intf) + elif dest_link in nh_details["links"].keys(): + try: + ip_addr = nh_details["links"][dest_link][addr_type].split("/")[ + 0 + ] + except KeyError: + intf = topo[peer_name]["links"][dest_link]["interface"] + ip_addr = get_frr_ipv6_linklocal(tgen, peer_name, intf) + if ( + addr_type == "ipv4" + and bgp_data["ipv6"] + and check_address_types("ipv6") + and "ipv6" in nh_details["links"][dest_link] + ): deactivate = nh_details["links"][dest_link]["ipv6"].split("/")[ 0 ] @@ -822,6 +948,7 @@ def __create_bgp_unicast_address_family( prefix_lists = peer.setdefault("prefix_lists", {}) route_maps = peer.setdefault("route_maps", {}) no_send_community = peer.setdefault("no_send_community", None) + capability = peer.setdefault("capability", None) allowas_in = peer.setdefault("allowas-in", None) # next-hop-self @@ -841,6 +968,11 @@ def __create_bgp_unicast_address_family( "no {} send-community {}".format(neigh_cxt, no_send_community) ) + # capability_ext_nh + if capability and addr_type == "ipv6": + config_data.append("address-family ipv4 unicast") + config_data.append("{} activate".format(neigh_cxt)) + if "allowas_in" in peer: allow_as_in = peer["allowas_in"] config_data.append("{} allowas-in {}".format(neigh_cxt, allow_as_in)) @@ -1067,33 +1199,37 @@ def verify_bgp_convergence(tgen, topo, dut=None, expected=True): API will verify if BGP is converged with in the given time frame. Running "show bgp summary json" command and verify bgp neighbor state is established, + Parameters ---------- * `tgen`: topogen object * `topo`: input json file data * `dut`: device under test - * `expected` : expected results from API, by-default True Usage ----- # To veriry is BGP is converged for all the routers used in topology results = verify_bgp_convergence(tgen, topo, dut="r1") + Returns ------- errormsg(str) or True """ - logger.debug("Entering lib API: verify_bgp_convergence()") + result = False + logger.debug("Entering lib API: {}".format(sys._getframe().f_code.co_name)) + tgen = get_topogen() for router, rnode in tgen.routers().items(): - if dut is not None and dut != router: + if 'bgp' not in topo['routers'][router]: continue - if "bgp" not in topo["routers"][router]: + if dut is not None and dut != router: continue logger.info("Verifying BGP Convergence on router %s:", router) - show_bgp_json = run_frr_cmd(rnode, "show bgp vrf all summary json", isjson=True) + show_bgp_json = run_frr_cmd(rnode, "show bgp vrf all summary json", + isjson=True) # Verifying output dictionary show_bgp_json is empty or not if not bool(show_bgp_json): errormsg = "BGP is not running" @@ -1115,100 +1251,6 @@ def verify_bgp_convergence(tgen, topo, dut=None, expected=True): # To find neighbor ip type bgp_addr_type = bgp_data["address_family"] - if "ipv4" in bgp_addr_type or "ipv6" in bgp_addr_type: - for addr_type in bgp_addr_type.keys(): - if not check_address_types(addr_type): - continue - total_peer = 0 - - bgp_neighbors = bgp_addr_type[addr_type]["unicast"]["neighbor"] - - for bgp_neighbor in bgp_neighbors: - total_peer += len(bgp_neighbors[bgp_neighbor]["dest_link"]) - - for addr_type in bgp_addr_type.keys(): - if not check_address_types(addr_type): - continue - bgp_neighbors = bgp_addr_type[addr_type]["unicast"]["neighbor"] - - no_of_peer = 0 - for bgp_neighbor, peer_data in bgp_neighbors.items(): - for dest_link in peer_data["dest_link"].keys(): - data = topo["routers"][bgp_neighbor]["links"] - if dest_link in data: - peer_details = peer_data["dest_link"][dest_link] - # for link local neighbors - if ( - "neighbor_type" in peer_details - and peer_details["neighbor_type"] == "link-local" - ): - neighbor_ip = get_ipv6_linklocal_address( - topo["routers"], bgp_neighbor, dest_link - ) - elif "source_link" in peer_details: - neighbor_ip = topo["routers"][bgp_neighbor][ - "links" - ][peer_details["source_link"]][addr_type].split( - "/" - )[ - 0 - ] - elif ( - "neighbor_type" in peer_details - and peer_details["neighbor_type"] == "unnumbered" - ): - neighbor_ip = data[dest_link]["peer-interface"] - else: - neighbor_ip = data[dest_link][addr_type].split("/")[ - 0 - ] - nh_state = None - - if addr_type == "ipv4": - if "ipv4Unicast" in show_bgp_json[vrf]: - ipv4_data = show_bgp_json[vrf]["ipv4Unicast"][ - "peers" - ] - nh_state = ipv4_data[neighbor_ip]["state"] - else: - if "ipv6Unicast" in show_bgp_json[vrf]: - ipv6_data = show_bgp_json[vrf]["ipv6Unicast"][ - "peers" - ] - nh_state = ipv6_data[neighbor_ip]["state"] - if nh_state == "Established": - no_of_peer += 1 - - if "l2vpn" in bgp_addr_type: - if "neighbor" not in bgp_addr_type["l2vpn"]["evpn"]: - if no_of_peer == total_peer: - logger.info( - "[DUT: %s] VRF: %s, BGP is Converged for %s address-family", - router, - vrf, - addr_type, - ) - else: - errormsg = ( - "[DUT: %s] VRF: %s, BGP is not converged for %s address-family" - % (router, vrf, addr_type) - ) - return errormsg - else: - if no_of_peer == total_peer: - logger.info( - "[DUT: %s] VRF: %s, BGP is Converged for %s address-family", - router, - vrf, - addr_type, - ) - else: - errormsg = ( - "[DUT: %s] VRF: %s, BGP is not converged for %s address-family" - % (router, vrf, addr_type) - ) - return errormsg - if "l2vpn" in bgp_addr_type: total_evpn_peer = 0 @@ -1224,46 +1266,120 @@ def verify_bgp_convergence(tgen, topo, dut=None, expected=True): data = topo["routers"][bgp_neighbor]["links"] for dest_link in dest_link_dict.keys(): if dest_link in data: - peer_details = peer_data[_addr_type][dest_link] + peer_details = \ + peer_data[_addr_type][dest_link] - neighbor_ip = data[dest_link][_addr_type].split("/")[0] + neighbor_ip = \ + data[dest_link][_addr_type].split( + "/")[0] nh_state = None - if ( - "ipv4Unicast" in show_bgp_json[vrf] - or "ipv6Unicast" in show_bgp_json[vrf] - ): - errormsg = ( - "[DUT: %s] VRF: %s, " - "ipv4Unicast/ipv6Unicast" - " address-family present" - " under l2vpn" % (router, vrf) - ) + if "ipv4Unicast" in show_bgp_json[vrf] or \ + "ipv6Unicast" in show_bgp_json[vrf]: + errormsg = ("[DUT: %s] VRF: %s, " + "ipv4Unicast/ipv6Unicast" + " address-family present" + " under l2vpn" % (router, + vrf)) return errormsg - l2VpnEvpn_data = show_bgp_json[vrf]["l2VpnEvpn"][ - "peers" - ] - nh_state = l2VpnEvpn_data[neighbor_ip]["state"] + l2VpnEvpn_data = \ + show_bgp_json[vrf]["l2VpnEvpn"][ + "peers"] + nh_state = \ + l2VpnEvpn_data[neighbor_ip]["state"] if nh_state == "Established": no_of_evpn_peer += 1 if no_of_evpn_peer == total_evpn_peer: - logger.info( - "[DUT: %s] VRF: %s, BGP is Converged for " "epvn peers", - router, - vrf, - ) + logger.info("[DUT: %s] VRF: %s, BGP is Converged for " + "epvn peers", router, vrf) + result = True else: - errormsg = ( - "[DUT: %s] VRF: %s, BGP is not converged " - "for evpn peers" % (router, vrf) - ) + errormsg = ("[DUT: %s] VRF: %s, BGP is not converged " + "for evpn peers" % (router, vrf)) return errormsg + else: + total_peer = 0 + for addr_type in bgp_addr_type.keys(): + if not check_address_types(addr_type): + continue - logger.debug("Exiting API: verify_bgp_convergence()") - return True + bgp_neighbors = \ + bgp_addr_type[addr_type]["unicast"]["neighbor"] + + for bgp_neighbor in bgp_neighbors: + total_peer += \ + len(bgp_neighbors[bgp_neighbor]["dest_link"]) + + no_of_peer = 0 + for addr_type in bgp_addr_type.keys(): + if not check_address_types(addr_type): + continue + bgp_neighbors = \ + bgp_addr_type[addr_type]["unicast"]["neighbor"] + + for bgp_neighbor, peer_data in bgp_neighbors.items(): + for dest_link in peer_data["dest_link"].\ + keys(): + data = \ + topo["routers"][bgp_neighbor]["links"] + if dest_link in data: + peer_details = \ + peer_data['dest_link'][dest_link] + # for link local neighbors + if "neighbor_type" in peer_details and \ + peer_details["neighbor_type"] == \ + 'link-local': + intf = topo["routers"][bgp_neighbor][ + "links"][dest_link]["interface"] + neighbor_ip = get_frr_ipv6_linklocal( + tgen, bgp_neighbor, intf) + elif "source_link" in peer_details: + neighbor_ip = \ + topo["routers"][bgp_neighbor][ + "links"][peer_details[ + 'source_link']][ + addr_type].\ + split("/")[0] + elif "neighbor_type" in peer_details and \ + peer_details["neighbor_type"] == \ + 'unnumbered': + neighbor_ip = \ + data[dest_link]["peer-interface"] + else: + neighbor_ip = \ + data[dest_link][addr_type].split( + "/")[0] + nh_state = None + neighbor_ip = neighbor_ip.lower() + if addr_type == "ipv4": + ipv4_data = show_bgp_json[vrf][ + "ipv4Unicast"]["peers"] + nh_state = \ + ipv4_data[neighbor_ip]["state"] + else: + ipv6_data = show_bgp_json[vrf][ + "ipv6Unicast"]["peers"] + if neighbor_ip in ipv6_data: + nh_state = \ + ipv6_data[neighbor_ip]["state"] + + if nh_state == "Established": + no_of_peer += 1 + + if no_of_peer == total_peer and no_of_peer > 0: + logger.info("[DUT: %s] VRF: %s, BGP is Converged", + router, vrf) + result = True + else: + errormsg = ("[DUT: %s] VRF: %s, BGP is not converged" + % (router, vrf)) + return errormsg + + logger.debug("Exiting lib API: {}".format(sys._getframe().f_code.co_name)) + return result @retry(retry_timeout=16) diff --git a/tests/topotests/lib/common_config.py b/tests/topotests/lib/common_config.py index 9e38608631..6a02e50127 100644 --- a/tests/topotests/lib/common_config.py +++ b/tests/topotests/lib/common_config.py @@ -365,7 +365,7 @@ def create_common_configuration( return True -def kill_router_daemons(tgen, router, daemons): +def kill_router_daemons(tgen, router, daemons, save_config=True): """ Router's current config would be saved to /etc/frr/ for each daemon and daemon would be killed forcefully using SIGKILL. @@ -379,9 +379,10 @@ def kill_router_daemons(tgen, router, daemons): try: router_list = tgen.routers() - # Saving router config to /etc/frr, which will be loaded to router - # when it starts - router_list[router].vtysh_cmd("write memory") + if save_config: + # Saving router config to /etc/frr, which will be loaded to router + # when it starts + router_list[router].vtysh_cmd("write memory") # Kill Daemons result = router_list[router].killDaemons(daemons) @@ -496,7 +497,7 @@ def reset_config_on_routers(tgen, routerName=None): f.close() run_cfg_file = "{}/{}/frr.sav".format(TMPDIR, rname) init_cfg_file = "{}/{}/frr_json_initial.conf".format(TMPDIR, rname) - command = "/usr/lib/frr/frr-reload.py --input {} --test {} > {}".format( + command = "/usr/lib/frr/frr-reload.py --test --test-reset --input {} {} > {}".format( run_cfg_file, init_cfg_file, dname ) result = call(command, shell=True, stderr=SUB_STDOUT, stdout=SUB_PIPE) @@ -526,37 +527,9 @@ def reset_config_on_routers(tgen, routerName=None): raise InvalidCLIError(out_data) raise InvalidCLIError("Unknown error in %s", output) - f = open(dname, "r") delta = StringIO() - delta.write("configure terminal\n") - t_delta = f.read() - - # Don't disable debugs - check_debug = True - - for line in t_delta.split("\n"): - line = line.strip() - if line == "Lines To Delete" or line == "===============" or not line: - continue - - if line == "Lines To Add": - check_debug = False - continue - - if line == "============" or not line: - continue - - # Leave debugs and log output alone - if check_debug: - if "debug" in line or "log file" in line: - continue - - delta.write(line) - delta.write("\n") - - f.close() - - delta.write("end\n") + with open(dname, "r") as f: + delta.write(f.read()) output = router.vtysh_multicmd(delta.getvalue(), pretty_output=False) @@ -636,6 +609,7 @@ def load_config_to_router(tgen, routerName, save_bkup=False): return True + def get_frr_ipv6_linklocal(tgen, router, intf=None, vrf=None): """ API to get the link local ipv6 address of a particular interface using @@ -668,38 +642,48 @@ def get_frr_ipv6_linklocal(tgen, router, intf=None, vrf=None): else: cmd = "show interface" - ifaces = router_list[router].run('vtysh -c "{}"'.format(cmd)) - - # Fix newlines (make them all the same) - ifaces = ("\n".join(ifaces.splitlines()) + "\n").splitlines() - - interface = None - ll_per_if_count = 0 - for line in ifaces: - # Interface name - m = re_search("Interface ([a-zA-Z0-9-]+) is", line) - if m: - interface = m.group(1).split(" ")[0] - ll_per_if_count = 0 - - # Interface ip - m1 = re_search("inet6 (fe80[:a-fA-F0-9]+[/0-9]+)", line) - if m1: - local = m1.group(1) - ll_per_if_count += 1 - if ll_per_if_count > 1: - linklocal += [["%s-%s" % (interface, ll_per_if_count), local]] - else: - linklocal += [[interface, local]] - - if linklocal: - if intf: - return [_linklocal[1] for _linklocal in linklocal if _linklocal[0] == intf][ - 0 - ].split("/")[0] - return linklocal - else: - errormsg = "Link local ip missing on router {}" + linklocal = [] + if vrf: + cmd = "show interface vrf {}".format(vrf) + else: + cmd = "show interface" + for chk_ll in range(0, 60): + sleep(1/4) + ifaces = router_list[router].run('vtysh -c "{}"'.format(cmd)) + # Fix newlines (make them all the same) + ifaces = ('\n'.join(ifaces.splitlines()) + '\n').splitlines() + + interface = None + ll_per_if_count = 0 + for line in ifaces: + # Interface name + m = re_search('Interface ([a-zA-Z0-9-]+) is', line) + if m: + interface = m.group(1).split(" ")[0] + ll_per_if_count = 0 + + # Interface ip + m1 = re_search('inet6 (fe80[:a-fA-F0-9]+[\/0-9]+)', + line) + if m1: + local = m1.group(1) + ll_per_if_count += 1 + if ll_per_if_count > 1: + linklocal += [["%s-%s" % + (interface, ll_per_if_count), local]] + else: + linklocal += [[interface, local]] + + try: + if linklocal: + if intf: + return [_linklocal[1] for _linklocal in linklocal if _linklocal[0]==intf][0].\ + split("/")[0] + return linklocal + except IndexError: + continue + + errormsg = "Link local ip missing on router {}".format(router) return errormsg @@ -712,20 +696,36 @@ def generate_support_bundle(): tgen = get_topogen() router_list = tgen.routers() - test_name = sys._getframe(2).f_code.co_name + test_name = os.environ.get('PYTEST_CURRENT_TEST').split(':')[-1].split(' ')[0] + TMPDIR = os.path.join(LOGDIR, tgen.modname) + bundle_procs = {} for rname, rnode in router_list.items(): - logger.info("Generating support bundle for {}".format(rname)) + logger.info("Spawn collection of support bundle for %s", rname) rnode.run("mkdir -p /var/log/frr") + bundle_procs[rname] = tgen.net[rname].popen( + "/usr/lib/frr/generate_support_bundle.py", + stdin=None, + stdout=SUB_PIPE, + stderr=SUB_PIPE, + ) - # Support only python3 going forward - bundle_log = rnode.run("env python3 /usr/lib/frr/generate_support_bundle.py") - - logger.info(bundle_log) - + for rname, rnode in router_list.items(): dst_bundle = "{}/{}/support_bundles/{}".format(TMPDIR, rname, test_name) src_bundle = "/var/log/frr" + + output, error = bundle_procs[rname].communicate() + + logger.info("Saving support bundle for %s", rname) + if output: + logger.info( + "Output from collecting support bundle for %s:\n%s", rname, output + ) + if error: + logger.warning( + "Error from collecting support bundle for %s:\n%s", rname, error + ) rnode.run("rm -rf {}".format(dst_bundle)) rnode.run("mkdir -p {}".format(dst_bundle)) rnode.run("mv -f {}/* {}".format(src_bundle, dst_bundle)) @@ -1829,6 +1829,14 @@ def create_interfaces_cfg(tgen, topo, build=False): else: interface_data.append("ipv6 address {}".format(intf_addr)) + # Wait for vrf interfaces to get link local address once they are up + if not destRouterLink == 'lo' and 'vrf' in topo[c_router][ + 'links'][destRouterLink]: + vrf = topo[c_router]['links'][destRouterLink]['vrf'] + intf = topo[c_router]['links'][destRouterLink]['interface'] + ll = get_frr_ipv6_linklocal(tgen, c_router, intf=intf, + vrf = vrf) + if "ipv6-link-local" in data: intf_addr = c_data["links"][destRouterLink]["ipv6-link-local"] diff --git a/tests/topotests/lib/topogen.py b/tests/topotests/lib/topogen.py index ade5933504..b998878118 100644 --- a/tests/topotests/lib/topogen.py +++ b/tests/topotests/lib/topogen.py @@ -801,8 +801,8 @@ class TopoRouter(TopoGear): try: return json.loads(output) - except ValueError: - logger.warning("vtysh_cmd: failed to convert json output") + except ValueError as error: + logger.warning("vtysh_cmd: %s: failed to convert json output: %s: %s", self.name, str(output), str(error)) return {} def vtysh_multicmd(self, commands, pretty_output=True, daemon=None): diff --git a/tests/topotests/lib/topotest.py b/tests/topotests/lib/topotest.py index 4c0c6ab54a..b516a67d5c 100644 --- a/tests/topotests/lib/topotest.py +++ b/tests/topotests/lib/topotest.py @@ -1152,6 +1152,18 @@ class Router(Node): self.reportCores = True self.version = None + self.ns_cmd = "sudo nsenter -m -n -t {} ".format(self.pid) + try: + # Allow escaping from running inside docker + cgroup = open("/proc/1/cgroup").read() + m = re.search("[0-9]+:cpuset:/docker/([a-f0-9]+)", cgroup) + if m: + self.ns_cmd = "docker exec -it {} ".format(m.group(1)) + self.ns_cmd + except IOError: + pass + else: + logger.debug("CMD to enter {}: {}".format(self.name, self.ns_cmd)) + def _config_frr(self, **params): "Configure FRR binaries" self.daemondir = params.get("frrdir") @@ -1353,7 +1365,7 @@ class Router(Node): term = topo_terminal if topo_terminal else "xterm" makeTerm(self, title=title if title else cmd, term=term, cmd=cmd) else: - nscmd = "sudo nsenter -m -n -t {} {}".format(self.pid, cmd) + nscmd = self.ns_cmd + cmd if "TMUX" in os.environ: self.cmd("tmux select-layout main-horizontal") wcmd = "tmux split-window -h" @@ -1454,11 +1466,13 @@ class Router(Node): def startRouterDaemons(self, daemons=None): "Starts all FRR daemons for this router." + asan_abort = g_extra_config["asan_abort"] gdb_breakpoints = g_extra_config["gdb_breakpoints"] gdb_daemons = g_extra_config["gdb_daemons"] gdb_routers = g_extra_config["gdb_routers"] valgrind_extra = g_extra_config["valgrind_extra"] valgrind_memleaks = g_extra_config["valgrind_memleaks"] + strace_daemons = g_extra_config["strace_daemons"] bundle_data = "" @@ -1485,7 +1499,6 @@ class Router(Node): os.path.join(self.daemondir, "bgpd") + " -v" ).split()[2] logger.info("{}: running version: {}".format(self.name, self.version)) - # If `daemons` was specified then some upper API called us with # specific daemons, otherwise just use our own configuration. daemons_list = [] @@ -1509,13 +1522,20 @@ class Router(Node): else: binary = os.path.join(self.daemondir, daemon) - cmdenv = "ASAN_OPTIONS=log_path={0}.asan".format(daemon) + cmdenv = "ASAN_OPTIONS=" + if asan_abort: + cmdenv = "abort_on_error=1:" + cmdenv += "log_path={0}/{1}.{2}.asan ".format(self.logdir, self.name, daemon) + if valgrind_memleaks: this_dir = os.path.dirname(os.path.abspath(os.path.realpath(__file__))) supp_file = os.path.abspath(os.path.join(this_dir, "../../../tools/valgrind.supp")) cmdenv += " /usr/bin/valgrind --num-callers=50 --log-file={1}/{2}.valgrind.{0}.%p --leak-check=full --suppressions={3}".format(daemon, self.logdir, self.name, supp_file) if valgrind_extra: cmdenv += "--gen-suppressions=all --expensive-definedness-checks=yes" + elif daemon in strace_daemons or "all" in strace_daemons: + cmdenv = "strace -f -D -o {1}/{2}.strace.{0} ".format(daemon, self.logdir, self.name) + cmdopt = "{} --log file:{}.log --log-level debug".format( daemon_opts, daemon ) diff --git a/tests/topotests/multicast_pim_sm_topo1/test_multicast_pim_sm_topo1.py b/tests/topotests/multicast_pim_sm_topo1/test_multicast_pim_sm_topo1.py index e55e30270d..b880e0e462 100755 --- a/tests/topotests/multicast_pim_sm_topo1/test_multicast_pim_sm_topo1.py +++ b/tests/topotests/multicast_pim_sm_topo1/test_multicast_pim_sm_topo1.py @@ -526,9 +526,14 @@ def test_multicast_data_traffic_static_RP_send_traffic_then_join_p0(request): {"dut": "r2", "src_address": source, "iif": "r2-f1-eth0", "oil": "r2-l1-eth2"}, {"dut": "f1", "src_address": source, "iif": "f1-i2-eth1", "oil": "f1-r2-eth3"}, ] + # On timeout change from default of 80 to 120: failures logs indicate times 90+ + # seconds for success on the 2nd entry in the above table. Using 100s here restores + # previous 80 retries with 2s wait if we assume .5s per vtysh/show ip mroute runtime + # (41 * (2 + .5)) == 102. for data in input_dict: result = verify_ip_mroutes( - tgen, data["dut"], data["src_address"], IGMP_JOIN, data["iif"], data["oil"] + tgen, data["dut"], data["src_address"], IGMP_JOIN, data["iif"], data["oil"], + retry_timeout=102 ) assert result is True, "Testcase {} : Failed Error: {}".format(tc_name, result) diff --git a/tests/topotests/ospf_gr_topo1/__init__.py b/tests/topotests/ospf_gr_topo1/__init__.py new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/__init__.py diff --git a/tests/topotests/ospf_gr_topo1/rt1/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt1/ospfd.conf new file mode 100644 index 0000000000..9c04b74d35 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/ospfd.conf @@ -0,0 +1,32 @@ +password 1 +hostname rt1 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 1 +! +interface eth-rt2 + ip ospf network point-to-point + ip ospf area 1 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 1.1.1.1 + capability opaque + redistribute connected + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_database.json new file mode 100644 index 0000000000..d01ac74c17 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_database.json @@ -0,0 +1,98 @@ +{ + "routerId":"1.1.1.1", + "areas":{ + "0.0.0.1":{ + "routerLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"1.1.1.1", + "numOfRouterLinks":3 + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":2 + } + ], + "summaryLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"6.6.6.6", + "advertisedRouter":"2.2.2.2" + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..ed290323a4 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_neighbor.json @@ -0,0 +1,11 @@ +{ + "neighbors":{ + "2.2.2.2":[ + { + "state":"Full\/DROther", + "address":"10.0.1.2", + "ifaceName":"eth-rt2:10.0.1.1" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_route.json new file mode 100644 index 0000000000..548ca1e2d1 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/show_ip_ospf_route.json @@ -0,0 +1,180 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N IA", + "cost":10, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt2" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "2.2.2.2":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.1", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":30, + "area":"0.0.0.1", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":40, + "nexthops":[ + { + "ip":"10.0.1.2", + "via":"eth-rt2" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt1/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt1/show_ip_route.json new file mode 100644 index 0000000000..3dce1eee3e --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/show_ip_route.json @@ -0,0 +1,210 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.1.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt1/zebra.conf b/tests/topotests/ospf_gr_topo1/rt1/zebra.conf new file mode 100644 index 0000000000..183cd3df48 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt1/zebra.conf @@ -0,0 +1,23 @@ +password 1 +hostname rt1 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 1.1.1.1/32 +! +interface stub1 + ip address 172.16.1.1/24 +! +interface eth-rt2 + ip address 10.0.1.1/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt2/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt2/ospfd.conf new file mode 100644 index 0000000000..922db8c8cc --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/ospfd.conf @@ -0,0 +1,37 @@ +password 1 +hostname rt2 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 0 +! +interface eth-rt1 + ip ospf network point-to-point + ip ospf area 1 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +interface eth-rt3 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 2.2.2.2 + capability opaque + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_database.json new file mode 100644 index 0000000000..40c3e82d6a --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_database.json @@ -0,0 +1,160 @@ +{ + "routerId":"2.2.2.2", + "areas":{ + "0.0.0.0":{ + "routerLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":3 + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"3.3.3.3", + "numOfRouterLinks":7 + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":3 + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2" + } + ] + }, + "0.0.0.1":{ + "routerLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"1.1.1.1", + "numOfRouterLinks":3 + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":2 + } + ], + "summaryLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"6.6.6.6", + "advertisedRouter":"2.2.2.2" + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..4fe92b0b98 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_neighbor.json @@ -0,0 +1,18 @@ +{ + "neighbors":{ + "1.1.1.1":[ + { + "state":"Full\/DROther", + "address":"10.0.1.1", + "ifaceName":"eth-rt1:10.0.1.2" + } + ], + "3.3.3.3":[ + { + "state":"Full\/DROther", + "address":"10.0.2.3", + "ifaceName":"eth-rt3:10.0.2.2" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_route.json new file mode 100644 index 0000000000..4accb2ba4a --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/show_ip_ospf_route.json @@ -0,0 +1,201 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":"10.0.1.1", + "via":"eth-rt1" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.1", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt1" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt3" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "1.1.1.1":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.1", + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.1.1", + "via":"eth-rt1" + } + ] + }, + "4.4.4.4":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + }, + "172.16.1.0\/24":{ + "routeType":"N E2", + "cost":10, + "nexthops":[ + { + "ip":"10.0.1.1", + "via":"eth-rt1" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":30, + "nexthops":[ + { + "ip":"10.0.2.3", + "via":"eth-rt3" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt2/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt2/show_ip_route.json new file mode 100644 index 0000000000..8989a45765 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/show_ip_route.json @@ -0,0 +1,224 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.1.1", + "afi":"ipv4", + "interfaceName":"eth-rt1" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt1" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "172.16.1.0\/24":[ + { + "prefix":"172.16.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.1.1", + "afi":"ipv4", + "interfaceName":"eth-rt1" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt2/zebra.conf b/tests/topotests/ospf_gr_topo1/rt2/zebra.conf new file mode 100644 index 0000000000..8bde98ad44 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt2/zebra.conf @@ -0,0 +1,23 @@ +password 1 +hostname rt2 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 2.2.2.2/32 +! +interface eth-rt1 + ip address 10.0.1.2/24 +! +interface eth-rt3 + ip address 10.0.2.2/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt3/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt3/ospfd.conf new file mode 100644 index 0000000000..51e48f13da --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/ospfd.conf @@ -0,0 +1,43 @@ +password 1 +hostname rt3 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 0 +! +interface eth-rt2 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +interface eth-rt4 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +interface eth-rt6 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 3.3.3.3 + capability opaque + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_database.json new file mode 100644 index 0000000000..1fc5b546e4 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_database.json @@ -0,0 +1,83 @@ +{ + "routerId":"3.3.3.3", + "areas":{ + "0.0.0.0":{ + "routerLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":3 + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"3.3.3.3", + "numOfRouterLinks":7 + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":3 + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2" + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..e3c36ab9a3 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_neighbor.json @@ -0,0 +1,25 @@ +{ + "neighbors":{ + "2.2.2.2":[ + { + "state":"Full\/DROther", + "address":"10.0.2.2", + "ifaceName":"eth-rt2:10.0.2.3" + } + ], + "4.4.4.4":[ + { + "state":"Full\/DROther", + "address":"10.0.3.4", + "ifaceName":"eth-rt4:10.0.3.3" + } + ], + "6.6.6.6":[ + { + "state":"Full\/DROther", + "address":"10.0.4.6", + "ifaceName":"eth-rt6:10.0.4.3" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_route.json new file mode 100644 index 0000000000..b2f37e25a1 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/show_ip_ospf_route.json @@ -0,0 +1,214 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.4", + "via":"eth-rt4" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.4", + "via":"eth-rt4" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.6", + "via":"eth-rt6" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.6", + "via":"eth-rt6" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt2" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt4" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt6" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.4", + "via":"eth-rt4" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.6", + "via":"eth-rt6" + } + ] + }, + "1.1.1.1":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "2.2.2.2":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "4.4.4.4":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.3.4", + "via":"eth-rt4" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.4.6", + "via":"eth-rt6" + } + ] + }, + "172.16.1.0\/24":{ + "routeType":"N E2", + "cost":20, + "nexthops":[ + { + "ip":"10.0.2.2", + "via":"eth-rt2" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":20, + "nexthops":[ + { + "ip":"10.0.4.6", + "via":"eth-rt6" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt3/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt3/show_ip_route.json new file mode 100644 index 0000000000..c9a1e18b92 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/show_ip_route.json @@ -0,0 +1,223 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.2.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.3.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.4.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt2" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "172.16.1.0\/24":[ + { + "prefix":"172.16.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.2.2", + "afi":"ipv4", + "interfaceName":"eth-rt2" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt3/zebra.conf b/tests/topotests/ospf_gr_topo1/rt3/zebra.conf new file mode 100644 index 0000000000..dfd89cbe5b --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt3/zebra.conf @@ -0,0 +1,26 @@ +password 1 +hostname rt3 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 3.3.3.3/32 +! +interface eth-rt2 + ip address 10.0.2.3/24 +! +interface eth-rt4 + ip address 10.0.3.3/24 +! +interface eth-rt6 + ip address 10.0.4.3/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt4/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt4/ospfd.conf new file mode 100644 index 0000000000..a54f27a1d7 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/ospfd.conf @@ -0,0 +1,37 @@ +password 1 +hostname rt4 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 0 +! +interface eth-rt3 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +interface eth-rt5 + ip ospf network point-to-point + ip ospf area 2 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 4.4.4.4 + capability opaque + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_database.json new file mode 100644 index 0000000000..87b80414c9 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_database.json @@ -0,0 +1,164 @@ +{ + "routerId":"4.4.4.4", + "areas":{ + "0.0.0.0":{ + "routerLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":3 + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"3.3.3.3", + "numOfRouterLinks":7 + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":3 + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2" + } + ] + }, + "0.0.0.2":{ + "routerLinkStates":[ + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":2 + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"5.5.5.5", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"4.4.4.4" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"4.4.4.4" + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..2123ecb8da --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_neighbor.json @@ -0,0 +1,18 @@ +{ + "neighbors":{ + "3.3.3.3":[ + { + "state":"Full\/DROther", + "address":"10.0.3.3", + "ifaceName":"eth-rt3:10.0.3.4" + } + ], + "5.5.5.5":[ + { + "state":"Full\/DROther", + "address":"10.0.5.5", + "ifaceName":"eth-rt5:10.0.5.4" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_route.json new file mode 100644 index 0000000000..04e318aef0 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/show_ip_ospf_route.json @@ -0,0 +1,202 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.5", + "via":"eth-rt5" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt3" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt5" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "1.1.1.1":{ + "routeType":"R ", + "cost":30, + "area":"0.0.0.0", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "2.2.2.2":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "172.16.1.0\/24":{ + "routeType":"N E2", + "cost":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "via":"eth-rt3" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt4/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt4/show_ip_route.json new file mode 100644 index 0000000000..8058f8f431 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/show_ip_route.json @@ -0,0 +1,224 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.5.5", + "afi":"ipv4", + "interfaceName":"eth-rt5" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt5" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "172.16.1.0\/24":[ + { + "prefix":"172.16.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.3.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt4/zebra.conf b/tests/topotests/ospf_gr_topo1/rt4/zebra.conf new file mode 100644 index 0000000000..f399b29f3f --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt4/zebra.conf @@ -0,0 +1,23 @@ +password 1 +hostname rt4 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 4.4.4.4/32 +! +interface eth-rt3 + ip address 10.0.3.4/24 +! +interface eth-rt5 + ip address 10.0.5.4/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt5/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt5/ospfd.conf new file mode 100644 index 0000000000..724af0e97c --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/ospfd.conf @@ -0,0 +1,31 @@ +password 1 +hostname rt5 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 2 +! +interface eth-rt4 + ip ospf network point-to-point + ip ospf area 2 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 5.5.5.5 + capability opaque + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_database.json new file mode 100644 index 0000000000..aeb8604473 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_database.json @@ -0,0 +1,102 @@ +{ + "routerId":"5.5.5.5", + "areas":{ + "0.0.0.2":{ + "routerLinkStates":[ + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":2 + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"5.5.5.5", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"4.4.4.4" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"4.4.4.4" + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..6440b67698 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_neighbor.json @@ -0,0 +1,11 @@ +{ + "neighbors":{ + "4.4.4.4":[ + { + "state":"Full\/DROther", + "address":"10.0.5.4", + "ifaceName":"eth-rt4:10.0.5.5" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_route.json new file mode 100644 index 0000000000..e7f712ea6b --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/show_ip_ospf_route.json @@ -0,0 +1,203 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N IA", + "cost":10, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt4" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.2", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "1.1.1.1":{ + "routeType":"R ", + "cost":40, + "area":"0.0.0.2", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "4.4.4.4":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.2", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":30, + "area":"0.0.0.2", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "172.16.1.0\/24":{ + "routeType":"N E2", + "cost":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "via":"eth-rt4" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt5/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt5/show_ip_route.json new file mode 100644 index 0000000000..9896839440 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/show_ip_route.json @@ -0,0 +1,225 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt4" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "172.16.1.0\/24":[ + { + "prefix":"172.16.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.5.4", + "afi":"ipv4", + "interfaceName":"eth-rt4" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt5/zebra.conf b/tests/topotests/ospf_gr_topo1/rt5/zebra.conf new file mode 100644 index 0000000000..49a1c05a6d --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt5/zebra.conf @@ -0,0 +1,20 @@ +password 1 +hostname rt5 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 5.5.5.5/32 +! +interface eth-rt4 + ip address 10.0.5.5/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt6/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt6/ospfd.conf new file mode 100644 index 0000000000..0b9b83bcd2 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/ospfd.conf @@ -0,0 +1,38 @@ +password 1 +hostname rt6 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 0 +! +interface eth-rt3 + ip ospf network point-to-point + ip ospf area 0 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +interface eth-rt7 + ip ospf network point-to-point + ip ospf area 3 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 6.6.6.6 + capability opaque + area 3 nssa + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_database.json new file mode 100644 index 0000000000..294b2c904e --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_database.json @@ -0,0 +1,168 @@ +{ + "routerId":"6.6.6.6", + "areas":{ + "0.0.0.0":{ + "routerLinkStates":[ + { + "lsId":"2.2.2.2", + "advertisedRouter":"2.2.2.2", + "numOfRouterLinks":3 + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"3.3.3.3", + "numOfRouterLinks":7 + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"4.4.4.4", + "numOfRouterLinks":3 + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"7.7.7.7\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"2.2.2.2", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"4.4.4.4", + "summaryAddress":"10.0.5.0\/24" + }, + { + "lsId":"10.0.6.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.6.0\/24" + } + ], + "asbrSummaryLinkStates":[ + { + "lsId":"1.1.1.1", + "advertisedRouter":"2.2.2.2" + } + ] + }, + "0.0.0.3":{ + "routerLinkStates":[ + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":2 + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"7.7.7.7", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"0.0.0.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"0.0.0.0\/0" + }, + { + "lsId":"1.1.1.1", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.5.0\/24" + } + ], + "nssaExternalLinkStates":[ + { + "lsId":"192.168.1.0", + "advertisedRouter":"7.7.7.7", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"172.16.1.0", + "advertisedRouter":"1.1.1.1", + "metricType":"E2", + "route":"172.16.1.0\/24", + "tag":0 + }, + { + "lsId":"192.168.1.0", + "advertisedRouter":"6.6.6.6", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..d815c23927 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_neighbor.json @@ -0,0 +1,18 @@ +{ + "neighbors":{ + "3.3.3.3":[ + { + "state":"Full\/DROther", + "address":"10.0.4.3", + "ifaceName":"eth-rt3:10.0.4.6" + } + ], + "7.7.7.7":[ + { + "state":"Full\/DROther", + "address":"10.0.6.7", + "ifaceName":"eth-rt7:10.0.6.6" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_route.json new file mode 100644 index 0000000000..d9009724d5 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/show_ip_ospf_route.json @@ -0,0 +1,214 @@ +{ + "1.1.1.1\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.7", + "via":"eth-rt7" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N", + "cost":20, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt3" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.0", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt7" + } + ] + }, + "1.1.1.1":{ + "routeType":"R ", + "cost":30, + "area":"0.0.0.0", + "IA":true, + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "2.2.2.2":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "4.4.4.4":{ + "routeType":"R ", + "cost":20, + "area":"0.0.0.0", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "7.7.7.7":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.3", + "routerType":"asbr", + "nexthops":[ + { + "ip":"10.0.6.7", + "via":"eth-rt7" + } + ] + }, + "172.16.1.0\/24":{ + "routeType":"N E2", + "cost":30, + "nexthops":[ + { + "ip":"10.0.4.3", + "via":"eth-rt3" + } + ] + }, + "192.168.1.0\/24":{ + "routeType":"N E2", + "cost":10, + "nexthops":[ + { + "ip":"10.0.6.7", + "via":"eth-rt7" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt6/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt6/show_ip_route.json new file mode 100644 index 0000000000..dd95f1fab1 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/show_ip_route.json @@ -0,0 +1,224 @@ +{ + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.6.7", + "afi":"ipv4", + "interfaceName":"eth-rt7" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt7" + } + ] + } + ], + "172.16.1.0\/24":[ + { + "prefix":"172.16.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.4.3", + "afi":"ipv4", + "interfaceName":"eth-rt3" + } + ] + } + ], + "192.168.1.0\/24":[ + { + "prefix":"192.168.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.6.7", + "afi":"ipv4", + "interfaceName":"eth-rt7" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt6/zebra.conf b/tests/topotests/ospf_gr_topo1/rt6/zebra.conf new file mode 100644 index 0000000000..d6a8f52b3a --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt6/zebra.conf @@ -0,0 +1,23 @@ +password 1 +hostname rt6 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 6.6.6.6/32 +! +interface eth-rt3 + ip address 10.0.4.6/24 +! +interface eth-rt7 + ip address 10.0.6.6/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/rt7/ospfd.conf b/tests/topotests/ospf_gr_topo1/rt7/ospfd.conf new file mode 100644 index 0000000000..49db254410 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/ospfd.conf @@ -0,0 +1,33 @@ +password 1 +hostname rt7 +log file ospfd.log +log commands +! +debug ospf zebra +debug ospf event +debug ospf lsa +debug ospf te +debug ospf packet all +debug ospf packet ls-update detail +debug ospf ism +debug ospf nsm +debug ospf nssa +debug ospf graceful-restart +! +interface lo + ip ospf area 3 +! +interface eth-rt6 + ip ospf network point-to-point + ip ospf area 3 + ip ospf hello-interval 3 + ip ospf dead-interval 9 +! +router ospf + router-id 7.7.7.7 + capability opaque + redistribute connected + area 3 nssa + graceful-restart grace-period 120 + graceful-restart helper-only +! diff --git a/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_database.json b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_database.json new file mode 100644 index 0000000000..4916fba9d4 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_database.json @@ -0,0 +1,99 @@ +{ + "routerId":"7.7.7.7", + "areas":{ + "0.0.0.3":{ + "routerLinkStates":[ + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "numOfRouterLinks":2 + }, + { + "lsId":"7.7.7.7", + "advertisedRouter":"7.7.7.7", + "numOfRouterLinks":3 + } + ], + "summaryLinkStates":[ + { + "lsId":"0.0.0.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"0.0.0.0\/0" + }, + { + "lsId":"1.1.1.1", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"1.1.1.1\/32" + }, + { + "lsId":"2.2.2.2", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"2.2.2.2\/32" + }, + { + "lsId":"3.3.3.3", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"3.3.3.3\/32" + }, + { + "lsId":"4.4.4.4", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"4.4.4.4\/32" + }, + { + "lsId":"5.5.5.5", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"5.5.5.5\/32" + }, + { + "lsId":"6.6.6.6", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"6.6.6.6\/32" + }, + { + "lsId":"10.0.1.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.1.0\/24" + }, + { + "lsId":"10.0.2.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.2.0\/24" + }, + { + "lsId":"10.0.3.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.3.0\/24" + }, + { + "lsId":"10.0.4.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.4.0\/24" + }, + { + "lsId":"10.0.5.0", + "advertisedRouter":"6.6.6.6", + "summaryAddress":"10.0.5.0\/24" + } + ], + "nssaExternalLinkStates":[ + { + "lsId":"192.168.1.0", + "advertisedRouter":"7.7.7.7", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] + } + }, + "asExternalLinkStates":[ + { + "lsId":"192.168.1.0", + "advertisedRouter":"7.7.7.7", + "metricType":"E2", + "route":"192.168.1.0\/24", + "tag":0 + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_neighbor.json b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_neighbor.json new file mode 100644 index 0000000000..2254aea9a6 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_neighbor.json @@ -0,0 +1,11 @@ +{ + "neighbors":{ + "6.6.6.6":[ + { + "state":"Full\/DROther", + "address":"10.0.6.6", + "ifaceName":"eth-rt6:10.0.6.7" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_route.json b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_route.json new file mode 100644 index 0000000000..89bad320bb --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/show_ip_ospf_route.json @@ -0,0 +1,168 @@ +{ + "0.0.0.0\/0":{ + "routeType":"N IA", + "cost":11, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "1.1.1.1\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "2.2.2.2\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "3.3.3.3\/32":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "4.4.4.4\/32":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "5.5.5.5\/32":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "6.6.6.6\/32":{ + "routeType":"N IA", + "cost":10, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "7.7.7.7\/32":{ + "routeType":"N", + "cost":0, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":" ", + "directly attached to":"lo" + } + ] + }, + "10.0.1.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "10.0.2.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "10.0.3.0\/24":{ + "routeType":"N IA", + "cost":30, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "10.0.4.0\/24":{ + "routeType":"N IA", + "cost":20, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "10.0.5.0\/24":{ + "routeType":"N IA", + "cost":40, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + }, + "10.0.6.0\/24":{ + "routeType":"N", + "cost":10, + "area":"0.0.0.3", + "nexthops":[ + { + "ip":" ", + "directly attached to":"eth-rt6" + } + ] + }, + "6.6.6.6":{ + "routeType":"R ", + "cost":10, + "area":"0.0.0.3", + "routerType":"abr", + "nexthops":[ + { + "ip":"10.0.6.6", + "via":"eth-rt6" + } + ] + } +} diff --git a/tests/topotests/ospf_gr_topo1/rt7/show_ip_route.json b/tests/topotests/ospf_gr_topo1/rt7/show_ip_route.json new file mode 100644 index 0000000000..0fb906b76b --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/show_ip_route.json @@ -0,0 +1,210 @@ +{ + "0.0.0.0\/0":[ + { + "prefix":"0.0.0.0\/0", + "protocol":"ospf", + "distance":110, + "metric":11, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "1.1.1.1\/32":[ + { + "prefix":"1.1.1.1\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "2.2.2.2\/32":[ + { + "prefix":"2.2.2.2\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "3.3.3.3\/32":[ + { + "prefix":"3.3.3.3\/32", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "4.4.4.4\/32":[ + { + "prefix":"4.4.4.4\/32", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "5.5.5.5\/32":[ + { + "prefix":"5.5.5.5\/32", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "6.6.6.6\/32":[ + { + "prefix":"6.6.6.6\/32", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "7.7.7.7\/32":[ + { + "prefix":"7.7.7.7\/32", + "protocol":"ospf", + "distance":110, + "metric":0, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"lo" + } + ] + } + ], + "10.0.1.0\/24":[ + { + "prefix":"10.0.1.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.2.0\/24":[ + { + "prefix":"10.0.2.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.3.0\/24":[ + { + "prefix":"10.0.3.0\/24", + "protocol":"ospf", + "distance":110, + "metric":30, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.4.0\/24":[ + { + "prefix":"10.0.4.0\/24", + "protocol":"ospf", + "distance":110, + "metric":20, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.5.0\/24":[ + { + "prefix":"10.0.5.0\/24", + "protocol":"ospf", + "distance":110, + "metric":40, + "nexthops":[ + { + "ip":"10.0.6.6", + "afi":"ipv4", + "interfaceName":"eth-rt6" + } + ] + } + ], + "10.0.6.0\/24":[ + { + "prefix":"10.0.6.0\/24", + "protocol":"ospf", + "distance":110, + "metric":10, + "nexthops":[ + { + "directlyConnected":true, + "interfaceName":"eth-rt6" + } + ] + } + ] +} diff --git a/tests/topotests/ospf_gr_topo1/rt7/zebra.conf b/tests/topotests/ospf_gr_topo1/rt7/zebra.conf new file mode 100644 index 0000000000..c481e4532b --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/rt7/zebra.conf @@ -0,0 +1,23 @@ +password 1 +hostname rt7 +log file zebra.log +log commands +! +debug zebra event +debug zebra packet +debug zebra rib +debug zebra kernel +! +interface lo + ip address 7.7.7.7/32 +! +interface stub1 + ip address 192.168.1.1/24 +! +interface eth-rt6 + ip address 10.0.6.7/24 +! +ip forwarding +! +line vty +! diff --git a/tests/topotests/ospf_gr_topo1/test_ospf_gr_topo1.py b/tests/topotests/ospf_gr_topo1/test_ospf_gr_topo1.py new file mode 100755 index 0000000000..0507c2d516 --- /dev/null +++ b/tests/topotests/ospf_gr_topo1/test_ospf_gr_topo1.py @@ -0,0 +1,393 @@ +#!/usr/bin/env python + +# +# test_ospf_gr_topo1.py +# Part of NetDEF Topology Tests +# +# Copyright (c) 2021 by +# Network Device Education Foundation, Inc. ("NetDEF") +# +# 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_ospf_gr_topo1.py: + + +---------+ + | RT1 | + | 1.1.1.1 | + +---------+ + |eth-rt2 + | + |10.0.1.0/24 + | + |eth-rt1 + +---------+ + | RT2 | + | 2.2.2.2 | + +---------+ + |eth-rt3 + | + |10.0.2.0/24 + | + |eth-rt2 + +---------+ + | RT3 | + | 3.3.3.3 | + +---------+ + eth-rt4| |eth-rt6 + | | + 10.0.3.0/24 | | 10.0.4.0/24 + +---------+ +--------+ + | | + |eth-rt3 |eth-rt3 + +---------+ +---------+ + | RT4 | | RT6 | + | 4.4.4.4 | | 6.6.6.6 | + +---------+ +---------+ + |eth-rt5 |eth-rt7 + | | + |10.0.5.0/24 |10.0.6.0/24 + | | + |eth-rt4 |eth-rt6 + +---------+ +---------+ + | RT5 | | RT7 | + | 5.5.5.5 | | 7.7.7.7 | + +---------+ +---------+ +""" + +import os +import sys +import pytest +import json +import re +import tempfile +from time import sleep +from functools import partial + +# 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 +from lib.common_config import ( + kill_router_daemons, + start_router_daemons, +) + +# Required to instantiate the topology builder class. +from mininet.topo import Topo + +pytestmark = [pytest.mark.ospfd] + +# Global multi-dimensional dictionary containing all expected outputs +outputs = {} + + +class TemplateTopo(Topo): + "Test topology builder" + + def build(self, *_args, **_opts): + "Build function" + tgen = get_topogen(self) + + # + # Define FRR Routers + # + for router in ["rt1", "rt2", "rt3", "rt4", "rt5", "rt6", "rt7"]: + tgen.add_router(router) + + # + # Define connections + # + switch = tgen.add_switch("s1") + switch.add_link(tgen.gears["rt1"], nodeif="eth-rt2") + switch.add_link(tgen.gears["rt2"], nodeif="eth-rt1") + + switch = tgen.add_switch("s2") + switch.add_link(tgen.gears["rt1"], nodeif="stub1") + + switch = tgen.add_switch("s3") + switch.add_link(tgen.gears["rt2"], nodeif="eth-rt3") + switch.add_link(tgen.gears["rt3"], nodeif="eth-rt2") + + switch = tgen.add_switch("s4") + switch.add_link(tgen.gears["rt3"], nodeif="eth-rt4") + switch.add_link(tgen.gears["rt4"], nodeif="eth-rt3") + + switch = tgen.add_switch("s5") + switch.add_link(tgen.gears["rt3"], nodeif="eth-rt6") + switch.add_link(tgen.gears["rt6"], nodeif="eth-rt3") + + switch = tgen.add_switch("s6") + switch.add_link(tgen.gears["rt4"], nodeif="eth-rt5") + switch.add_link(tgen.gears["rt5"], nodeif="eth-rt4") + + switch = tgen.add_switch("s7") + switch.add_link(tgen.gears["rt6"], nodeif="eth-rt7") + switch.add_link(tgen.gears["rt7"], nodeif="eth-rt6") + + switch = tgen.add_switch("s8") + switch.add_link(tgen.gears["rt7"], nodeif="stub1") + + +def setup_module(mod): + "Sets up the pytest environment" + tgen = Topogen(TemplateTopo, mod.__name__) + tgen.start_topology() + + 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)) + ) + + 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 router_compare_json_output(rname, command, reference, tries): + "Compare router JSON output" + + logger.info('Comparing router "%s" "%s" output', rname, command) + + tgen = get_topogen() + filename = "{}/{}/{}".format(CWD, rname, reference) + expected = json.loads(open(filename).read()) + + test_func = partial(topotest.router_json_cmp, tgen.gears[rname], command, expected) + _, diff = topotest.run_and_expect(test_func, None, count=tries, wait=0.5) + assertmsg = '"{}" JSON output mismatches the expected result'.format(rname) + assert diff is None, assertmsg + + +def check_routers(initial_convergence=False, exiting=None, restarting=None): + for rname in ["rt1", "rt2", "rt3", "rt4", "rt5", "rt6", "rt7"]: + # Check the RIB first, which should be preserved across restarts in + # all routers of the routing domain. + if initial_convergence == True: + tries = 240 + else: + tries = 1 + router_compare_json_output( + rname, "show ip route ospf json", "show_ip_route.json", tries + ) + + # Check that all adjacencies are up and running (except when there's + # an OSPF instance that is shutting down). + if exiting == None: + tries = 240 + router_compare_json_output( + rname, "show ip ospf neighbor json", "show_ip_ospf_neighbor.json", tries + ) + + # Check the OSPF RIB and LSDB. + # In the restarting router, wait up to one minute for the LSDB to converge. + if exiting != rname: + if initial_convergence == True or restarting == rname: + tries = 240 + else: + tries = 1 + router_compare_json_output( + rname, "show ip ospf database json", "show_ip_ospf_database.json", tries + ) + router_compare_json_output( + rname, "show ip ospf route json", "show_ip_ospf_route.json", tries + ) + + +# +# Test initial network convergence +# +def test_initial_convergence(): + logger.info("Test: verify initial network convergence") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + check_routers(initial_convergence=True) + + +# +# Test rt1 performing a graceful restart +# +def test_gr_rt1(): + logger.info("Test: verify rt1 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt1"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt1", ["ospfd"], save_config=False) + check_routers(exiting="rt1") + + start_router_daemons(tgen, "rt1", ["ospfd"]) + check_routers(restarting="rt1") + + +# +# Test rt2 performing a graceful restart +# +def test_gr_rt2(): + logger.info("Test: verify rt2 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt2"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt2", ["ospfd"], save_config=False) + check_routers(exiting="rt2") + + start_router_daemons(tgen, "rt2", ["ospfd"]) + check_routers(restarting="rt2") + + +# +# Test rt3 performing a graceful restart +# +def test_gr_rt3(): + logger.info("Test: verify rt3 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt3"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt3", ["ospfd"], save_config=False) + check_routers(exiting="rt3") + + start_router_daemons(tgen, "rt3", ["ospfd"]) + check_routers(restarting="rt3") + + +# +# Test rt4 performing a graceful restart +# +def test_gr_rt4(): + logger.info("Test: verify rt4 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt4"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt4", ["ospfd"], save_config=False) + check_routers(exiting="rt4") + + start_router_daemons(tgen, "rt4", ["ospfd"]) + check_routers(restarting="rt4") + + +# +# Test rt5 performing a graceful restart +# +def test_gr_rt5(): + logger.info("Test: verify rt5 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt5"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt5", ["ospfd"], save_config=False) + check_routers(exiting="rt5") + + start_router_daemons(tgen, "rt5", ["ospfd"]) + check_routers(restarting="rt5") + + +# +# Test rt6 performing a graceful restart +# +def test_gr_rt6(): + logger.info("Test: verify rt6 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt6"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt6", ["ospfd"], save_config=False) + check_routers(exiting="rt6") + + start_router_daemons(tgen, "rt6", ["ospfd"]) + check_routers(restarting="rt6") + + +# +# Test rt7 performing a graceful restart +# +def test_gr_rt7(): + logger.info("Test: verify rt7 performing a graceful restart") + tgen = get_topogen() + + # Skip if previous fatal error condition is raised + if tgen.routers_have_failure(): + pytest.skip(tgen.errors) + + tgen.net["rt7"].cmd('vtysh -c "graceful-restart prepare ip ospf"') + sleep(3) + kill_router_daemons(tgen, "rt7", ["ospfd"], save_config=False) + check_routers(exiting="rt7") + + start_router_daemons(tgen, "rt7", ["ospfd"]) + check_routers(restarting="rt7") + + +# Memory leak test template +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)) |
