🎃

network namespaceで遊ぶ - OSPF(2)

2022/05/30に公開

前回のおさらい

こちらの記事でOSPFネットワークを作成しました。ちゃんと動いているか確認していきましょう。

https://zenn.dev/takai404/articles/9633f5aa669f32

状態確認

CLIの使い方

frrのCLIは以下のコマンドでアクセスできます。

ip netns exec router1 vtysh -N router1

network namespace名が2回も入っていて面倒くさいですね。
vtyshがfrrのCLIなので、通常の利用ではvtyshだけ打てばよいのですが、network namespace(frrではpathspaceと呼んでいます)を指定するために-Nオプションをつけています。[1]

ところで、vtysh -N router1コマンドだけでもOSPFの情報を見るだけなら実は問題ないです。vtyshの中でPingコマンド等を使おうとするとip netns exec router1をつける必要があります。

以下がip netns exec router1をつけた場合。OSPF neibourが見え、ping成功しています。

# ip netns exec router1 vtysh -N router1

Hello, this is FRRouting (version 8.1).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

router1# show ip ospf neighbor

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.24.2         1 Full/Backup       36.430s 10.0.12.2       e1:10.0.12.1                         0     0     0
10.0.34.3         1 Full/Backup       36.583s 10.0.13.3       e2:10.0.13.1                         0     0     0

router1# ping 10.0.92.100
PING 10.0.92.100 (10.0.92.100) 56(84) bytes of data.
64 bytes from 10.0.92.100: icmp_seq=1 ttl=62 time=0.034 ms
64 bytes from 10.0.92.100: icmp_seq=2 ttl=62 time=0.035 ms
64 bytes from 10.0.92.100: icmp_seq=3 ttl=62 time=0.036 ms
^C
--- 10.0.92.100 ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2033ms
rtt min/avg/max/mdev = 0.034/0.035/0.036/0.000 ms
router1# exit

以下がip netns exec router1をつけない場合。OSPF neighborは見えますが、ping失敗します。

# router1 vtysh -N router1
router1: command not found
root@test01:~/hakoniwa/networks/ospf# vtysh -N router1

Hello, this is FRRouting (version 8.1).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

router1# show ip ospf neighbor

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.24.2         1 Full/Backup       39.591s 10.0.12.2       e1:10.0.12.1                         0     0     0
10.0.34.3         1 Full/Backup       39.744s 10.0.13.3       e2:10.0.13.1                         0     0     0

router1# ping 10.0.92.100
PING 10.0.92.100 (10.0.92.100) 56(84) bytes of data.
^C
--- 10.0.92.100 ping statistics ---
5 packets transmitted, 0 received, 100% packet loss, time 4081ms

router1# exit

これはfrrのデーモンであるzebraやospfdはnetwork namespaceの中で動いているので、クライアントであるvtyshをdefault namespaceで起動してもデーモンが持っている情報は見れるのに対し、pingコマンドはvtysh自体がICMP echoを発出するのでdefault namespaceに出ていこうとして疎通できないものと思われます。

IPアドレス

zebra(ospfd?)から各network namespaceのインターフェイスが見えていること、IPアドレスが付与されていること、リンクアップしていることを確認しましょう。

# ip netns exec router1 vtysh -N router1

Hello, this is FRRouting (version 8.1).
Copyright 1996-2005 Kunihiro Ishiguro, et al.

router1# show interface
Interface e0 is up, line protocol is up
  Link ups:       1    last: 2022/05/29 19:31:19.93
  Link downs:     0    last: (never)
  vrf: default
  index 2 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 3a:25:48:c5:a9:4d
  inet 10.0.91.1/24
  inet6 fe80::3825:48ff:fec5:a94d/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e0
Interface e1 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 3 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 22:ca:a9:12:bf:49
  inet 10.0.12.1/24
  inet6 fe80::20ca:a9ff:fe12:bf49/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e0
Interface e2 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 4 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: ca:d1:cf:17:aa:72
  inet 10.0.13.1/24
  inet6 fe80::c8d1:cfff:fe17:aa72/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e0
Interface lo is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 1 metric 0 mtu 65536 speed 0
  flags: <UP,LOOPBACK,RUNNING>
  Type: Loopback
  Interface Type Other
  Interface Slave Type None
  protodown: off

vtyshは対話的に使うこともできるし、-cで打鍵するコマンドを指定してスクリプト等で一括して状態確認することもできます。

router2 ~ router4のshow interface
# for i in `seq 2 4`; do ip netns exec router$i vtysh -N router$i -E -c 'show interface'; done
router2# show interface
Interface e0 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 2 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 4e:aa:e4:54:35:09
  inet 10.0.12.2/24
  inet6 fe80::4caa:e4ff:fe54:3509/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e1
Interface e1 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 3 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: b6:36:36:5b:3a:3a
  inet 10.0.24.2/24
  inet6 fe80::b436:36ff:fe5b:3a3a/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e0
Interface lo is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 1 metric 0 mtu 65536 speed 0
  flags: <UP,LOOPBACK,RUNNING>
  Type: Loopback
  Interface Type Other
  Interface Slave Type None
  protodown: off
router3# show interface
Interface e0 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 2 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 62:12:34:67:49:3f
  inet 10.0.13.3/24
  inet6 fe80::6012:34ff:fe67:493f/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent ifindex: 4
Interface e1 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 3 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: d6:ed:ff:9a:b8:64
  inet 10.0.34.3/24
  inet6 fe80::d4ed:ffff:fe9a:b864/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e1
Interface lo is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 1 metric 0 mtu 65536 speed 0
  flags: <UP,LOOPBACK,RUNNING>
  Type: Loopback
  Interface Type Other
  Interface Slave Type None
  protodown: off
router4# show interface
Interface e0 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 2 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 1a:a0:39:38:b0:c9
  inet 10.0.24.4/24
  inet6 fe80::18a0:39ff:fe38:b0c9/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e1
Interface e1 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 3 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: 6a:ed:0c:a5:96:4f
  inet 10.0.34.4/24
  inet6 fe80::68ed:cff:fea5:964f/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e1
