KVM ホストの NetworkManager 管理の DNS の設定を変える

とある KVM ホストの NetworkManager 管理の DNS の設定を変えようとしたときのこと。

cat /etc/resolv.conf | grep nameserver
# 古い dns サーバになってるぜ

nmcli con modify br0 ipv4.dns 192.0.2.100
# 変更するぜ

nmcli con up br0
# 変更を反映するぜ

cat /etc/resolv.conf
# 変更が反映されているぜ

おしまい

.

.

.

とはなりませんでした。この KVM ホストの中のゲストのネットワークが全死しました。

KVM でゲストの I/F をブリッジで構成する場合(つまりホストの I/F を共有する構成)、次のようにホストのブリッジ br* に仮想I/F vnet* がぶら下がるようになります。

brctl show
# bridge name     bridge id               STP enabled     interfaces
# br0             8000.1234567890ab       no              eth0
#                                                         vnet0
#                                                         vnet1
#                                                         vnet2

この「br0vnet* がぶら下がっている」という構成は NetworkManager の管理外なので nmcli con up br0 などとすると。

brctl show
# bridge name     bridge id               STP enabled     interfaces
# br0             8000.1234567890ab       no              eth0

のように全部外れてしまいます。

対応策 v1

手でもとに戻せば OK です。

btctl addif br0 vnet0
btctl addif br0 vnet1
btctl addif br0 vnet2

昔なにかのときに実際のこの方法で復旧させたことがあるのでたぶん大丈夫です、たぶん。

対応策 v2

ゲストを再起動(停止→開始)させれば戻ります(reboot だとダメだったかも)

virsh shutdown guest0
virsh shutdown guest1
virsh shutdown guest2

virsh list --all

virsh start guest0
virsh start guest1
virsh start guest2

対応策 v3

もっと良い方法があるはず・・・

要するに nmcli con up br0 だと NetworkManager 管理外のブリッジの構成が外れてしまうことが問題なので、別の方法で dns の変更を反映させられればよいのですが、試しに適当な環境で試行錯誤しました。

# ブリッジを作る
nmcli con add type bridge ifname br0 con-name br0 stp no

# ブリッジの設定
nmcli con mod br0 \
    ipv4.method manual \
    ipv4.addresses 192.168.0.123/23 \
    ipv4.gateway 192.168.0.1 \
    ipv4.dns 192.168.0.2 \
    ipv6.method ignore

# ブリッジを有効にする
nmcli con down eth0
nmcli con up br0

# NetworkManager の管理外で eth0 をブリッジに入れる
brctl addif br0 eth0

# 試しに `nmcli con up br0` してみる
nmcli con up br0

# ブリッジから eth0 が外れてます
brctl show
# bridge name     bridge id               STP enabled     interfaces
# br0             8000.000000000000       no

# 元に戻します
brctl addif br0 eth0
brctl show
# bridge name     bridge id               STP enabled     interfaces
# br0             8000.1234567890ab       no              eth0

# dns を変更します
nmcli con mod br0 ipv4.dns 192.168.0.3

# NetworkManager をリスタートします
systemctl restart NetworkManager

# 新しい dns に・・反映されてるぜ
cat /etc/resolv.conf | grep nameserver
# nameserver 192.168.0.3

# ブリッジの構成は・・変わってないぜ
brctl show
# bridge name     bridge id               STP enabled     interfaces
# br0             8000.1234567890ab       no              eth0

というわけで単に NetworkManager をリスタートするのが正解なのかもしれません。今までなんとなく考えなしに nmcli con mod した後は nmcli con up で反映させてました・・・

対応策 v4

そもそものところ resolv.conf を書き換えたいだけなのに変なリスクを犯すのもどうかと思うので NetworkManager が resolv.conf を書き換えないようにしてしまえば良い気がする。

/etc/NetworkManager/NetworkManager.conf

[main]
plugins=ifcfg-rh
dns=none