hnakamur’s blog

ものすごい勢いで忘れる私のために未整理でもいいからとりあえずメモ

2009-08-26

libvirtでNAT構成にするための設定

ブリッジを止めてNATに切り替えたわけ

KVMのゲストOSのネットワークをブリッジにするの環境でkeepalivedでのVRRPの実験は成功したのですが、DSR構成でのロードバランサの実験がどうもうまくいきませんでした。仮想環境でのネットワーク構築がよくわかっていない私がいきなり上級者編のDSRにチャレンジというのに無理があったということで、まずはNAT構成でチャレンジすることにしてみました。

libvirtでNAT構成

libvirt: Wiki: Networkingを参考にしました。また、今まではゲストOSを実運用に近い設定にしようとして固定IPにしていましたが、virt-cloneでゲストOSイメージをコピーしたあとにゲストOS毎に設定を変えるのが面倒なので、今回から極力ゲストOS毎の設定変更箇所を少なくするという方針に変更しました。

試行錯誤しながらホストOSでのlibvirtの設定変更を変更したので、手順は無しで設定ファイルだけメモしておきます。

ホストOS (Ubuntu) の設定

/etc/libvirt/qemu/networks/default.xml

<network>
  <name>default</name>
  <uuid>212ea219-055f-bd26-1c76-52817e607642</uuid>
  <bridge name="virbr%d" />
  <forward mode="nat"/>
  <ip address="192.168.122.1" netmask="255.255.255.0">
    <dhcp>
      <range start="192.168.122.100" end="192.168.122.254" />
      <host mac="52:54:00:12:34:56" name="vm10" ip="192.168.122.11" />
      <host mac="52:54:00:12:34:57" name="vm11" ip="192.168.122.12" />
    </dhcp>
  </ip>
</network>

/etc/libvirt/qemu/vm10.xml

<domain type='kvm'>
  <name>vm10</name>
  <uuid>35e92166-78c8-641f-15d7-5a30af377d55</uuid>
  <memory>524288</memory>
  <currentMemory>524288</currentMemory>
  <vcpu>1</vcpu>
  <os>
    <type arch='i686' machine='pc'>hvm</type>
    <boot dev='hd'/>
  </os>
  <features>
    <acpi/>
    <apic/>
    <pae/>
  </features>
  <clock offset='utc'/>
  <on_poweroff>destroy</on_poweroff>
  <on_reboot>restart</on_reboot>
  <on_crash>restart</on_crash>
  <devices>
    <emulator>/usr/bin/kvm</emulator>
    <disk type='file' device='disk'>
      <source file='/home/hnakamur/kvm_work/vm10.qcow2'/>
      <target dev='hda' bus='ide'/>
    </disk>
    <disk type='file' device='cdrom'>
      <target dev='hdc' bus='ide'/>
      <readonly/>
    </disk>
    <interface type='network'>
      <mac address='52:54:00:12:34:56'/>
      <source network='default'/>
    </interface>
    <serial type='pty'>
      <target port='0'/>
    </serial>
    <console type='pty'>
      <target port='0'/>
    </console>
  </devices>
</domain>

/etc/sysctl.confでは以下の設定変更をしてsysctl -pで読み込みました。

net.ipv4.ip_forward=1

/etc/resolv.conf

nameserver 192.168.122.1
nameserver 192.168.11.1

ゲストOS (CentOS) の設定

/etc/sysconfig/network (ホスト名はDHCPで設定するので空にしました)

NETWORKING=yes
NETWORKING_IPV6=no
HOSTNAME=

/etc/resolv.conf

nameserver 192.168.122.1

/etc/sysconfig/network-scripts/ifcfg-eth0

DEVICE=eth0
BOOTPROTO=dhcp
ONBOOT=yes
TYPE=Ethernet
DNS1=192.168.122.1

(追記) その後試していると/etc/resolv.confの設定が消されてしまってeth0が上がらないことがありました。/etc/sysconfig/network-scripts/ifcfg-eth0にDNS1=で指定しておくとOKでした。これがまっとうなのかはわかりませんが、とりあえずこれで。

(2009-08-27追記) CentOSのDeployment Guideの14.2. Interface Configuration Filesに説明がありました。PEERDNSがyesの場合DNS1とDNS2に指定した値で/etc/resolv.confが修正されます。dhcpの場合PEERDNSのデフォルト値はyesです。

ホストOSでのlibvirtの設定の試行錯誤

手順として整理したものは無いのですが、どんな試行錯誤をしたかのメモを書いておきます。

/etc/libvirt/qemu/networks/default.xmlの変更と反映での試行錯誤

libvirt: Wiki: Networkingを参考にしたのですが、結局のところvirshを起動してhelpコマンドで出てくるネット関連のコマンド(net-*)を手当たり次第に試して変更しました。net-editで変更してみたり、net-destroyやnet-undefineで消してからnet-createで作り直したり。net-destroyかnet-undefineを実行したときは、/etc/libvirt/qemu/networks/default.xmlが消えてしまって慌てたりしました。事前にバックアップをとっておいたほうがいいです。

また途中でnet-editを実行したときに