Interface e2 is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 4 metric 0 mtu 1500 speed 10000
  flags: <UP,BROADCAST,RUNNING,MULTICAST>
  Type: Ethernet
  HWaddr: f2:d2:c3:0c:38:59
  inet 10.0.92.4/24
  inet6 fe80::f0d2:c3ff:fe0c:3859/64
  Interface Type VETH
  Interface Slave Type None
  protodown: off
  Parent interface: e0
Interface lo is up, line protocol is up
  Link ups:       0    last: (never)
  Link downs:     0    last: (never)
  vrf: default
  index 1 metric 0 mtu 65536 speed 0
  flags: <UP,LOOPBACK,RUNNING>
  Type: Loopback
  Interface Type Other
  Interface Slave Type None
  protodown: off

OSPF状態

show ip ospfでOSPFの情報が見れます。いろいろ細かい情報がでていますが、まずはそもそも出力があるかどうかをチェックします。OSPFが無効だと何も出力されません。

# ip netns exec router1 vtysh -N router1 -c 'show ip ospf'
OSPF Routing Process, Router ID: 10.0.91.1
 Supports only single TOS (TOS0) routes
 This implementation conforms to RFC2328
 RFC1583Compatibility flag is disabled
 OpaqueCapability flag is disabled
 Initial SPF scheduling delay 0 millisec(s)
 Minimum hold time between consecutive SPFs 50 millisec(s)
 Maximum hold time between consecutive SPFs 5000 millisec(s)
 Hold time multiplier is currently 2
 SPF algorithm last executed 2h39m25s ago
 Last SPF duration 59 usecs
 SPF timer is inactive
 LSA minimum interval 5000 msecs
 LSA minimum arrival 1000 msecs
 Write Multiplier set to 20
 Refresh timer 10 secs
 Maximum multiple paths(ECMP) supported  256
 Number of external LSA 0. Checksum Sum 0x00000000
 Number of opaque AS LSA 0. Checksum Sum 0x00000000
 Number of areas attached to this router: 1
 Area ID: 0.0.0.0 (Backbone)
   Number of interfaces in this area: Total: 3, Active: 3
   Number of fully adjacent neighbors in this area: 2
   Area has no authentication
   SPF algorithm executed 6 times
   Number of LSA 8
   Number of router LSA 4. Checksum Sum 0x00024bea
   Number of network LSA 4. Checksum Sum 0x0001c91b
   Number of summary LSA 0. Checksum Sum 0x00000000
   Number of ASBR summary LSA 0. Checksum Sum 0x00000000
   Number of NSSA LSA 0. Checksum Sum 0x00000000
   Number of opaque link LSA 0. Checksum Sum 0x00000000
   Number of opaque area LSA 0. Checksum Sum 0x00000000

OSPF neighbor確認

近接ルータとのneighbor関係が確立できているかを確認します。
これはrouter1の出力なので、router2, rourter3とneighborを確立しているはず(=2行出力があるはず)です。ちゃんとありますね。
StateがFullなので収束状態です。

# ip netns exec router1 vtysh -N router1 -c 'show ip ospf neighbor'

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.24.2         1 Full/Backup       38.007s 10.0.12.2       e1:10.0.12.1                         0     0     0
10.0.34.3         1 Full/Backup       38.160s 10.0.13.3       e2:10.0.13.1                         0     0     0

OSPF route

ospfで交換しているルーティング情報を確認します。

  • router2の向こう側 10.0.24.0/24へのnext hopがrouter2(10.0.12.2)
  • router3の向こう側 10.0.34.0/24へのnext hopがrouter3(10.0.13.3)
  • router4の向こう側(host2のセグメント) 10.0.92.0/24へのnext hopがrouter2(10.0.12.2)とrouter3(10.0.13.3)の2つ
# ip netns exec router1 vtysh -N router1 -c 'show ip ospf route'
============ OSPF network routing table ============
N    10.0.12.0/24          [10] area: 0.0.0.0
                           directly attached to e1
N    10.0.13.0/24          [10] area: 0.0.0.0
                           directly attached to e2
N    10.0.24.0/24          [20] area: 0.0.0.0
                           via 10.0.12.2, e1
N    10.0.34.0/24          [20] area: 0.0.0.0
                           via 10.0.13.3, e2
N    10.0.91.0/24          [10] area: 0.0.0.0
                           directly attached to e0
N    10.0.92.0/24          [30] area: 0.0.0.0
                           via 10.0.12.2, e1
                           via 10.0.13.3, e2

============ OSPF router routing table =============

============ OSPF external routing table ===========

ノードのルーティングテーブル

ospfで交換したルーティング情報をルータ自身(=Linux)のルーティングテーブルに乗せているかが分かります。

  • 先頭のOはOSPFで交換したということ
  • *はFIB(Forwarding Infomation Base)に乗っている=Linuxのルーティングテーブルに乗っているということ
# ip netns exec router1 vtysh -N router1 -c 'show ip route'
Codes: K - kernel route, C - connected, S - static, R - RIP,
       O - OSPF, I - IS-IS, B - BGP, E - EIGRP, N - NHRP,
       T - Table, v - VNC, V - VNC-Direct, A - Babel, F - PBR,
       f - OpenFabric,
       > - selected route, * - FIB route, q - queued, r - rejected, b - backup
       t - trapped, o - offload failure

O   10.0.12.0/24 [110/10] is directly connected, e1, weight 1, 02:40:54
C>* 10.0.12.0/24 is directly connected, e1, 02:40:54
O   10.0.13.0/24 [110/10] is directly connected, e2, weight 1, 02:40:54
C>* 10.0.13.0/24 is directly connected, e2, 02:40:54
O>* 10.0.24.0/24 [110/20] via 10.0.12.2, e1, weight 1, 02:40:04
O>* 10.0.34.0/24 [110/20] via 10.0.13.3, e2, weight 1, 02:40:04
O   10.0.91.0/24 [110/10] is directly connected, e0, weight 1, 02:40:53
C>* 10.0.91.0/24 is directly connected, e0, 02:40:53
O>* 10.0.92.0/24 [110/30] via 10.0.12.2, e1, weight 1, 02:40:04
  *                       via 10.0.13.3, e2, weight 1, 02:40:04

