SNMPでLLDP情報を拾ってくる
何をしたいのか
inet-henge に入力するLLDP情報をSNMPで拾いたい
GitHub - codeout/inet-henge: Generate d3.js based Network Diagram from JSON data.
LLDP-MIB
LLDP-MIBを使うとLLDP情報を拾ってこれる。
inet-hengeに使う情報は ホスト名
、ポート名
、対向ホスト名
、対向ポート名
があれば十分そう。
これらに対応するMIBシンボルは次の通り。
パラメータ | MIBシンボル |
---|---|
ホスト名 | LLDP-MIB::lldpLocSysName |
ポート名 | LLDP-MIB::lldpLocPortDesc |
対向ホスト名 | LLDP-MIB::lldpRemSysName |
対向ポート名 | LLDP-MIB::lldpRemPortDesc |
動作確認
トポロジはこんな感じで
snmpwalkでRouter1とRouter2からLLDP情報を取得してみる
Router1
LLDP-MIB::lldpLocSysName.0 = STRING: Router1 LLDP-MIB::lldpLocPortDesc.1 = STRING: GigabitEthernet0/0 LLDP-MIB::lldpLocPortDesc.2 = STRING: GigabitEthernet0/1 LLDP-MIB::lldpLocPortDesc.3 = STRING: GigabitEthernet0/2 LLDP-MIB::lldpLocPortDesc.4 = STRING: GigabitEthernet0/3 LLDP-MIB::lldpRemSysName.0.2.2 = STRING: Router2 LLDP-MIB::lldpRemSysName.0.3.3 = STRING: Switch1-1 LLDP-MIB::lldpRemSysName.0.4.4 = STRING: Switch1-2 LLDP-MIB::lldpRemPortDesc.0.2.2 = STRING: GigabitEthernet0/1 LLDP-MIB::lldpRemPortDesc.0.3.3 = STRING: GigabitEthernet0/0 LLDP-MIB::lldpRemPortDesc.0.4.4 = STRING: GigabitEthernet0/0
Router2
LLDP-MIB::lldpLocSysName.0 = STRING: Router2 LLDP-MIB::lldpLocPortDesc.1 = STRING: GigabitEthernet0/0 LLDP-MIB::lldpLocPortDesc.2 = STRING: GigabitEthernet0/1 LLDP-MIB::lldpLocPortDesc.3 = STRING: GigabitEthernet0/2 LLDP-MIB::lldpLocPortDesc.4 = STRING: GigabitEthernet0/3 LLDP-MIB::lldpRemSysName.0.2.1 = STRING: Router1 LLDP-MIB::lldpRemSysName.0.3.2 = STRING: Switch2-1 LLDP-MIB::lldpRemSysName.0.4.3 = STRING: Switch2-2 LLDP-MIB::lldpRemPortDesc.0.2.1 = STRING: GigabitEthernet0/1 LLDP-MIB::lldpRemPortDesc.0.3.2 = STRING: GigabitEthernet0/0 LLDP-MIB::lldpRemPortDesc.0.4.3 = STRING: GigabitEthernet0/0
それぞれのフォーマットについて
ポート名は lldpLocPortDesc.<ifindex>
対向ホスト名は lldpRemSysName.x.<ifindex>.x
対向ポート名は lldpRemPortDesc.x.<ifindex>.x
inet-henge用のデータ整形
LLDP-MIB::lldpLocPortDescでifindexが把握できる。 ifindexが分かれば、そこから対向ホスト名、対向ポート名が紐付けられるので、、、いい感じにやる。
LLDP情報を定期的にDBに [ホスト名, ポート名, 対向ホスト名, 対向ポート名] という形で保存しておけばinet-hengeに突っ込む用のデータとしては十分かなと思う。
Cumulus Linux の Prescriptive Topology Manager で配線を検証する
Cumulus Linux では Prescriptive Topology Manager という機能が提供されている。
Prescriptive Topology Manager - PTM - Cumulus Linux 3.7 - Cumulus Networks
これは LLDP の情報を使用して配線情報を検証してくれるというもの。
実際に Cumulus VX と GNS3 で検証してみる。 目的のトポロジはこんな感じ。
まず、正しい配線情報を/etc/ptmd/topology.dot
に記述する。
graph G { "spine-1":"swp3" -- "leaf-1":"swp1" "spine-1":"swp4" -- "leaf-2":"swp1" "spine-1":"swp5" -- "leaf-3":"swp1" "spine-2":"swp3" -- "leaf-1":"swp2" "spine-2":"swp4" -- "leaf-2":"swp2" "spine-2":"swp5" -- "leaf-3":"swp2" }
ptmd
を再起動する。これは設定ファイルを書き換えるたび必要になる。
systemctl restart ptmd
これで準備は整ったので、あとは配線をしていく。
まず1本目をつないでみる。spine-1 の swp3 と leaf-1 の swp1 を結線。
つないだらptmctl
で検証結果を確認。
cumulus@spine-1:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp3 pass N/A N/A N/A N/A swp4 N/A N/A N/A N/A N/A swp5 N/A N/A N/A N/A N/A
topology.dot に定義した内容と LLDP の情報が合致しているため、pass
と出ている。
では間違った配線をするとどうなるかを見てみる。 spine-1 の swp4 に leaf-2 の swp2 を接続する。(正しい接続は spine-1:swp4 <-> leaf-2:swp1)
ptmctl
を実行。
cumulus@spine-1:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp3 pass N/A N/A N/A N/A swp4 fail N/A N/A N/A N/A swp5 N/A N/A N/A N/A N/A
swp4 において fail
と表示されている。これは LLDP 情報が topology.dot と一致しないため。
ちなみに /var/log/ptmd.log
にもいろいろ出てたりする。
接続が正しいとき
2019-03-29T14:42:45.645249+00:00 spine-1 ptmd[2647]: Port swp3 correctly matched with remote leaf-1.swp1
接続が誤っているとき
2019-03-29T14:47:45.831388+00:00 spine-1 ptmd[2647]: Port swp4 NOT matched with remote - Expected [leaf-2.swp1] != [leaf-2.swp2]
全部つないだところでのテストは以下の通り。topology.dotはすべてのホストで同じファイルが使い回せるのでいちいち書き換える必要はない。 それぞれのホストは自分のホスト名が存在するテスト項目のみ検証を行っていく。
spine-1
cumulus@spine-1:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp3 pass N/A N/A N/A N/A swp4 pass N/A N/A N/A N/A swp5 pass N/A N/A N/A N/A
spine-2
cumulus@spine-2:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp3 pass N/A N/A N/A N/A swp4 pass N/A N/A N/A N/A swp5 pass N/A N/A N/A N/A
leaf-1
cumulus@leaf-1:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp1 pass N/A N/A N/A N/A swp2 pass N/A N/A N/A N/A
leaf-2
cumulus@leaf-2:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp1 pass N/A N/A N/A N/A swp2 pass N/A N/A N/A N/A
leaf-3
cumulus@leaf-3:~$ ptmctl ----------------------------------------- port cbl BFD BFD BFD BFD status status peer local type ----------------------------------------- swp1 pass N/A N/A N/A N/A swp2 pass N/A N/A N/A N/A
実際にどんな場面で使うのか?
結線して LLDP 情報を受け取ったら即テストが走って配線情報を検証してくれるので、構築時などには役立つと思う。
ESXiのvmnic番号と物理ポートのマッピングとか間違えやすいし...
ちなみにESXiはvCenterがないと標準スイッチでCDPしかしゃべれないけど、Cumulus Linuxで使用している lldpd は CDP にも対応しているので大丈夫(だと思う...)。