6 Topotests is a suite of topology tests for FRR built on top of Mininet.
11 Only tested with Ubuntu 16.04 and Ubuntu 18.04 (which uses Mininet 2.2.x).
13 Instructions are the same for all setups (i.e. ExaBGP is only used for BGP
16 Installing Mininet Infrastructure
17 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
21 apt-get install mininet
22 apt-get install python-pip
23 apt-get install iproute
26 pip install "pytest<5"
27 pip install "scapy>=2.4.2"
28 pip install exabgp==3.4.17 (Newer 4.0 version of exabgp is not yet
30 useradd -d /var/run/exabgp/ -s /bin/false exabgp
35 Optional, will give better output.
40 disable apport (which move core files)
42 Set ``enabled=0`` in ``/etc/default/apport``.
44 Next, update security limits by changing :file:`/etc/security/limits.conf` to::
46 #<domain> <type> <item> <value>
48 root soft core unlimited
50 root hard core unlimited
52 Reboot for options to take effect.
54 SNMP Utilities Installation
55 """""""""""""""""""""""""""
57 To run SNMP test you need to install SNMP utilities and MIBs. Unfortunately
58 there are some errors in the upstream MIBS which need to be patched up. The
59 following steps will get you there on Ubuntu 20.04.
63 apt install snmpd snmp
64 apt install snmp-mibs-downloader
66 wget http://www.iana.org/assignments/ianaippmmetricsregistry-mib/ianaippmmetricsregistry-mib -O /usr/share/snmp/mibs/iana/IANA-IPPM-METRICS-REGISTRY-MIB
67 wget http://pastebin.com/raw.php?i=p3QyuXzZ -O /usr/share/snmp/mibs/ietf/SNMPv2-PDU
68 wget http://pastebin.com/raw.php?i=gG7j8nyk -O /usr/share/snmp/mibs/ietf/IPATM-IPMC-MIB
69 edit /etc/snmp/snmp.conf to look like this
70 # As the snmp packages come without MIB files due to license reasons, loading
71 # of MIBs is disabled by default. If you added the MIBs you can reenable
72 # loading them by commenting out the following line.
79 FRR needs to be installed separately. It is assume to be configured like the
80 standard Ubuntu Packages:
82 - Binaries in :file:`/usr/lib/frr`
83 - State Directory :file:`/var/run/frr`
84 - Running under user ``frr``, group ``frr``
85 - vtygroup: ``frrvty``
86 - config directory: :file:`/etc/frr`
87 - For FRR Packages, install the dbg package as well for coredump decoding
89 No FRR config needs to be done and no FRR daemons should be run ahead of the
90 test. They are all started as part of the test.
95 If you prefer to manually build FRR, then use the following suggested config:
101 --localstatedir=/var/run/frr \
102 --sbindir=/usr/lib/frr \
103 --sysconfdir=/etc/frr \
107 --enable-multipath=64 \
110 --enable-vty-group=frrvty \
111 --enable-snmp=agentx \
112 --with-pkg-extra-version=-my-manual-build
114 And create ``frr`` user and ``frrvty`` group as follows:
118 addgroup --system --gid 92 frr
119 addgroup --system --gid 85 frrvty
120 adduser --system --ingroup frr --home /var/run/frr/ \
121 --gecos "FRRouting suite" --shell /bin/false frr
122 usermod -G frrvty frr
127 Execute all tests with output to console
128 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
132 py.test -s -v --tb=no
134 The above command must be executed from inside the topotests directory.
136 All test\_\* scripts in subdirectories are detected and executed (unless
137 disabled in ``pytest.ini`` file).
139 ``--tb=no`` disables the python traceback which might be irrelevant unless the
140 test script itself is debugged.
150 For example, and assuming you are inside the frr directory:
154 cd tests/topotests/bgp_l3vpn_to_bgp_vrf
155 ./test_bgp_l3vpn_to_bgp_vrf.py
157 For further options, refer to pytest documentation.
159 Test will set exit code which can be used with ``git bisect``.
161 For the simulated topology, see the description in the python file.
163 If you need to clear the mininet setup between tests (if it isn't cleanly
164 shutdown), then use the ``mn -c`` command to clean up the environment.
166 StdErr log from daemos after exit
167 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
169 To enable the reporting of any messages seen on StdErr after the daemons exit,
170 the following env variable can be set::
172 export TOPOTESTS_CHECK_STDERR=Yes
174 (The value doesn't matter at this time. The check is whether the env
175 variable exists or not.) There is no pass/fail on this reporting; the
176 Output will be reported to the console.
178 Collect Memory Leak Information
179 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
181 FRR processes can report unfreed memory allocations upon exit. To
182 enable the reporting of memory leaks, define an environment variable
183 ``TOPOTESTS_CHECK_MEMLEAK`` with the file prefix, i.e.::
185 export TOPOTESTS_CHECK_MEMLEAK="/home/mydir/memleak_"
187 This will enable the check and output to console and the writing of
188 the information to files with the given prefix (followed by testname),
189 ie :file:`/home/mydir/memcheck_test_bgp_multiview_topo1.txt` in case
192 Running Topotests with AddressSanitizer
193 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
195 Topotests can be run with AddressSanitizer. It requires GCC 4.8 or newer.
196 (Ubuntu 16.04 as suggested here is fine with GCC 5 as default). For more
197 information on AddressSanitizer, see
198 https://github.com/google/sanitizers/wiki/AddressSanitizer.
200 The checks are done automatically in the library call of ``checkRouterRunning``
201 (ie at beginning of tests when there is a check for all daemons running). No
202 changes or extra configuration for topotests is required beside compiling the
203 suite with AddressSanitizer enabled.
205 If a daemon crashed, then the errorlog is checked for AddressSanitizer output.
206 If found, then this is added with context (calling test) to
207 :file:`/tmp/AddressSanitizer.txt` in Markdown compatible format.
209 Compiling for GCC AddressSanitizer requires to use ``gcc`` as a linker as well
210 (instead of ``ld``). Here is a suggest way to compile frr with AddressSanitizer
211 for ``master`` branch:
215 git clone https://github.com/FRRouting/frr.git
219 --enable-address-sanitizer \
220 --prefix=/usr/lib/frr --sysconfdir=/etc/frr \
221 --localstatedir=/var/run/frr \
222 --sbindir=/usr/lib/frr --bindir=/usr/lib/frr \
223 --enable-exampledir=/usr/lib/frr/examples \
224 --with-moduledir=/usr/lib/frr/modules \
225 --enable-multipath=0 --enable-rtadv \
226 --enable-tcp-zebra --enable-fpm --enable-pimd \
230 # Create symlink for vtysh, so topotest finds it in /usr/lib/frr
231 sudo ln -s /usr/lib/frr/vtysh /usr/bin/
233 and create ``frr`` user and ``frrvty`` group as shown above.
235 .. _topotests_docker:
237 Running Tests with Docker
238 -------------------------
240 There is a Docker image which allows to run topotests.
245 If you have Docker installed, you can run the topotests in Docker. The easiest
246 way to do this, is to use the make targets from this repository.
248 Your current user needs to have access to the Docker daemon. Alternatively you
249 can run these commands as root.
255 This command will pull the most recent topotests image from Dockerhub, compile
256 FRR inside of it, and run the topotests.
261 Internally, the topotests make target uses a shell script to pull the image and
262 spawn the Docker container.
264 There are several environment variables which can be used to modify the
265 behavior of the script, these can be listed by calling it with ``-h``:
269 ./tests/topotests/docker/frr-topotests.sh -h
271 For example, a volume is used to cache build artifacts between multiple runs of
272 the image. If you need to force a complete recompile, you can set
277 TOPOTEST_CLEAN=1 ./tests/topotests/docker/frr-topotests.sh
279 By default, ``frr-topotests.sh`` will build frr and run pytest. If you append
280 arguments and the first one starts with ``/`` or ``./``, they will replace the
281 call to pytest. If the appended arguments do not match this patttern, they will
282 be provided to pytest as arguments. So, to run a specific test with more
287 ./tests/topotests/docker/frr-topotests.sh -vv -s all-protocol-startup/test_all_protocol_startup.py
289 And to compile FRR but drop into a shell instead of running pytest:
293 ./tests/topotests/docker/frr-topotests.sh /bin/bash
298 The Docker image just includes all the components to run the topotests, but not
299 the topotests themselves. So if you just want to write tests and don't want to
300 make changes to the environment provided by the Docker image. You don't need to
301 build your own Docker image if you do not want to.
303 When developing new tests, there is one caveat though: The startup script of
304 the container will run a ``git-clean`` on its copy of the FRR tree to avoid any
305 pollution of the container with build artefacts from the host. This will also
306 result in your newly written tests being unavailable in the container unless at
307 least added to the index with ``git-add``.
309 If you do want to test changes to the Docker image, you can locally build the
310 image and run the tests without pulling from the registry using the following
316 TOPOTEST_PULL=0 make topotests
319 .. _topotests-guidelines:
327 To run the whole suite of tests the following commands must be executed at the
328 top level directory of topotest:
332 $ # Change to the top level directory of topotests.
333 $ cd path/to/topotests
334 $ # Tests must be run as root, since Mininet requires it.
337 In order to run a specific test, you can use the following command:
341 $ # running a specific topology
342 $ sudo pytest ospf-topo1/
343 $ # or inside the test folder
345 $ sudo pytest # to run all tests inside the directory
346 $ sudo pytest test_ospf_topo1.py # to run a specific test
347 $ # or outside the test folder
349 $ sudo pytest ospf-topo1/test_ospf_topo1.py # to run a specific one
351 The output of the tested daemons will be available at the temporary folder of
356 $ ls /tmp/topotest/ospf-topo1.test_ospf-topo1/r1
358 zebra.err # zebra stderr output
359 zebra.log # zebra log file
360 zebra.out # zebra stdout output
363 You can also run memory leak tests to get reports:
367 $ # Set the environment variable to apply to a specific test...
368 $ sudo env TOPOTESTS_CHECK_MEMLEAK="/tmp/memleak_report_" pytest ospf-topo1/test_ospf_topo1.py
369 $ # ...or apply to all tests adding this line to the configuration file
370 $ echo 'memleak_path = /tmp/memleak_report_' >> pytest.ini
371 $ # You can also use your editor
373 $ # After running tests you should see your files:
374 $ ls /tmp/memleak_report_*
375 memleak_report_test_ospf_topo1.txt
380 This section will guide you in all recommended steps to produce a standard
383 This is the recommended test writing routine:
385 - Write a topology (Graphviz recommended)
386 - Obtain configuration files
387 - Write the test itself
388 - Format the new code using `black <https://github.com/psf/black>`_
389 - Create a Pull Request
391 Some things to keep in mind:
393 - BGP tests MUST use generous convergence timeouts - you must ensure
394 that any test involving BGP uses a convergence timeout of at least
396 - Topotests are run on a range of Linux versions: if your test
397 requires some OS-specific capability (like mpls support, or vrf
398 support), there are test functions available in the libraries that
399 will help you determine whether your test should run or be skipped.
400 - Avoid including unstable data in your test: don't rely on link-local
401 addresses or ifindex values, for example, because these can change
405 Topotest File Hierarchy
406 """""""""""""""""""""""
408 Before starting to write any tests one must know the file hierarchy. The
409 repository hierarchy looks like this:
413 $ cd path/to/topotest
416 ./README.md # repository read me
417 ./GUIDELINES.md # this file
418 ./conftest.py # test hooks - pytest related functions
419 ./example-test # example test folder
420 ./example-test/__init__.py # python package marker - must always exist.
421 ./example-test/test_template.jpg # generated topology picture - see next section
422 ./example-test/test_template.dot # Graphviz dot file
423 ./example-test/test_template.py # the topology plus the test
425 ./ospf-topo1 # the ospf topology test
426 ./ospf-topo1/r1 # router 1 configuration files
427 ./ospf-topo1/r1/zebra.conf # zebra configuration file
428 ./ospf-topo1/r1/ospfd.conf # ospf configuration file
429 ./ospf-topo1/r1/ospfroute.txt # 'show ip ospf' output reference file
430 # removed other for shortness sake
432 ./lib # shared test/topology functions
433 ./lib/topogen.py # topogen implementation
434 ./lib/topotest.py # topotest implementation
436 Guidelines for creating/editing topotest:
438 - New topologies that don't fit the existing directories should create its own
439 - Always remember to add the ``__init__.py`` to new folders, this makes auto
440 complete engines and pylint happy
441 - Router (Quagga/FRR) specific code should go on topotest.py
442 - Generic/repeated router actions should have an abstraction in
444 - Generic/repeated non-router code should go to topotest.py
445 - pytest related code should go to conftest.py (e.g. specialized asserts)
447 Defining the Topology
448 """""""""""""""""""""
450 The first step to write a new test is to define the topology. This step can be
451 done in many ways, but the recommended is to use Graphviz to generate a drawing
452 of the topology. It allows us to see the topology graphically and to see the
453 names of equipment, links and addresses.
455 Here is an example of Graphviz dot file that generates the template topology
456 :file:`tests/topotests/example-test/test_template.dot` (the inlined code might
457 get outdated, please see the linked file)::
479 label="s1\n192.168.0.0/24",
485 label="s2\n192.168.1.0/24",
491 r1 -- s1 [label="eth0\n.1"];
493 r1 -- s2 [label="eth1\n.100"];
494 r2 -- s2 [label="eth0\n.1"];
497 Here is the produced graph:
521 label="s1\n192.168.0.0/24",
527 label="s2\n192.168.1.0/24",
533 r1 -- s1 [label="eth0\n.1"];
535 r1 -- s2 [label="eth1\n.100"];
536 r2 -- s2 [label="eth0\n.1"];
539 Generating / Obtaining Configuration Files
540 """"""""""""""""""""""""""""""""""""""""""
542 In order to get the configuration files or command output for each router, we
543 need to run the topology and execute commands in ``vtysh``. The quickest way to
544 achieve that is writing the topology building code and running the topology.
546 To bootstrap your test topology, do the following steps:
548 - Copy the template test
553 $ touch new-topo/__init__.py
554 $ cp example-test/test_template.py new-topo/test_new_topo.py
556 - Modify the template according to your dot file
558 Here is the template topology described in the previous section in python code:
562 class TemplateTopo(Topo):
563 "Test topology builder"
564 def build(self, *_args, **_opts):
566 tgen = get_topogen(self)
569 for routern in range(1, 3):
570 tgen.add_router('r{}'.format(routern))
572 # Create a switch with just one router connected to it to simulate a
574 switch = tgen.add_switch('s1')
575 switch.add_link(tgen.gears['r1'])
577 # Create a connection between r1 and r2
578 switch = tgen.add_switch('s2')
579 switch.add_link(tgen.gears['r1'])
580 switch.add_link(tgen.gears['r2'])
584 Topogen allows us to run the topology without running any tests, you can do
585 that using the following example commands:
589 $ # Running your bootstraped topology
590 $ sudo pytest -s --topology-only new-topo/test_new_topo.py
591 $ # Running the test_template.py topology
592 $ sudo pytest -s --topology-only example-test/test_template.py
593 $ # Running the ospf_topo1.py topology
594 $ sudo pytest -s --topology-only ospf-topo1/test_ospf_topo1.py
596 Parameters explanation:
602 Actives input/output capture. This is required by mininet in order to show
603 the interactive shell.
605 .. option:: --topology-only
607 Don't run any tests, just build the topology.
609 After executing the commands above, you should get the following terminal
614 === test session starts ===
615 platform linux2 -- Python 2.7.12, pytest-3.1.2, py-1.4.34, pluggy-0.4.0
616 rootdir: /media/sf_src/topotests, inifile: pytest.ini
619 ospf-topo1/test_ospf_topo1.py *** Starting controller
621 *** Starting 6 switches
622 switch1 switch2 switch3 switch4 switch5 switch6 ...
623 r2: frr zebra started
624 r2: frr ospfd started
625 r3: frr zebra started
626 r3: frr ospfd started
627 r1: frr zebra started
628 r1: frr ospfd started
629 r4: frr zebra started
630 r4: frr ospfd started
634 The last line shows us that we are now using the Mininet CLI (Command Line
635 Interface), from here you can call your router ``vtysh`` or even bash.
637 Here are some commands example:
641 mininet> r1 ping 10.0.3.1
642 PING 10.0.3.1 (10.0.3.1) 56(84) bytes of data.
643 64 bytes from 10.0.3.1: icmp_seq=1 ttl=64 time=0.576 ms
644 64 bytes from 10.0.3.1: icmp_seq=2 ttl=64 time=0.083 ms
645 64 bytes from 10.0.3.1: icmp_seq=3 ttl=64 time=0.088 ms
647 --- 10.0.3.1 ping statistics ---
648 3 packets transmitted, 3 received, 0% packet loss, time 1998ms
649 rtt min/avg/max/mdev = 0.083/0.249/0.576/0.231 ms
653 mininet> r1 ping 10.0.3.3
654 PING 10.0.3.3 (10.0.3.3) 56(84) bytes of data.
655 64 bytes from 10.0.3.3: icmp_seq=1 ttl=64 time=2.87 ms
656 64 bytes from 10.0.3.3: icmp_seq=2 ttl=64 time=0.080 ms
657 64 bytes from 10.0.3.3: icmp_seq=3 ttl=64 time=0.091 ms
659 --- 10.0.3.3 ping statistics ---
660 3 packets transmitted, 3 received, 0% packet loss, time 2003ms
661 rtt min/avg/max/mdev = 0.080/1.014/2.872/1.313 ms
667 Hello, this is FRRouting (version 3.1-devrzalamena-build).
668 Copyright 1996-2005 Kunihiro Ishiguro, et al.
670 frr-1# show running-config
671 Building configuration...
673 Current configuration:
675 frr version 3.1-devrzalamena-build
676 frr defaults traditional
678 no service integrated-vtysh-config
685 ip address 10.0.3.1/24
688 ip address 10.0.10.1/24
691 ip address 172.16.0.2/24
694 ospf router-id 10.0.255.3
696 redistribute connected
698 network 10.0.3.0/24 area 0
699 network 10.0.10.0/24 area 0
700 network 172.16.0.0/24 area 1
707 After you successfully configured your topology, you can obtain the
708 configuration files (per-daemon) using the following commands:
712 mininet> r3 vtysh -d ospfd
714 Hello, this is FRRouting (version 3.1-devrzalamena-build).
715 Copyright 1996-2005 Kunihiro Ishiguro, et al.
717 frr-1# show running-config
718 Building configuration...
720 Current configuration:
722 frr version 3.1-devrzalamena-build
723 frr defaults traditional
724 no service integrated-vtysh-config
729 ospf router-id 10.0.255.3
731 redistribute connected
733 network 10.0.3.0/24 area 0
734 network 10.0.10.0/24 area 0
735 network 172.16.0.0/24 area 1
745 Test topologies should always be bootstrapped from
746 :file:`tests/topotests/example-test/test_template.py` because it contains
747 important boilerplate code that can't be avoided, like:
749 - imports: os, sys, pytest, topotest/topogen and mininet topology class
750 - The global variable CWD (Current Working directory): which is most likely
751 going to be used to reference the routers configuration file location
757 # For all registered routers, load the zebra configuration file
758 for rname, router in router_list.items():
761 os.path.join(CWD, '{}/zebra.conf'.format(rname))
763 # os.path.join() joins the CWD string with arguments adding the necessary
764 # slashes ('/'). Arguments must not begin with '/'.
766 - The topology class that inherits from Mininet Topo class:
770 class TemplateTopo(Topo):
771 def build(self, *_args, **_opts):
772 tgen = get_topogen(self)
773 # topology build code
775 - pytest ``setup_module()`` and ``teardown_module()`` to start the topology
779 def setup_module(_m):
780 tgen = Topogen(TemplateTopo)
781 tgen.start_topology('debug')
783 def teardown_module(_m):
787 - ``__main__`` initialization code (to support running the script directly)
791 if __name__ == '__main__':
792 sys.exit(pytest.main(["-s"]))
796 - Test code should always be declared inside functions that begin with the
797 ``test_`` prefix. Functions beginning with different prefixes will not be run
799 - Configuration files and long output commands should go into separated files
800 inside folders named after the equipment.
801 - Tests must be able to run without any interaction. To make sure your test
802 conforms with this, run it without the :option:`-s` parameter.
803 - Use `black <https://github.com/psf/black>`_ code formatter before creating
804 a pull request. This ensures we have a unified code style.
805 - Mark test modules with pytest markers depending on the daemons used during the
806 tests (see :ref:`topotests-markers`)
810 - Keep results in stack variables, so people inspecting code with ``pdb`` can
811 easily print their values.
817 assert foobar(router1, router2)
823 result = foobar(router1, router2)
826 - Use ``assert`` messages to indicate where the test failed.
832 for router in router_list:
834 assert condition, 'Router "{}" condition failed'.format(router.name)
839 The most effective ways to inspect topology tests are:
841 - Run pytest with ``--pdb`` option. This option will cause a pdb shell to
842 appear when an assertion fails
844 Example: ``pytest -s --pdb ospf-topo1/test_ospf_topo1.py``
846 - Set a breakpoint in the test code with ``pdb``
852 # Add the pdb import at the beginning of the file
856 # Add a breakpoint where you think the problem is
862 The `Python Debugger <https://docs.python.org/2.7/library/pdb.html>`__ (pdb)
863 shell allows us to run many useful operations like:
865 - Setting breaking point on file/function/conditions (e.g. ``break``,
867 - Inspecting variables (e.g. ``p`` (print), ``pp`` (pretty print))
868 - Running python code
872 The TopoGear (equipment abstraction class) implements the ``__str__`` method
873 that allows the user to inspect equipment information.
875 Example of pdb usage:
879 > /media/sf_src/topotests/ospf-topo1/test_ospf_topo1.py(121)test_ospf_convergence()
880 -> for rnum in range(1, 5):
882 Documented commands (type help <topic>):
883 ========================================
884 EOF bt cont enable jump pp run unt
885 a c continue exit l q s until
886 alias cl d h list quit step up
887 args clear debug help n r tbreak w
888 b commands disable ignore next restart u whatis
889 break condition down j p return unalias where
891 Miscellaneous help topics:
892 ==========================
895 Undocumented commands:
896 ======================
900 116 title2="Expected output")
902 118 def test_ospf_convergence():
903 119 "Test OSPF daemon convergence"
905 121 -> for rnum in range(1, 5):
906 122 router = 'r{}'.format(rnum)
908 124 # Load expected results from the command
909 125 reffile = os.path.join(CWD, '{}/ospfroute.txt'.format(router))
910 126 expected = open(reffile).read()
912 > /media/sf_src/topotests/ospf-topo1/test_ospf_topo1.py(122)test_ospf_convergence()
913 -> router = 'r{}'.format(rnum)
915 > /media/sf_src/topotests/ospf-topo1/test_ospf_topo1.py(125)test_ospf_convergence()
916 -> reffile = os.path.join(CWD, '{}/ospfroute.txt'.format(router))
921 (Pdb) tgen = get_topogen()
922 (Pdb) pp tgen.gears[router]
923 <lib.topogen.TopoRouter object at 0x7f74e06c9850>
924 (Pdb) pp str(tgen.gears[router])
925 'TopoGear<name="r1",links=["r1-eth0"<->"s1-eth0","r1-eth1"<->"s3-eth0"]> TopoRouter<>'
928 121 for rnum in range(1, 5):
929 122 router = 'r{}'.format(rnum)
931 124 # Load expected results from the command
932 125 -> reffile = os.path.join(CWD, '{}/ospfroute.txt'.format(router))
933 126 expected = open(reffile).read()
935 128 # Run test function until we get an result. Wait at most 60 seconds.
936 129 test_func = partial(compare_show_ip_ospf, router, expected)
937 130 result, diff = topotest.run_and_expect(test_func, '',
938 (Pdb) router1 = tgen.gears[router]
939 (Pdb) router1.vtysh_cmd('show ip ospf route')
940 '============ OSPF network routing table ============\r\nN 10.0.1.0/24 [10] area: 0.0.0.0\r\n directly attached to r1-eth0\r\nN 10.0.2.0/24 [20] area: 0.0.0.0\r\n via 10.0.3.3, r1-eth1\r\nN 10.0.3.0/24 [10] area: 0.0.0.0\r\n directly attached to r1-eth1\r\nN 10.0.10.0/24 [20] area: 0.0.0.0\r\n via 10.0.3.1, r1-eth1\r\nN IA 172.16.0.0/24 [20] area: 0.0.0.0\r\n via 10.0.3.1, r1-eth1\r\nN IA 172.16.1.0/24 [30] area: 0.0.0.0\r\n via 10.0.3.1, r1-eth1\r\n\r\n============ OSPF router routing table =============\r\nR 10.0.255.2 [10] area: 0.0.0.0, ASBR\r\n via 10.0.3.3, r1-eth1\r\nR 10.0.255.3 [10] area: 0.0.0.0, ABR, ASBR\r\n via 10.0.3.1, r1-eth1\r\nR 10.0.255.4 IA [20] area: 0.0.0.0, ASBR\r\n via 10.0.3.1, r1-eth1\r\n\r\n============ OSPF external routing table ===========\r\n\r\n\r\n'
941 (Pdb) tgen.mininet_cli()
945 To enable more debug messages in other Topogen subsystems (like Mininet), more
946 logging messages can be displayed by modifying the test configuration file
952 # Change the default verbosity line from 'info'...
957 Instructions for use, write or debug topologies can be found in :ref:`topotests-guidelines`.
958 To learn/remember common code snippets see :ref:`topotests-snippets`.
960 Before creating a new topology, make sure that there isn't one already that
961 does what you need. If nothing is similar, then you may create a new topology,
962 preferably, using the newest template
963 (:file:`tests/topotests/example-test/test_template.py`).
965 .. include:: topotests-markers.rst
967 .. include:: topotests-snippets.rst
972 All the configs and scripts are licensed under a ISC-style license. See Python