error: invalid network pointer in no network with matching uuid
というエラーが出て困りました。どうやら、/etc/libvirt/qemu/networks/default.xmlを直接エディタで変更したのがよくなかったようで、常にnet-editで編集するようにしておいたほうがいいみたいです。あと、確か元々の/etc/libvirt/qemu/networks/default.xmlにはuuidの要素は無かったのが、net-editで見たときは入っていました。/etc/libvirt/qemu/networks/default.xmlはテンプレートみたいなものでvmを作るときにそこからコピーされるのかとも思ったのですが、net-editで編集した結果は/etc/libvirt/qemu/networks/default.xmlに反映されるようです。そのときにどこか別の場所にも反映されているのかな、まだよくわかってないです。

ゲストOSでのlibvirt組み込みのDNSサーバーdnsmasqの設定変更の試行錯誤

libvirt: Wiki: Networking

If you are already running dnsmasq on your machine, please see libvirtd and dnsmasq.
という説明があります。libvirt: Wiki: Libvirtd and dnsmasqを読んで、psで見てみるとdnsmasqのプロセスがありますが/etc/dnsmasq.confはありませんでした。というわけでこれはlibvirtが起動したもののようです。ただ、/etc/init.d/dnsmasqとかはないんですよね。Bug #231060 in libvirt (Ubuntu): “packages dnsmasq and libvirt-bin conflict with each other”とかが関係ありそうですが、とりあえずスルーしました。

libvirtのネットワークをうまく設定できた今の状態ではpsで見るとこんな感じです。

# ps auxww|grep dnsmasq
root      5077  0.0  0.0   2076   564 pts/7    S+   00:52   0:00 grep dnsmasq
nobody   31008  0.0  0.0   2388   716 ?        S    Aug26   0:00 dnsmasq --strict-order
 --bind-interfaces --pid-file=/var/run/libvirt/network/default.pid --conf-file=  
--listen-address 192.168.122.1 --except-interface lo --dhcp-range 192.168.122.100,192.168.122.254
 --dhcp-host 52:54:00:12:34:56,vm10,192.168.122.11 --dhcp-host 52:54:00:12:34:57,vm11,192.168.122.12

こうなるまでにいろいろ試行錯誤しました。/etc/libvirt/qemu/networks/default.xmlの<dhcp>タグの設定に対応していることはわかったのですが、viやvirsh net-editで変更するだけでは反映されないようなので、killして上げ直そうとしたのですが起動方法をまた試行錯誤するはめに。どうやらnet-startのときに同時にあがるのかと思いきや

virsh# net-start default
error: Failed to start network default
error: internal error network is already active
というエラーになったり。1

今、再度試してみたところ以下の手順でとりあえず変更できることを確認しました。

virsh # net-destroy default

ここでviで/etc/libvirt/qemu/networks/default.xmlを編集

virsh # net-create /etc/libvirt/qemu/networks/default.xml
Network default created from /etc/libvirt/qemu/networks/default.xml

net-createを実行した時点でdnsmasqのプロセスが上がっていました。

さらに一覧を確認して自動実行する設定にします。

virsh # net-list --all
Name                 State      Autostart
-----------------------------------------
default              active     no
virsh # net-autostart default
error: failed to mark network default as autostarted
error: Failed to create symlink '/etc/libvirt/qemu/networks/autostart/default.xml' 
to '/etc/libvirt/qemu/networks/default.xml': File exists

別端末にて/etc/libvirt/qemu/networks/autostart/default.xmlというシンボリックリンクを削除します。

# ls -l /etc/libvirt/qemu/networks/autostart/default.xml 
lrwxrwxrwx 1 root root 38 Aug 26 20:43 /etc/libvirt/qemu/networks/autostart/default.xml -> /etc/libvirt/qemu/networks/default.xml
# rm /etc/libvirt/qemu/networks/autostart/default.xml

これでようやく設定変更できた状態でdnsmasqが起動できたと思ったら今度は、ゲストOSの変更前のIPアドレスがキャッシュされて残っていたようでdigコマンドで引いても古い値を返されてしまいました。そこでkillして

# dnsmasq --clear-on-reload

を実行した後再度killしてvirshでnet-destroy、net-createとして再起動などとしてなんとかdigで新しい設定のIPアドレスが返されるところまでこぎつけました。このへんの手順も試行錯誤してたまたま見つけただけで、まっとうな手順はまだよくわかっていません。が、とりあえず目的は達成できたのでよしということで。

DHCPの恩恵

ホストOSもゲストOSも192.168.122.1のdnsmasqを使うようにしたので、/etc/hostsからvm10とvm11のエントリを削除できました。DHCPといっても、/etc/libvirt/qemu/networks/default.xmlの<host>タグでMACアドレスに対してホスト名とIPアドレスを指定しているので、各vmのIPアドレスが変動することはありません。

2009-09-29追記

  1. これはdnsmasqのプロセスが残っていたからでした。単にpsでdnsmasqのPIDを調べてkillした後、net-defineコマンドでxmlの内容を反映し、net-startコマンドでdnsmasqを起動します。ちなみに、net-destroyは定義ファイルを削除するのでやりすぎです。

2010-09-19追記

定義ファイルごと削除されるのはnet-undefineを実行したときです。net-destroyはdnsmasqのプロセスを止めます。

2010-12-16追記

DHCPで運用しているとゲストを上げたまま一日ぐらいたつとゲストのIPアドレスが消失してネットワークが繋がらなくなるという現象を何度か体験しました。仕方が無いのでDHCPはやめて静的にIPアドレスを指定する運用に切り替えました。

ブログ アーカイブ