Linuxのルーティングテーブルに乗っているので、linuxのipコマンドでも同様の情報を確認できます。

# ip netns exec router1 ip route show
10.0.12.0/24 dev e1 proto kernel scope link src 10.0.12.1
10.0.13.0/24 dev e2 proto kernel scope link src 10.0.13.1
10.0.24.0/24 nhid 20 via 10.0.12.2 dev e1 proto ospf metric 20
10.0.34.0/24 nhid 24 via 10.0.13.3 dev e2 proto ospf metric 20
10.0.91.0/24 dev e0 proto kernel scope link src 10.0.91.1
10.0.92.0/24 nhid 25 proto ospf metric 20
        nexthop via 10.0.12.2 dev e1 weight 1
        nexthop via 10.0.13.3 dev e2 weight 1
router2 ~ router4のOSPF情報
# for i in `seq 2 4`; do ip netns exec router$i vtysh -N router$i -E -c 'show ip ospf' -c 'show ip ospf neighbor' -c 'show ip ospf route' -c 'show ip route'; done
router2# show ip ospf
 OSPF Routing Process, Router ID: 10.0.24.2
 Supports only single TOS (TOS0) routes
 This implementation conforms to RFC2328
 RFC1583Compatibility flag is disabled
 OpaqueCapability flag is disabled
 Initial SPF scheduling delay 0 millisec(s)
 Minimum hold time between consecutive SPFs 50 millisec(s)
 Maximum hold time between consecutive SPFs 5000 millisec(s)
 Hold time multiplier is currently 1
 SPF algorithm last executed 2h52m08s ago
 Last SPF duration 20 usecs
 SPF timer is inactive
 LSA minimum interval 5000 msecs
 LSA minimum arrival 1000 msecs
 Write Multiplier set to 20
 Refresh timer 10 secs
 Maximum multiple paths(ECMP) supported  256
 Number of external LSA 0. Checksum Sum 0x00000000
 Number of opaque AS LSA 0. Checksum Sum 0x00000000
 Number of areas attached to this router: 1
 Area ID: 0.0.0.0 (Backbone)
   Number of interfaces in this area: Total: 2, Active: 2
   Number of fully adjacent neighbors in this area: 2
   Area has no authentication
   SPF algorithm executed 6 times
   Number of LSA 8
   Number of router LSA 4. Checksum Sum 0x000247ec
   Number of network LSA 4. Checksum Sum 0x0001c11f
   Number of summary LSA 0. Checksum Sum 0x00000000
   Number of ASBR summary LSA 0. Checksum Sum 0x00000000
   Number of NSSA LSA 0. Checksum Sum 0x00000000
   Number of opaque link LSA 0. Checksum Sum 0x00000000
   Number of opaque area LSA 0. Checksum Sum 0x00000000


router2# show ip ospf neighbor

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.91.1         1 Full/DR           31.480s 10.0.12.1       e0:10.0.12.2                         0     0     0
10.0.92.4         1 Full/DR           31.752s 10.0.24.4       e1:10.0.24.2                         0     0     0

router2# show ip ospf route
============ OSPF network routing table ============
N    10.0.12.0/24          [10] area: 0.0.0.0
                           directly attached to e0
N    10.0.13.0/24          [20] area: 0.0.0.0
                           via 10.0.12.1, e0
N    10.0.24.0/24          [10] area: 0.0.0.0
                           directly attached to e1
N    10.0.34.0/24          [20] area: 0.0.0.0
                           via 10.0.24.4, e1
N    10.0.91.0/24          [20] area: 0.0.0.0
                           via 10.0.12.1, e0
N    10.0.92.0/24          [20] area: 0.0.0.0
                           via 10.0.24.4, e1

============ OSPF router routing table =============

============ OSPF external routing table ===========


router2# show ip route
Codes: K - kernel route, C - connected, S - static, R - RIP,
       O - OSPF, I - IS-IS, B - BGP, E - EIGRP, N - NHRP,
       T - Table, v - VNC, V - VNC-Direct, A - Babel, F - PBR,
       f - OpenFabric,
       > - selected route, * - FIB route, q - queued, r - rejected, b - backup
       t - trapped, o - offload failure

O   10.0.12.0/24 [110/10] is directly connected, e0, weight 1, 02:52:09
C>* 10.0.12.0/24 is directly connected, e0, 02:52:59
O>* 10.0.13.0/24 [110/20] via 10.0.12.1, e0, weight 1, 02:52:09
O   10.0.24.0/24 [110/10] is directly connected, e1, weight 1, 02:52:59
C>* 10.0.24.0/24 is directly connected, e1, 02:52:59
O>* 10.0.34.0/24 [110/20] via 10.0.24.4, e1, weight 1, 02:52:14
O>* 10.0.91.0/24 [110/20] via 10.0.12.1, e0, weight 1, 02:52:09
O>* 10.0.92.0/24 [110/20] via 10.0.24.4, e1, weight 1, 02:52:14
router3# show ip ospf
 OSPF Routing Process, Router ID: 10.0.34.3
 Supports only single TOS (TOS0) routes
 This implementation conforms to RFC2328
 RFC1583Compatibility flag is disabled
 OpaqueCapability flag is disabled
 Initial SPF scheduling delay 0 millisec(s)
 Minimum hold time between consecutive SPFs 50 millisec(s)
 Maximum hold time between consecutive SPFs 5000 millisec(s)
 Hold time multiplier is currently 1
 SPF algorithm last executed 2h52m08s ago
 Last SPF duration 32 usecs
 SPF timer is inactive
 LSA minimum interval 5000 msecs
 LSA minimum arrival 1000 msecs
 Write Multiplier set to 20
 Refresh timer 10 secs
 Maximum multiple paths(ECMP) supported  256
 Number of external LSA 0. Checksum Sum 0x00000000
 Number of opaque AS LSA 0. Checksum Sum 0x00000000
 Number of areas attached to this router: 1
 Area ID: 0.0.0.0 (Backbone)
   Number of interfaces in this area: Total: 2, Active: 2
   Number of fully adjacent neighbors in this area: 2
   Area has no authentication
   SPF algorithm executed 7 times
   Number of LSA 8
   Number of router LSA 4. Checksum Sum 0x000247ec
   Number of network LSA 4. Checksum Sum 0x0001c11f
   Number of summary LSA 0. Checksum Sum 0x00000000
   Number of ASBR summary LSA 0. Checksum Sum 0x00000000
   Number of NSSA LSA 0. Checksum Sum 0x00000000
   Number of opaque link LSA 0. Checksum Sum 0x00000000
   Number of opaque area LSA 0. Checksum Sum 0x00000000


