1# This test runs FRR and checks if OSPF routing works.
2#
3# Network topology:
4# [ client ]--net1--[ router1 ]--net2--[ router2 ]--net3--[ server ]
5#
6# All interfaces are in OSPF Area 0.
7
8import ./make-test-python.nix (
9 { pkgs, ... }:
10 let
11
12 ifAddr = node: iface: (pkgs.lib.head node.networking.interfaces.${iface}.ipv4.addresses).address;
13
14 ospfConf1 = ''
15 interface eth2
16 ip ospf hello-interval 1
17 ip ospf dead-interval 5
18 !
19 router ospf
20 network 192.168.0.0/16 area 0
21 '';
22
23 ospfConf2 = ''
24 interface eth2
25 ip ospf hello-interval 1
26 ip ospf dead-interval 5
27 !
28 router ospf
29 network 192.168.0.0/16 area 0
30 '';
31
32 in
33 {
34 name = "frr";
35
36 meta = with pkgs.lib.maintainers; {
37 maintainers = [ ];
38 };
39
40 nodes = {
41
42 client =
43 { nodes, ... }:
44 {
45 virtualisation.vlans = [ 1 ];
46 services.frr = {
47 config = ''
48 ip route 192.168.0.0/16 ${ifAddr nodes.router1 "eth1"}
49 '';
50 };
51 };
52
53 router1 =
54 { ... }:
55 {
56 virtualisation.vlans = [
57 1
58 2
59 ];
60 boot.kernel.sysctl."net.ipv4.ip_forward" = "1";
61 networking.firewall.extraCommands = "iptables -A nixos-fw -i eth2 -p ospfigp -j ACCEPT";
62 services.frr = {
63 ospfd.enable = true;
64 config = ospfConf1;
65 };
66
67 specialisation.ospf.configuration = {
68 services.frr.config = ospfConf2;
69 };
70 };
71
72 router2 =
73 { ... }:
74 {
75 virtualisation.vlans = [
76 3
77 2
78 ];
79 boot.kernel.sysctl."net.ipv4.ip_forward" = "1";
80 networking.firewall.extraCommands = "iptables -A nixos-fw -i eth2 -p ospfigp -j ACCEPT";
81 services.frr = {
82 ospfd.enable = true;
83 config = ospfConf2;
84 };
85 };
86
87 server =
88 { nodes, ... }:
89 {
90 virtualisation.vlans = [ 3 ];
91 services.frr = {
92 config = ''
93 ip route 192.168.0.0/16 ${ifAddr nodes.router2 "eth1"}
94 '';
95 };
96 };
97 };
98
99 testScript =
100 { nodes, ... }:
101 ''
102 start_all()
103
104 # Wait for the networking to start on all machines
105 for machine in client, router1, router2, server:
106 machine.wait_for_unit("network.target")
107
108 with subtest("Wait for FRR"):
109 for gw in client, router1, router2, server:
110 gw.wait_for_unit("frr")
111
112 router1.succeed("${nodes.router1.system.build.toplevel}/specialisation/ospf/bin/switch-to-configuration test >&2")
113
114 with subtest("Wait for OSPF to form adjacencies"):
115 for gw in router1, router2:
116 gw.wait_until_succeeds("vtysh -c 'show ip ospf neighbor' | grep Full")
117 gw.wait_until_succeeds("vtysh -c 'show ip route' | grep '^O>'")
118
119 with subtest("Test ICMP"):
120 client.wait_until_succeeds("ping -4 -c 3 server >&2")
121 '';
122 }
123)