HalNiの雑記

備忘録を兼ねて。サーバマシンとかネットワークとか

KVM でゲストのストレージに Transient Disk を使用する ( openSUSE Tumbleweed )

の記事はopenSUSE Advent Calendar 2021 8日目の記事です。

transient diskとは、特定のディスクイメージ内の状態を基準として、ゲスト動作中の変更点をゲスト停止時に破棄し、次回立ち上げた時にまた特定の状態からゲストを開始させることで、 前回の起動時と同じ環境が維持されているというものです。

transient disk 自体は libvirt 6.9.0 で実装され、7.4.0ではホットプラグのサポートや単一イメージで複数のゲスト動作等が追加されています。
openSUSE の場合、 libvirt 7.1.0 である Leap 15.3 から transient disk を使用することができます。
Leap 15.2 まで(~libvirt 6.0.0 )では、サポートされてない旨の表示となり使用できません。

SUSE-152:~ # cat /etc/os-release | grep PRETTY_NAME
PRETTY_NAME="openSUSE Leap 15.2"

SUSE-152:~ # virsh start vm01
error: Failed to start domain Win10-test01
error: unsupported configuration: transient disks not supported yet

Tumbleweed では、現時点で libvirt 7.9.0 のため ディスクのゲスト間共有等も使用することができます。

検証環境:

Supermicro SuperServer 5028R-WR ( X10SRW-F )
openSUSE Tumbleweed : 20211129

Virt-managerからの transient disk の設定は現時点でまだ実装されていないため、virsh から ゲストの xmlファイル を編集します。

sudo virsh edit vm01

xmlの <disk> 内に <transient/> を追加するだけでゲストの起動時に選択されているディスクイメージをベースにした上で、一時ファイル( ベースイメージ名.TRANSIENT-ゲストドメイン )に差分を書き込むようになります。

halni@SUSE-X10SRW:~> sudo virsh dumpxml vm01 | xmllint --xpath //disk -
<disk type="file" device="disk">
      <driver name="qemu" type="qcow2"/>
      <source file="/var/lib/libvirt/images/vm01.qcow2"/>
      <target dev="vda" bus="virtio"/>
      <transient/>
      <address type="pci" domain="0x0000" bus="0x04" slot="0x00" function="0x0"/>
    </disk>

反映されていることを確認し、ゲストの電源を投入します

ゲストのディスクイメージが保存されているディレクトリ下に、一時ファイルが作成されます。

halni@SUSE-X10SRW:~> sudo ls -lsh /var/lib/libvirt/images/
total 2.1G
2.1G -rw------- 1 qemu qemu 5.1G Dec  5 16:17 vm01.qcow2
 15M -rw------- 1 qemu qemu 9.2M Dec  5 17:37 vm01.qcow2.TRANSIENT-vm01

ゲスト側で適当にパッケージをインストールしてみます。

halni@vm01:~> sudo zypper install cowsay
Loading repository data...
Reading installed packages...
Resolving package dependencies...

The following NEW package is going to be installed:
  cowsay
~~~~
halni@vm01:~> cowsay "transient!"
 ____________
< transient! >
 ------------
        \   ^__^
         \  (oo)\_______
            (__)\       )\/\
                ||----w |
                ||     ||

ゲストを停止、再立ち上げしてみます。

halni@SUSE-X10SRW:/var/lib/libvirt/images> sudo ls -lsh
total 2.3G
2.1G -rw------- 1 qemu qemu 5.1G Dec  5 16:17 vm01.qcow2
236M -rw------- 1 qemu qemu 108M Dec  5 17:37 vm01.qcow2.TRANSIENT-vm01

halni@SUSE-X10SRW:/var/lib/libvirt/images> sudo virsh shutdown vm01
Domain 'vm01' is being shutdown

halni@SUSE-X10SRW:/var/lib/libvirt/images> sudo ls -lsh
total 2.1G
2.1G -rw------- 1 qemu qemu 5.1G Dec  5 16:17 vm01.qcow2

halni@SUSE-X10SRW:/var/lib/libvirt/images> sudo virsh start vm01
Domain 'vm01' started

halni@SUSE-X10SRW:/var/lib/libvirt/images> sudo ls -lsh
total 2.1G
2.1G -rw------- 1 qemu qemu 5.1G Dec  5 16:17 vm01.qcow2
15M -rw------- 1 qemu qemu 12M Dec  5 17:49 vm01.qcow2.TRANSIENT-vm01
halni@vm01:~> cowsay
If 'cowsay' is not a typo you can use command-not-found to lookup the package that contains it, like this:
    cnf cowsay

一時ファイルが再生成され、インストールしたはずのパッケージが無かったことになっています。

に単一のディスクイメージを、複数台のゲストで使用してみます。
<transient shareBacking='yes'/> を追加すると、ゲストの起動時に選択されているディスクイメージをRead Only でマウントするため、 複数台のゲストがディスクイメージを掴み、各々の一時ファイルに差分を書き込むようになります。

構成としては、vm01.qcow2 を vm01 と vm02 の2台で transient disk のベースイメージとして使用します。
vm02のxmlファイルに<transient shareBacking='yes'/> を追加します。

halni@SUSE-X10SRW:~> sudo virsh dumpxml vm02 | xmllint --xpath //disk -
<disk type="file" device="disk">
      <driver name="qemu" type="qcow2"/>
      <source file="/var/lib/libvirt/images/vm01.qcow2"/>
      <target dev="vda" bus="virtio"/>
      <transient shareBacking="yes"/>
      <address type="pci" domain="0x0000" bus="0x04" slot="0x00" function="0x0"/>
    </disk>

vm01・vm02を起動します。

halni@SUSE-X10SRW:~> sudo virsh list --all
 Id   Name   State
----------------------
 8    vm01   running
 9    vm02   running

halni@SUSE-X10SRW:~> sudo ls -lsh /var/lib/libvirt/images/
total 2.1G
2.1G -rw------- 1 qemu qemu 5.1G Dec  5 16:17 vm01.qcow2
 26M -rw------- 1 qemu qemu 26M Dec  5 18:12 vm01.qcow2.TRANSIENT-vm01
 26M -rw------- 1 qemu qemu 26M Dec  5 18:12 vm01.qcow2.TRANSIENT-vm02

vm01・vm02共に 同一の Disk identifier となっているのが確認できます。

halni@SUSE-X10SRW:~> ssh root@vm01 fdisk -l | grep "Disk identifier"
Disk identifier: 56C65EE3-EC23-41BC-8C66-DA8300EC17EA

halni@SUSE-X10SRW:~> ssh root@vm02 fdisk -l | grep "Disk identifier"
Disk identifier: 56C65EE3-EC23-41BC-8C66-DA8300EC17EA

また前回終了時刻が同じことからも、同じディスクイメージから起動していることがわかるかと思います。

halni@SUSE-X10SRW:~> ssh vm01 last reboot
reboot   system boot  5.15.5-1-default Sun Dec  5 18:12   still running
reboot   system boot  5.15.5-1-default Thu Dec  2 00:24   still running

wtmp begins Thu Dec  2 00:24:29 2021
halni@SUSE-X10SRW:~> ssh vm02 last reboot
reboot   system boot  5.15.5-1-default Sun Dec  5 18:12   still running
reboot   system boot  5.15.5-1-default Thu Dec  2 00:24   still running

wtmp begins Thu Dec  2 00:24:29 2021

transient disk は使いつぶし環境であったり、 検証環境等、一時的に変更して動作の確認後、すぐ元の状態に戻す場合に、snapshotを使用するよりも楽に巻き戻しを行うことができます。