router3# show ip ospf neighbor

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.91.1         1 Full/DR           31.392s 10.0.13.1       e0:10.0.13.3                         0     0     0
10.0.92.4         1 Full/DR           31.664s 10.0.34.4       e1:10.0.34.3                         0     0     0

router3# show ip ospf route
============ OSPF network routing table ============
N    10.0.12.0/24          [20] area: 0.0.0.0
                           via 10.0.13.1, e0
N    10.0.13.0/24          [10] area: 0.0.0.0
                           directly attached to e0
N    10.0.24.0/24          [20] area: 0.0.0.0
                           via 10.0.34.4, e1
N    10.0.34.0/24          [10] area: 0.0.0.0
                           directly attached to e1
N    10.0.91.0/24          [20] area: 0.0.0.0
                           via 10.0.13.1, e0
N    10.0.92.0/24          [20] area: 0.0.0.0
                           via 10.0.34.4, e1

============ OSPF router routing table =============

============ OSPF external routing table ===========


router3# show ip route
Codes: K - kernel route, C - connected, S - static, R - RIP,
       O - OSPF, I - IS-IS, B - BGP, E - EIGRP, N - NHRP,
       T - Table, v - VNC, V - VNC-Direct, A - Babel, F - PBR,
       f - OpenFabric,
       > - selected route, * - FIB route, q - queued, r - rejected, b - backup
       t - trapped, o - offload failure

O>* 10.0.12.0/24 [110/20] via 10.0.13.1, e0, weight 1, 02:52:09
O   10.0.13.0/24 [110/10] is directly connected, e0, weight 1, 02:52:59
C>* 10.0.13.0/24 is directly connected, e0, 02:52:59
O>* 10.0.24.0/24 [110/20] via 10.0.34.4, e1, weight 1, 02:52:09
O   10.0.34.0/24 [110/10] is directly connected, e1, weight 1, 02:52:19
C>* 10.0.34.0/24 is directly connected, e1, 02:52:59
O>* 10.0.91.0/24 [110/20] via 10.0.13.1, e0, weight 1, 02:52:09
O>* 10.0.92.0/24 [110/20] via 10.0.34.4, e1, weight 1, 02:52:09
router4# show ip ospf
 OSPF Routing Process, Router ID: 10.0.92.4
 Supports only single TOS (TOS0) routes
 This implementation conforms to RFC2328
 RFC1583Compatibility flag is disabled
 OpaqueCapability flag is disabled
 Initial SPF scheduling delay 0 millisec(s)
 Minimum hold time between consecutive SPFs 50 millisec(s)
 Maximum hold time between consecutive SPFs 5000 millisec(s)
 Hold time multiplier is currently 1
 SPF algorithm last executed 2h52m08s ago
 Last SPF duration 31 usecs
 SPF timer is inactive
 LSA minimum interval 5000 msecs
 LSA minimum arrival 1000 msecs
 Write Multiplier set to 20
 Refresh timer 10 secs
 Maximum multiple paths(ECMP) supported  256
 Number of external LSA 0. Checksum Sum 0x00000000
 Number of opaque AS LSA 0. Checksum Sum 0x00000000
 Number of areas attached to this router: 1
 Area ID: 0.0.0.0 (Backbone)
   Number of interfaces in this area: Total: 3, Active: 3
   Number of fully adjacent neighbors in this area: 2
   Area has no authentication
   SPF algorithm executed 6 times
   Number of LSA 8
   Number of router LSA 4. Checksum Sum 0x000247ec
   Number of network LSA 4. Checksum Sum 0x0001c11f
   Number of summary LSA 0. Checksum Sum 0x00000000
   Number of ASBR summary LSA 0. Checksum Sum 0x00000000
   Number of NSSA LSA 0. Checksum Sum 0x00000000
   Number of opaque link LSA 0. Checksum Sum 0x00000000
   Number of opaque area LSA 0. Checksum Sum 0x00000000


router4# show ip ospf neighbor

Neighbor ID     Pri State           Dead Time Address         Interface                        RXmtL RqstL DBsmL
10.0.24.2         1 Full/Backup       31.247s 10.0.24.2       e0:10.0.24.4                         0     0     0
10.0.34.3         1 Full/Backup       31.390s 10.0.34.3       e1:10.0.34.4                         0     0     0

router4# show ip ospf route
============ OSPF network routing table ============
N    10.0.12.0/24          [20] area: 0.0.0.0
                           via 10.0.24.2, e0
N    10.0.13.0/24          [20] area: 0.0.0.0
                           via 10.0.34.3, e1
N    10.0.24.0/24          [10] area: 0.0.0.0
                           directly attached to e0
N    10.0.34.0/24          [10] area: 0.0.0.0
                           directly attached to e1
N    10.0.91.0/24          [30] area: 0.0.0.0
                           via 10.0.24.2, e0
                           via 10.0.34.3, e1
N    10.0.92.0/24          [10] area: 0.0.0.0
                           directly attached to e2

============ OSPF router routing table =============

============ OSPF external routing table ===========


router4# show ip route
Codes: K - kernel route, C - connected, S - static, R - RIP,
       O - OSPF, I - IS-IS, B - BGP, E - EIGRP, N - NHRP,
       T - Table, v - VNC, V - VNC-Direct, A - Babel, F - PBR,
       f - OpenFabric,
       > - selected route, * - FIB route, q - queued, r - rejected, b - backup
       t - trapped, o - offload failure

