]> git.puffer.fish Git - mirror/frr.git/commitdiff
topotest: add pbr test suite
authorJakub Urbańczyk <xthaid@gmail.com>
Tue, 26 May 2020 16:24:16 +0000 (18:24 +0200)
committerJakub Urbańczyk <xthaid@gmail.com>
Wed, 10 Jun 2020 14:29:14 +0000 (16:29 +0200)
Add some basic tests for installing PBR rules into the kernel.

Signed-off-by: Jakub Urbańczyk <xthaid@gmail.com>
tests/topotests/lib/topogen.py
tests/topotests/lib/topotest.py
tests/topotests/pbr-topo1/__init__.py [new file with mode: 0644]
tests/topotests/pbr-topo1/r1/linux-rules.json [new file with mode: 0644]
tests/topotests/pbr-topo1/test_pbr_topo1.py

index 414dc1787487264326126922699bf60b6fc38a10..efd5b90685964118ad8d4fdc6f981961dbd2be45 100644 (file)
@@ -658,7 +658,7 @@ class TopoRouter(TopoGear):
         Possible daemon values are: TopoRouter.RD_ZEBRA, TopoRouter.RD_RIP,
         TopoRouter.RD_RIPNG, TopoRouter.RD_OSPF, TopoRouter.RD_OSPF6,
         TopoRouter.RD_ISIS, TopoRouter.RD_BGP, TopoRouter.RD_LDP,
-        TopoRouter.RD_PIM.
+        TopoRouter.RD_PIM, TopoRouter.RD_PBR.
         """
         daemonstr = self.RD.get(daemon)
         self.logger.info('loading "{}" configuration: {}'.format(daemonstr, source))
@@ -1064,6 +1064,7 @@ def diagnose_env_linux():
             "isisd",
             "pimd",
             "ldpd",
+            "pbrd"
         ]:
             path = os.path.join(frrdir, fname)
             if not os.path.isfile(path):
@@ -1121,6 +1122,7 @@ def diagnose_env_linux():
             "ripngd",
             "isisd",
             "pimd",
+            "pbrd"
         ]:
             path = os.path.join(quaggadir, fname)
             if not os.path.isfile(path):
index 6262082193955cb657c8b34f365c97fe0a4391ff..9d945d5262450d5ae3aeb652a5eedcdd6a9b037c 100644 (file)
@@ -727,6 +727,57 @@ def ip6_route(node):
     return result
 
 
+def ip_rules(node):
+    """
+    Gets a structured return of the command 'ip rule'. It can be used in
+    conjuction with json_cmp() to provide accurate assert explanations.
+
+    Return example:
+    [
+        {
+            "pref": "0"
+            "from": "all"
+        },
+        {
+            "pref": "32766"
+            "from": "all"
+        },
+        {
+            "to": "3.4.5.0/24",
+            "iif": "r1-eth2",
+            "pref": "304",
+            "from": "1.2.0.0/16",
+            "proto": "zebra"
+        }
+    ]
+    """
+    output = normalize_text(node.run("ip rule")).splitlines()
+    result = []
+    for line in output:
+        columns = line.split(" ")
+
+        route = {}
+        # remove last character, since it is ':'
+        pref = columns[0][:-1]
+        route["pref"] = pref
+        prev = None
+        for column in columns:
+            if prev == "from":
+                route["from"] = column
+            if prev == "to":
+                route["to"] = column
+            if prev == "proto":
+                route["proto"] = column
+            if prev == "iif":
+                route["iif"] = column
+            if prev == "fwmark":
+                route["fwmark"] = column
+            prev = column
+
+        result.append(route)
+    return result
+
+
 def sleep(amount, reason=None):
     """
     Sleep wrapper that registers in the log the amount of sleep
diff --git a/tests/topotests/pbr-topo1/__init__.py b/tests/topotests/pbr-topo1/__init__.py
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/tests/topotests/pbr-topo1/r1/linux-rules.json b/tests/topotests/pbr-topo1/r1/linux-rules.json
new file mode 100644 (file)
index 0000000..5af4363
--- /dev/null
@@ -0,0 +1,19 @@
+[
+  {
+    "iif": "r1-eth1",
+    "pref": "304",
+    "from": "4.5.6.7"
+  },
+  {
+    "to": "3.4.5.0/24",
+    "iif": "r1-eth2",
+    "pref": "304",
+    "from": "1.2.0.0/16"
+  },
+  {
+    "to": "9.9.9.9",
+    "iif": "r1-eth1",
+    "pref": "309",
+    "from": "all"
+  }
+]
index aedc9ca3fc950e82e455909ebaf4f4ba5531d70a..7de1cfa519d538aa2a535f36dafccfccc4e67d9b 100755 (executable)
@@ -201,6 +201,28 @@ def test_pbr_flap():
         # Actual output from router
         actual = router.vtysh_cmd("show pbr interface json", isjson=True)
         assertmsg = '"show pbr interface" mismatches on {}'.format(router.name)
+
+        assert topotest.json_cmp(actual, expected) is None, assertmsg
+
+
+def test_rule_linux_installation():
+    "Ensure that rule is installed in the kernel"
+
+    tgen = get_topogen()
+    # Don't run this test if we have any failure.
+    if tgen.routers_have_failure():
+        pytest.skip(tgen.errors)
+
+    logger.info("Checking for installed PBR rules in OS")
+
+    router_list = tgen.routers().values()
+    for router in router_list:
+        rules_file = "{}/{}/linux-rules.json".format(CWD, router.name)
+
+        actual = topotest.ip_rules(router)
+        expected = json.loads(open(rules_file).read())
+
+        assertmsg = "Router {} OS rules mismatch".format(router.name)
         assert topotest.json_cmp(actual, expected) is None, assertmsg