O>* 10.0.12.0/24 [110/20] via 10.0.24.2, e0, weight 1, 02:52:09
O>* 10.0.13.0/24 [110/20] via 10.0.34.3, e1, weight 1, 02:52:14
O   10.0.24.0/24 [110/10] is directly connected, e0, weight 1, 02:52:59
C>* 10.0.24.0/24 is directly connected, e0, 02:52:59
O   10.0.34.0/24 [110/10] is directly connected, e1, weight 1, 02:52:59
C>* 10.0.34.0/24 is directly connected, e1, 02:52:59
O>* 10.0.91.0/24 [110/30] via 10.0.24.2, e0, weight 1, 02:52:09
  *                       via 10.0.34.3, e1, weight 1, 02:52:09
O   10.0.92.0/24 [110/10] is directly connected, e2, weight 1, 02:52:59
C>* 10.0.92.0/24 is directly connected, e2, 02:52:59

疎通確認

Ping

状態確認が終わったので疎通確認です(前の記事でもPingだけはしてましたが)。

#  ip netns exec host1 ping -c 10 10.0.92.100
PING 10.0.92.100 (10.0.92.100) 56(84) bytes of data.
64 bytes from 10.0.92.100: icmp_seq=1 ttl=61 time=0.052 ms
64 bytes from 10.0.92.100: icmp_seq=2 ttl=61 time=0.047 ms
64 bytes from 10.0.92.100: icmp_seq=3 ttl=61 time=0.052 ms
64 bytes from 10.0.92.100: icmp_seq=4 ttl=61 time=0.051 ms
64 bytes from 10.0.92.100: icmp_seq=5 ttl=61 time=0.048 ms
64 bytes from 10.0.92.100: icmp_seq=6 ttl=61 time=0.066 ms
64 bytes from 10.0.92.100: icmp_seq=7 ttl=61 time=0.046 ms
64 bytes from 10.0.92.100: icmp_seq=8 ttl=61 time=0.071 ms
64 bytes from 10.0.92.100: icmp_seq=9 ttl=61 time=0.065 ms
64 bytes from 10.0.92.100: icmp_seq=10 ttl=61 time=0.059 ms

--- 10.0.92.100 ping statistics ---
10 packets transmitted, 10 received, 0% packet loss, time 9209ms
rtt min/avg/max/mdev = 0.046/0.055/0.071/0.008 ms

Traceroute

host1からhost2にtracerouteします。
router1, router2, router4, host2の順で通信していることが分かります。

# ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.002ms  0.000ms  0.001ms
  2   10.0.12.2  0.001ms  0.001ms  0.000ms
  3   10.0.34.4  0.000ms  0.000ms  0.001ms
  4   10.0.92.100  0.000ms  0.001ms  0.001ms

逆にhost2からhost1にtracerouteします。
router4, router3, router1, host1の順で通信していることが分かります。
うーん。さっきはrouter2経由だったのにrouter3経由ですね。

# ip netns exec host2 traceroute 10.0.91.100
traceroute to 10.0.91.100 (10.0.91.100), 64 hops max
  1   10.0.92.4  0.002ms  0.000ms  0.000ms
  2   10.0.34.3  0.001ms  0.000ms  0.000ms
  3   10.0.12.1  0.001ms  0.000ms  0.001ms
  4   10.0.91.100  0.000ms  0.000ms  0.000ms

おそらく、このあたりに原因がありそうです。

https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/7/html/7.6_release_notes/new_features_networking

ECMP の fib_multipath_hash_policy を IPv4 パケットのカーネルに追加
この更新により、fib_multipath_hash_policy を使用した ECMP (Equal-cost multi-path routing) ハッシュポリシー選択のサポートが追加されました。これは、マルチパスルートにどのハッシュポリシーを使用するかを制御する新しい sysctl 設定です。fib_multipath_hash_policy を 1 に設定すると、カーネルが L4 hash を実行します。これは、値の 5-tuple セット (ソース IP、ソースポート、宛先 IP、宛先ポート、IP プロトコルタイプ) に基づいた IPv4 パケットのマルチパスハッシュです。fib_multipath_hash_policy を 0 (デフォルト) に設定している場合は、L3 hash (ソースおよび宛先の IP アドレス) だけが使用されます。
fib_multipath_hash_policy を有効にすると、ICMP (Internet Control Message Protocol) エラーパケットが、内部パケットヘッダーに基づいたハッシュ値を持ちません。この問題は、ICMP パケットが誤ったホストに配信されてしまうため、エニキャストサービスの問題です。(BZ#1511351)

試してみましょう。

# ip netns exec router1 sysctl net.ipv4.fib_multipath_hash_policy
net.ipv4.fib_multipath_hash_policy = 0

fib_multipath_hash_policyが0なので、L3ハッシュ(送信元、宛先IPアドレスのハッシュ)のはずです。

host2に10.0.92.101 ~ 109のIPアドレスを追加します。

# ip netns exec host2 ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0@if4: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether fe:01:c3:a5:a8:77 brd ff:ff:ff:ff:ff:ff link-netns router4
    inet 10.0.92.100/24 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::fc01:c3ff:fea5:a877/64 scope link
       valid_lft forever preferred_lft forever
# ip netns exec host2 ip addr add 10.0.92.101/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.102/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.103/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.104/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.105/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.106/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.107/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.108/24 dev eth0
# ip netns exec host2 ip addr add 10.0.92.109/24 dev eth0
# ip netns exec host2 ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0@if4: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether fe:01:c3:a5:a8:77 brd ff:ff:ff:ff:ff:ff link-netns router4
    inet 10.0.92.100/24 scope global eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.101/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.102/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.103/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.104/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.105/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.106/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.107/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.108/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet 10.0.92.109/24 scope global secondary eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::fc01:c3ff:fea5:a877/64 scope link
       valid_lft forever preferred_lft forever

host1から10個の宛先IPアドレスにtracerouteしてみます。

# (set -x; for i in `seq 100 109`; do ip netns exec host1 traceroute 10.0.92.$i; done)
++ seq 100 109
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.000ms
  2   10.0.12.2  0.000ms  0.000ms  0.001ms
  3   10.0.34.4  0.001ms  0.000ms  0.001ms
  4   10.0.92.100  0.001ms  0.001ms  0.001ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.101
traceroute to 10.0.92.101 (10.0.92.101), 64 hops max
  1   *  10.0.91.1  0.002ms  0.000ms
  2   10.0.12.2  0.001ms  0.000ms  0.000ms
  3   10.0.34.4  0.000ms  0.000ms  0.000ms
  4   10.0.92.101  0.001ms  0.000ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.102
traceroute to 10.0.92.102 (10.0.92.102), 64 hops max
  1   10.0.91.1  0.001ms  *  0.001ms
  2   10.0.12.2  0.000ms  0.000ms  0.000ms
  3   10.0.34.4  0.000ms  0.000ms  0.001ms
  4   10.0.92.102  0.000ms  0.000ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.103
traceroute to 10.0.92.103 (10.0.92.103), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  *
  2   10.0.13.3  0.001ms  0.000ms  0.000ms
  3   10.0.24.4  0.000ms  0.000ms  0.000ms
  4   10.0.92.103  0.001ms  0.000ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.104
traceroute to 10.0.92.104 (10.0.92.104), 64 hops max
  1   10.0.91.1  0.001ms  0.000ms  0.000ms
  2   10.0.13.3  0.001ms  0.000ms  0.000ms
  3   *  10.0.24.4  0.001ms  0.000ms
  4   10.0.92.104  0.001ms  0.000ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.105
traceroute to 10.0.92.105 (10.0.92.105), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.001ms
  2   10.0.13.3  0.000ms  0.000ms  0.000ms
  3   10.0.24.4  0.001ms  *  0.001ms
  4   10.0.92.105  0.001ms  0.001ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.106
traceroute to 10.0.92.106 (10.0.92.106), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.000ms
  2   10.0.12.2  0.000ms  0.000ms  0.000ms
  3   10.0.34.4  0.001ms  0.001ms  *
  4   10.0.92.106  0.001ms  0.001ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.107
traceroute to 10.0.92.107 (10.0.92.107), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.000ms
  2   10.0.13.3  0.000ms  0.000ms  0.000ms
  3   10.0.24.4  0.000ms  0.000ms  0.000ms
  4   *  10.0.92.107  0.001ms  0.000ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.108
traceroute to 10.0.92.108 (10.0.92.108), 64 hops max
  1   10.0.91.1  0.001ms  0.000ms  0.001ms
  2   10.0.13.3  0.000ms  0.001ms  0.001ms
  3   10.0.24.4  0.000ms  0.000ms  0.000ms
  4   10.0.92.108  0.000ms  *  0.001ms
+ for i in `seq 100 109`
+ ip netns exec host1 traceroute 10.0.92.109
traceroute to 10.0.92.109 (10.0.92.109), 64 hops max
  1   10.0.91.1  0.001ms  0.000ms  0.000ms
  2   10.0.13.3  0.001ms  0.000ms  0.000ms
  3   10.0.24.4  0.000ms  0.000ms  0.001ms
  4   10.0.92.109  0.000ms  0.001ms  *
#

結果はこうなりました。

宛先IP 経由ルータ
10.0.92.100 router2
10.0.92.101 router2
10.0.92.102 router2
10.0.92.103 router3
10.0.92.104 router3
10.0.92.105 router3
10.0.92.106 router2
10.0.92.107 router3
10.0.92.108 router3
10.0.92.109 router3

router2経由が4個、router3経由が6個になりました。まぁほどほどに分散されていますね。

net.ipv4.fib_multipath_hash_policyを1にして、L4ハッシュを使うようにしてみましょう。
今回は宛先IPは10.0.92.100固定で10回tracerouteします。tracerouteはLinuxではデフォルトでは宛先ポート番号はUDP 33434です。送信元ポート番号はコマンドを打つたびに変わります。

# ip netns exec router1 sysctl -w net.ipv4.fib_multipath_hash_policy=1
net.ipv4.fib_multipath_hash_policy = 1
# (set -x; for i in `seq 10`; do ip netns exec host1 traceroute 10.0.92.100; done)
++ seq 10
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.000ms  0.000ms
  2   10.0.12.2  0.000ms  0.001ms  0.001ms
  3   10.0.34.4  0.001ms  0.000ms  0.000ms
  4   10.0.92.100  0.001ms  0.000ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.000ms  0.000ms
  2   10.0.12.2  0.001ms  0.001ms  0.001ms
  3   10.0.34.4  0.001ms  0.000ms  0.001ms
  4   10.0.92.100  0.001ms  0.001ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   *  10.0.91.1  0.002ms  0.001ms
  2   10.0.12.2  0.001ms  0.001ms  0.001ms
  3   10.0.34.4  0.001ms  0.000ms  0.000ms
  4   10.0.92.100  0.000ms  0.000ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.002ms  *  0.001ms
  2   10.0.12.2  0.000ms  0.001ms  0.001ms
  3   10.0.34.4  0.000ms  0.000ms  0.000ms
  4   10.0.92.100  0.001ms  0.000ms  0.000ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.002ms  0.001ms  *
  2   10.0.12.2  0.002ms  0.001ms  0.001ms
  3   10.0.34.4  0.001ms  0.001ms  0.000ms
  4   10.0.92.100  0.001ms  0.001ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.003ms
  2   10.0.13.3  0.001ms  0.001ms  0.001ms
  3   *  10.0.34.4  0.002ms  0.000ms
  4   10.0.92.100  0.000ms  0.000ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.002ms  0.000ms  0.000ms
  2   10.0.13.3  0.000ms  0.000ms  0.001ms
  3   10.0.34.4  0.001ms  *  0.002ms
  4   10.0.92.100  0.001ms  0.001ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.000ms
  2   10.0.13.3  0.000ms  0.000ms  0.001ms
  3   10.0.34.4  0.000ms  0.001ms  *
  4   10.0.92.100  0.002ms  0.000ms  0.000ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.001ms  0.001ms  0.000ms
  2   10.0.12.2  0.000ms  0.000ms  0.000ms
  3   10.0.34.4  0.000ms  0.000ms  0.000ms
  4   *  10.0.92.100  0.001ms  0.001ms
+ for i in `seq 10`
+ ip netns exec host1 traceroute 10.0.92.100
traceroute to 10.0.92.100 (10.0.92.100), 64 hops max
  1   10.0.91.1  0.002ms  0.001ms  0.001ms
  2   10.0.13.3  0.001ms  0.001ms  0.001ms
  3   10.0.34.4  0.001ms  0.000ms  0.000ms
  4   10.0.92.100  0.001ms  *  0.002ms

router2経由が6個、router3経由が4個になりました。うまいことL4ハッシュで等コストマルチパス(ECMP: Equal Cost Multi Path)構成になっているみたいです。

とりあえずL4ハッシュはデフォルトであるOFFに戻しておきます。

# ip netns exec router1 sysctl -w net.ipv4.fib_multipath_hash_policy=0
net.ipv4.fib_multipath_hash_policy = 0

冗長性確認

リンクダウンによる経路切り替え

route1からrouter4までの間はOSPFによってrouter2を通る経路とrouter3を通る経路で冗長化されています。

host1からhost2にpingを打ちながら、router2のNICをダウンさせてrouter2経由での通信をできないようにしましょう。

コンソールを4枚用意します。

  • console1: ping発生用
  • console2: リンクダウン操作用。pingを始めてから約10秒後にrouter2のe1をリンクダウンさせます。
  • console3: router1のrouter2向けNIC(e1)をパケットキャプチャ
  • console4: router1のrouter3向けNIC(e2)をパケットキャプチャ
console1
# ip netns exec host1 ping 10.0.92.100
PING 10.0.92.100 (10.0.92.100) 56(84) bytes of data.
64 bytes from 10.0.92.100: icmp_seq=1 ttl=61 time=0.063 ms
64 bytes from 10.0.92.100: icmp_seq=2 ttl=61 time=0.051 ms
64 bytes from 10.0.92.100: icmp_seq=3 ttl=61 time=0.049 ms
64 bytes from 10.0.92.100: icmp_seq=4 ttl=61 time=0.048 ms
64 bytes from 10.0.92.100: icmp_seq=5 ttl=61 time=0.052 ms
64 bytes from 10.0.92.100: icmp_seq=6 ttl=61 time=0.046 ms
64 bytes from 10.0.92.100: icmp_seq=7 ttl=61 time=0.047 ms
64 bytes from 10.0.92.100: icmp_seq=8 ttl=61 time=0.051 ms
64 bytes from 10.0.92.100: icmp_seq=9 ttl=61 time=0.050 ms
64 bytes from 10.0.92.100: icmp_seq=10 ttl=61 time=0.047 ms
64 bytes from 10.0.92.100: icmp_seq=11 ttl=61 time=0.045 ms
64 bytes from 10.0.92.100: icmp_seq=12 ttl=61 time=0.044 ms
64 bytes from 10.0.92.100: icmp_seq=13 ttl=61 time=0.040 ms
64 bytes from 10.0.92.100: icmp_seq=14 ttl=61 time=0.040 ms
64 bytes from 10.0.92.100: icmp_seq=15 ttl=61 time=0.043 ms
64 bytes from 10.0.92.100: icmp_seq=16 ttl=61 time=0.032 ms
64 bytes from 10.0.92.100: icmp_seq=17 ttl=61 time=0.038 ms
64 bytes from 10.0.92.100: icmp_seq=18 ttl=61 time=0.042 ms
64 bytes from 10.0.92.100: icmp_seq=19 ttl=61 time=0.051 ms
64 bytes from 10.0.92.100: icmp_seq=20 ttl=61 time=0.043 ms
^C
--- 10.0.92.100 ping statistics ---
20 packets transmitted, 20 received, 0% packet loss, time 19442ms
rtt min/avg/max/mdev = 0.032/0.046/0.063/0.006 ms

seq=10のあたりでrouter2がダウンしているのですが、何事もなかったようにpingできています。いいですね。

console2
# ip netns exec router2 ip link set e1 down
# ip netns exec router1 vtysh -N router1 -E -c 'show ip route'
router1# show ip route
Codes: K - kernel route, C - connected, S - static, R - RIP,
       O - OSPF, I - IS-IS, B - BGP, E - EIGRP, N - NHRP,
       T - Table, v - VNC, V - VNC-Direct, A - Babel, F - PBR,
       f - OpenFabric,
       > - selected route, * - FIB route, q - queued, r - rejected, b - backup
       t - trapped, o - offload failure

O   10.0.12.0/24 [110/10] is directly connected, e1, weight 1, 03:57:36
C>* 10.0.12.0/24 is directly connected, e1, 03:57:36
O   10.0.13.0/24 [110/10] is directly connected, e2, weight 1, 03:57:36
C>* 10.0.13.0/24 is directly connected, e2, 03:57:36
O>* 10.0.34.0/24 [110/20] via 10.0.13.3, e2, weight 1, 03:56:46
O   10.0.91.0/24 [110/10] is directly connected, e0, weight 1, 03:57:35
C>* 10.0.91.0/24 is directly connected, e0, 03:57:35
O>* 10.0.92.0/24 [110/30] via 10.0.13.3, e2, weight 1, 00:00:35

router2のe1をリンクダウンさせ、しばらくしてからrouter1のルーティングテーブルを確認しています。10.0.92.0/24セグメント宛ののNext hopがrouter3だけになっています。想定通りです。

console3
# ip netns exec router1 tcpdump -nnl -i e1
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on e1, link-type EN10MB (Ethernet), snapshot length 262144 bytes
23:28:09.326525 IP 10.0.12.2 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:09.326573 IP 10.0.12.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:10.991836 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 1, length 64
23:28:12.001692 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 2, length 64
23:28:13.025640 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 3, length 64
23:28:14.049706 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 4, length 64
23:28:15.073682 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 5, length 64
23:28:16.097690 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 6, length 64
23:28:17.121646 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 7, length 64
23:28:18.145698 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 8, length 64
23:28:19.169651 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 9, length 64
23:28:19.326526 IP 10.0.12.2 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:19.326574 IP 10.0.12.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:20.193653 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 10, length 64
23:28:20.585460 IP 10.0.12.2 > 224.0.0.5: OSPFv2, LS-Update, length 192
23:28:20.585594 IP 10.0.12.1 > 10.0.12.2: OSPFv2, LS-Ack, length 64
23:28:20.585872 IP 10.0.12.1 > 224.0.0.5: OSPFv2, LS-Update, length 108
23:28:20.716054 IP 10.0.12.2 > 224.0.0.5: OSPFv2, LS-Ack, length 64
23:28:20.717884 IP 10.0.12.1 > 224.0.0.5: OSPFv2, LS-Ack, length 44
23:28:23.169695 ARP, Request who-has 10.0.12.2 tell 10.0.12.1, length 28
23:28:23.169779 ARP, Reply 10.0.12.2 is-at 4e:aa:e4:54:35:09, length 28
23:28:29.326765 IP 10.0.12.2 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:29.326998 IP 10.0.12.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:29.455116 IP 10.0.12.2 > 10.0.12.1: OSPFv2, LS-Update, length 64
23:28:29.718152 IP 10.0.12.1 > 224.0.0.5: OSPFv2, LS-Ack, length 44
23:28:30.046391 IP 10.0.12.1 > 224.0.0.5: OSPFv2, LS-Update, length 76
23:28:30.717470 IP 10.0.12.2 > 224.0.0.5: OSPFv2, LS-Ack, length 44
^C
27 packets captured
27 packets received by filter
0 packets dropped by kernel

この環境は非対称経路になっているので、seq 1 ~ 10までのICMP echo requestのみがキャプチャされています。ICMP echo replyは1つもありません。
また、seq 10の後でOSPFのLS-Update(Link State Update)パケットが出ていることが分かります。

console4
# ip netns exec router1 tcpdump -nnl -i e2
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on e2, link-type EN10MB (Ethernet), snapshot length 262144 bytes
23:28:09.326563 IP 10.0.13.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:09.415551 IP 10.0.13.3 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:10.991858 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 1, length 64
23:28:12.001716 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 2, length 64
23:28:13.025662 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 3, length 64
23:28:14.049729 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 4, length 64
23:28:15.073708 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 5, length 64
23:28:16.001626 ARP, Request who-has 10.0.13.1 tell 10.0.13.3, length 28
23:28:16.001739 ARP, Reply 10.0.13.1 is-at ca:d1:cf:17:aa:72, length 28
23:28:16.097713 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 6, length 64
23:28:17.121667 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 7, length 64
23:28:18.145721 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 8, length 64
23:28:19.169673 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 9, length 64
23:28:19.326566 IP 10.0.13.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:19.415553 IP 10.0.13.3 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:20.193674 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 10, length 64
23:28:20.585582 IP 10.0.13.1 > 224.0.0.5: OSPFv2, LS-Update, length 64
23:28:20.585838 IP 10.0.13.3 > 224.0.0.5: OSPFv2, LS-Update, length 108
23:28:20.717899 IP 10.0.13.1 > 224.0.0.5: OSPFv2, LS-Ack, length 64
23:28:20.949276 IP 10.0.13.3 > 224.0.0.5: OSPFv2, LS-Ack, length 44
23:28:21.217822 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 11, length 64
23:28:21.217842 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 11, length 64
23:28:22.241709 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 12, length 64
23:28:22.241727 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 12, length 64
23:28:23.265680 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 13, length 64
23:28:23.265698 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 13, length 64
23:28:24.289687 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 14, length 64
23:28:24.289703 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 14, length 64
23:28:25.313682 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 15, length 64
23:28:25.313700 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 15, length 64
23:28:26.241663 ARP, Request who-has 10.0.13.3 tell 10.0.13.1, length 28
23:28:26.241717 ARP, Reply 10.0.13.3 is-at 62:12:34:67:49:3f, length 28
23:28:26.337633 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 16, length 64
23:28:26.337648 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 16, length 64
23:28:27.361706 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 17, length 64
23:28:27.361722 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 17, length 64
23:28:28.385682 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 18, length 64
23:28:28.385699 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 18, length 64
23:28:29.326940 IP 10.0.13.1 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:29.409705 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 19, length 64
23:28:29.409724 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 19, length 64
23:28:29.415558 IP 10.0.13.3 > 224.0.0.5: OSPFv2, Hello, length 48
23:28:29.455195 IP 10.0.13.1 > 224.0.0.5: OSPFv2, LS-Update, length 64
23:28:29.950508 IP 10.0.13.3 > 224.0.0.5: OSPFv2, LS-Ack, length 44
23:28:30.046073 IP 10.0.13.3 > 224.0.0.5: OSPFv2, LS-Update, length 76
23:28:30.433702 IP 10.0.91.100 > 10.0.92.100: ICMP echo request, id 500, seq 20, length 64
23:28:30.433721 IP 10.0.92.100 > 10.0.91.100: ICMP echo reply, id 500, seq 20, length 64
23:28:30.718135 IP 10.0.13.1 > 224.0.0.5: OSPFv2, LS-Ack, length 44
^C
48 packets captured
48 packets received by filter
0 packets dropped by kernel

seq 1 ~ 10までのICMP echo replyと、seq 11 ~ 20 のecho request, echo replyがキャプチャされています。
seq 11で経路が切り替わり、行きも戻りもすべてのICMPパケットがrouter3を経由していることが確認できます。
いいですね。想定通りの動きをしています。

経路切り戻しも書きたいのですが、記事の最大文字数を超えてしまったので分割します。
続きはこちら。
https://zenn.dev/takai404/articles/7f282e5d5a8200

脚注
  1. man vtyshでマニュアルを見ても-Nオプションが書いていないのが罠です。vtysh --helpってやると出てくるんですけどね ↩︎

Discussion