Red Hat Training

A Red Hat training course is available for Red Hat Enterprise Linux

仮想化の導入および管理ガイド

Red Hat Enterprise Linux 7

Red Hat Enterprise Linux 物理マシン上での仮想マシンのインストール、設定および管理

Jiri Herrmann

Red Hat Customer Content Services

Yehuda Zimmerman

Red Hat Customer Content Services

Laura Novich

Red Hat Customer Content Services

Dayle Parker

Red Hat Customer Content Services

Scott Radvan

Red Hat Customer Content Services

Tahlia Richardson

Red Hat Customer Content Services

概要

本書では、Red Hat Enterprise Linux 7 マシンを設定して仮想ホストシステムとして動作させる方法と、KVM ハイパーバイザーを使用してゲスト仮想マシンをインストールおよび設定する方法について説明します。さらに、PCI デバイス設定、SR-IOV、ネットワーク設定、ストレージ、デバイスおよびゲスト仮想マシンの管理、トラブルシューティング、互換性、および制限についても説明します。ゲスト仮想マシンで実行する必要がある手順は、明確に示されています。

重要

本書に記載されているすべての手順は、特に明記しない限り、AMD64 または Intel 64 ホストマシン上での実行を目的としています。AMD64 および Intel 64 以外のアーキテクチャーで Red Hat Enterprise Linux 7 の仮想化を使用する場合は、付録B 複数のアーキテクチャー上での KVM 仮想化の使用 を参照してください。
Red Hat が提供する仮想化ソリューションの概説については、『Red Hat Enterprise Linux 7 仮想化スタートガイド』を参照してください。

パート I. デプロイメント

第1章 システム要件

仮想化は、Intel 64 および AMD64 アーキテクチャーをベースにした Red Hat Enterprise Linux 7 の KVM ハイパーバイザーで利用できます。本章では、実行中の仮想マシン (VM とも呼ばれる) のシステム要件の一覧を記載します。
仮想化パッケージのインストールに関する詳細は、 2章仮想化パッケージのインストール を参照してください。

1.1. ホストのシステム要件

最小ホストシステム要件

  • 6 GB の空きディスク領域
  • 2 GB の RAM

推奨されるシステム要件

  • 各仮想化 CPU に 1 つのコアまたはスレッド、およびホストに 1 つのコアまたはスレッド
  • 2 GB の RAM と仮想マシン用の追加の RAM
  • ホスト用に 6 GB のディスク領域、および仮想マシンに必要なディスク領域
    ほとんどのゲストオペレーティングシステムは少なくとも 6GB のディスク領域を必要とします。各ゲストの追加のストレージ領域はワークロードによって異なります。

    swap 領域

    Linux の swap 領域は、物理メモリー (RAM) の空き容量がなくなると使用されます。システムがより多くのメモリーリソースを必要とする場合、RAM に空き容量がないとメモリーの非アクティブなページが swap 領域に移されます。RAM の容量が小さいマシンでは swap 領域が役に立ちますが、容量の大きい RAM の代わりにしてはなりません。swap 領域は、物理メモリーよりもアクセスに時間がかかるハードドライブ上にあります。swap パーティションのサイズは、ホストの物理 RAM から計算できます。Red Hat カスタマーポータルのhttps://access.redhat.com/site/solutions/15244 には swap パーティションのサイズを安全かつ効果的に判別する方法が記載されています。
    • raw イメージファイルを使用する場合、必要なディスク領域の合計はイメージファイルで必要な領域、ホストオペレーティングシステムに必要な 6 GB の領域、およびゲストの swap 領域の合計と同等またはそれ以上となります。
      qcow イメージの場合、qcow および qcow2 イメージは必要に応じて拡大することから、ゲストの予測される最大ストレージ要件 (total for qcow format) も計算する必要があります。この拡大を可能にするには、まずゲストの予測される最大ストレージ要件 (expected maximum guest storage) を 1.01 倍し、これにホスト (host) で必要な領域と必要なスワップ領域 (swap) を加えます。
ゲスト仮想マシンの要件の詳細は、7章KVM でのオーバーコミット を参照してください。

1.2. KVM ハイパーバイザーの要件

KVM ハイパーバイザーには、以下が必要です。
  • x86 ベースシステム向けの Intel VT-x および Intel 64 仮想化拡張機能を備えた Intel プロセッサー
  • AMD-V および AMD64 仮想化拡張機能を備えた AMD プロセッサー
仮想化拡張機能 (Intel VT-x または AMD-V) は完全仮想化に必要です。以下のコマンドを入力し、システムにハードウェアの仮想化拡張機能があるかどうかや、それらが有効にされていることを判別します。

手順1.1 仮想化拡張機能の確認

  1. 利用できる CPU 仮想化拡張機能を確認します。

    次のコマンドを入力して利用できる CPU 仮想化拡張機能を確認します。
    $ grep -E 'svm|vmx' /proc/cpuinfo
  2. 出力を分析します。

    • 以下の出力例には、Intel VT-x 拡張の Intel プロセッサーを示す vmx エントリーが含まれています。
      flags   : fpu tsc msr pae mce cx8 vmx apic mtrr mca cmov pat pse36 clflush
      dts acpi mmx fxsr sse sse2 ss ht tm syscall lm constant_tsc pni monitor ds_cpl
      vmx est tm2 cx16 xtpr lahf_lm
    • 以下の出力例には、AMD-V 拡張の AMD プロセッサーを示す svm エントリーが含まれています。
      flags   :  fpu tsc msr pae mce cx8 apic mtrr mca cmov pat pse36 clflush
      mmx fxsr sse sse2 ht syscall nx mmxext svm fxsr_opt lm 3dnowext 3dnow pni cx16
      lahf_lm cmp_legacy svm cr8legacy ts fid vid ttp tm stc
    grep -E 'svm|vmx' /proc/cpuinfo コマンドが出力を返す場合、プロセッサーにはハードウェアの仮想化拡張機能が含まれます。場合によってはメーカーが BIOS で仮想化拡張機能を無効にすることがあります。拡張機能が表示されなかったり、完全仮想化が機能しない場合には、BIOS 設定ユーティリティーで拡張機能を有効にする方法について、手順A.3「BIOS での仮想化拡張の有効化」 を参照してください。
  3. KVM カーネルモジュールが読み込まれていることを確認します。

    追加のチェック事項として、以下のコマンドを使って kvm モジュールがカーネルに読み込まれていることを確認します。
    # lsmod | grep kvm
    出力に kvm_intel またはkvm_amd が含まれている場合は、kvm ハードウェア仮想化モジュールがロードされています。

注記

virsh ユーティリティー (libvirt-client パッケージで提供される) は、以下のコマンドを使ってシステムの仮想化機能の詳細一覧を出力します。
# virsh capabilities

1.3. KVM ゲスト仮想マシンの互換性

Red Hat Enterprise Linux 7 サーバーには、いくらかのサポート制限があります。
Red Hat Enterprise Linux のプロセッサーおよびメモリー容量の制限についての情報は、以下の URL をご覧ください。
以下の URL は、Red Hat Enterprise Linux KVM ホストでの実行が認定されているゲストオペレーティングシステムの一覧を表示しています。

注記

KVM ハイパーバイザーの制限およびサポート上の制限についての詳細は、付録C 仮想化の制限を参照してください。

1.4. ゲストのサポート対象 CPU モデル

それぞれのハイパーバイザーには、ゲストにデフォルトで表示する CPU 機能に関して独自のポリシーがあります。ハイパーバイザーがゲストに表示する CPU 機能のセットはゲスト仮想マシン設定で選択される CPU モデルによって異なります。

1.4.1. ゲスト CPU モデルの一覧表示

アーキテクチャーの種類に対応する CPU モデルの詳細一覧を確認するには、virsh cpu-models architecture コマンドを実行します。以下は例になります。
$ virsh cpu-models x86_64
486
pentium
pentium2
pentium3
pentiumpro
coreduo
n270
core2duo
qemu32
kvm32
cpu64-rhel5
cpu64-rhel6
kvm64
qemu64
Conroe
Penryn
Nehalem
Westmere
SandyBridge
Haswell
athlon
phenom
Opteron_G1
Opteron_G2
Opteron_G3
Opteron_G4
Opteron_G5
$ virsh cpu-models ppc64
POWER7
POWER7_v2.1
POWER7_v2.3
POWER7+_v2.1
POWER8_v1.0
サポート対象の CPU モデルおよび機能は、cpu_map.xml にある /usr/share/libvirt/ ファイルに記載されています。
# cat /usr/share/libvirt/cpu_map.xml
ゲストの CPU モデルおよび機能は、ドメイン XML ファイルの <cpu> セクションで変更できます。詳細は、「CPU モデルおよびトポロジー」 を参照してください。
ホストのモデルは、必要に応じて指定された機能を使用するように設定できます。詳細は、「指定 CPU に設定された機能の変更」 を参照してください。

第2章 仮想化パッケージのインストール

仮想化を使用するには、コンピューターに Red Hat 仮想化パッケージをインストールする必要があります。仮想化パッケージは、yum コマンドおよび Subscription Manager を使用して Red Hat Enterprise Linux のインストール時またはインストール後にインストールすることができます。
KVM ハイパーバイザーは、kvm カーネルモジュールを使うデフォルトの Red Hat Enterprise Linux カーネルを使用します。

2.1. Red Hat Enterprise Linux インストール時の仮想化パッケージのインストール

このセクションでは、Red Hat Enterprise Linux のインストール時に仮想化パッケージをインストールする方法について説明します。

注記

Red Hat Enterprise Linux のインストールに関する詳細は『Red Hat Enterprise Linux 7 インストールガイド』を参照してください。

重要

Anaconda インターフェースは、Red Hat Enterprise Linux サーバーのインストール時に Red Hat 仮想化パッケージをインストールする方法を提供します。
Red Hat Enterprise Linux Workstation をインストールする場合、ワークステーションのインストールが完了した後のみ Red Hat の仮想化パッケージをインストールできます。「既存の Red Hat Enterprise Linux システム上への仮想化パッケージのインストール」 を参照してください。

手順2.1 仮想化パッケージのインストール

  1. ソフトウェアを選択します。

    インストールの手順にしたがってインストールの概要 画面に移動します。
    Image shows the Installation Summary screen, which lists configurable options under group headings. Under the Localization heading : Date & Time, Language Support, and Keyboard. Under the Software heading: Installation Source and Software Selection. Under the System heading: Installation Destination and Network & Hostname.

    図2.1 「インストールの概要」画面

    インストールの概要 画面で ソフトウェアの選択 をクリックします。ソフトウェアの選択 画面が表示されます。
  2. サーバータイプとパッケージグループを選択します。

    Red Hat Enterprise Linux 7 は、基本的な仮想化パッケージまたはグラフィカルユーザーインターフェースでのゲスト管理を可能にするパッケージでインストールできます。以下のいずれかを実行します。
    • 最小限の仮想化ホストのインストール
      ベース環境 ぺインの下の 仮想化ホスト ラジオボタンを選択し、選択した環境のアドオン ペインの下の Virtualization Platform (仮想化プラットフォーム) チェックボックスを選択します。これにより、virsh で実行でき、ネットワーク経由のリモートで実行できる基本の仮想化環境がインストールされます。
      Image shows the Software Selection screen, which lists options under two headings: Base Environment and Add-Ons for Selected Environment. Virtualization Host is highlighted from the options under Base Environment, and Virtualization Platform is highlighted from the options under Add-Ons for Selected Environment.

      図2.2 「ソフトウェアの選択」画面で選択される仮想化ホスト

    • グラフィカルユーザーインターフェースを使った仮想化ホストのインストール
      ベース環境 ペインの Server with GUI (GUI のあるサーバー) ラジオボタンと、選択した環境のアドオン ペインにある Virtualization Client (仮想化クライアント)Virtualization Hypervisor (仮想化ハイパーバイザー)、および Virtualization Tools (仮想化ツール) のチェックボックスを選択します。これにより、ゲスト仮想マシンをインストールおよび管理するグラフィカルツールとともに仮想化環境がインストールされます。
      Image shows the Software Selection screen, which lists options under two headings: Base Environment and Add-Ons for Selected Environment. Server with GUI is highlighted from the options under Base Environment, and Virtualization Client, Virtualization Hypervisor, and Virtualization Tools are highlighted from the options under Add-Ons for Selected Environment.

      図2.3 「ソフトウェアの選択」画面で選択される Server with GUI

  3. インストールを終了します。

    完了 をクリックし、インストールを続行します。

重要

仮想化パッケージの更新を受信するには、有効な Red Hat Enterprise Linux サブスクリプションが必要です。

2.1.1. キックスタートファイルによる KVM パッケージのインストール

キックスタートファイルを使用して、仮想化パッケージとともに Red Hat Enterprise Linux をインストールするには、キックスタートファイルの %packages セクションに以下のパッケージグループを追加します。
@virtualization-hypervisor
@virtualization-client
@virtualization-platform
@virtualization-tools
キックスタートファイルのインストールに関する詳細は、『Red Hat Enterprise Linux 7 インストールガイド』を参照してください。

2.2. 既存の Red Hat Enterprise Linux システム上への仮想化パッケージのインストール

このセクションでは、既存の Red Hat Enterprise Linux 7 システムに KVM ハイパーバイザーをインストールするステップを説明します。
パッケージをインストールするには、Red Hat カスタマーポータルにマシンを登録して、サブスクライブする必要があります。Red Hat Subscription Manager を使用して登録するには、subscription-manager register コマンドを実行して、プロンプトにしたがいます。別の方法として、デスクトップの アプリケーションシステムツール から Red Hat Subscription Manager アプリケーションを実行して登録できます。
有効な Red Hat サブスクリプションがない場合は、Red Hat のオンラインストア でサブスクリプションを取得してください。システムの Red Hat カスタマーポータルへの登録およびサブスクライブに関する詳細は、「https://access.redhat.com/solutions/253273」を参照してください。

2.2.1. 仮想化パッケージの手動インストール

Red Hat Enterprise Linux で仮想化を使用するには、最低でも以下のパッケージをインストールする必要があります。
  • qemu-kvm: このパッケージは、ユーザーレベルの KVM エミュレーターを使用し、ホストとゲスト仮想マシン間の通信を容易にします。
  • qemu-img: このパッケージは、ゲスト仮想マシンのディスク管理を提供します。

    注記

    qemu-img パッケージは qemu-kvm パッケージの依存関係としてインストールされます。
  • libvirt: このパッケージは、ハイパーバイザーおよびホストシステムと対話するためにサーバーおよびホスト側のライブラリーを提供し、ライブラリー呼び出しの処理、仮想マシンの管理、およびハイパーバイザーの制御を行う libvirtd デーモンも提供します。
これらのパッケージをインストールするには、以下のコマンドを入力します。
# yum install qemu-kvm libvirt
以下の仮想化管理パッケージも利用可能であり、仮想化の導入時に使用が推奨されています。
  • virt-install: このパッケージは、コマンドラインからの仮想マシンを作成するために virt-install コマンドを提供します。
  • libvirt-python: このパッケージは、Python プログラミング言語で書かれているアプリケーションが libvirt API で提供されるインターフェースを使用できるようにするモジュールが含まれています。
  • virt-manager: このパッケージは Virtual Machine Manager virt-manager ツールを提供します。これは、仮想マシンを管理するためのグラフィカルツールです。管理 API として libvirt-client ライブラリーを使用します。
  • libvirt-client: このパッケージは、libvirt サーバーにアクセスするためのクライアント側の API とライブラリーを提供します。libvirt-client パッケージには、コマンドラインまたは特別な仮想化シェルから仮想マシンとハイパーバイザーを管理および制御する virsh コマンドラインツールが含まれます。
これらの推奨される仮想化パッケージすべては、以下のコマンドを使ってインストールしてください。
# yum install virt-install libvirt-python virt-manager virt-install libvirt-client

2.2.2. 仮想化パッケージグループのインストール

仮想化パッケージは、パッケージグループからもインストールできます。以下の表は、仮想化パッケージグループとその役割について説明しています。

表2.1 仮想化パッケージグループ

パッケージグループ説明必須パッケージオプションパッケージ
Virtualization Hypervisor仮想化ホストの最小インストールlibvirt、qemu-kvm、qemu-imgqemu-kvm-tools
Virtualization Client仮想化インスタンスをインストールし、管理するためのクライアントgnome-boxes、virt-install、virt-manager、virt-viewer、qemu-imgvirt-top、libguestfs-tools、libguestfs-tools-c
Virtualization Platform仮想マシンおよびコンテナーにアクセスしたり制御したりするためのインターフェースを提供libvirt、libvirt-client、virt-who、qemu-imgfence-virtd-libvirt、fence-virtd-multicast、fence-virtd-serial、libvirt-cim、libvirt-java、libvirt-snmp、perl-Sys-Virt
Virtualization Toolsオフラインの仮想イメージを管理するためのツールlibguestfs、qemu-imglibguestfs-java、libguestfs-tools、libguestfs-tools-c
パッケージグループをインストールするには、yum groupinstall package_group コマンドを実行します。--optional オプションを使用してパッケージグループのオプションパッケージをインストールします。たとえば、すべてのオプションパッケージを含む Virtualization Tools パッケージグループをインストールするには、以下を実行します。
# yum groupinstall "Virtualization Tools" --optional

第3章 仮想マシンの作成

Red Hat Enterprise Linux 7 ホストシステム上に 仮想化パッケージ をインストールした後、virt-manager インターフェースを使用して仮想マシンを作成し、ゲストオペレーティングシステムをインストールできます。この代わりに、パラメーターのリストやスクリプトを使用して virt-install コマンドラインユーティリティーを使用できます。本章では両方の方法を取り上げます。

3.1. ゲスト仮想マシンのデプロイに関する留意事項

ゲスト仮想マシンを作成する前には、様々な要素を考慮する必要があります。デプロイ前に仮想マシンの役割を評価する必要がありますが、定期的なモニタリングと (負荷やクライアント数などの) 様々な要素に基づく評価も実行する必要があります。考慮に入れる要素には、以下が含まれます。
パフォーマンス
ゲスト仮想マシンは、意図されるタスクに基づいてデプロイし、設定することをお勧めします。ゲストシステムには、パフォーマンスについての特別な考慮が必要なものもあります (例: データベースサーバーを実行するゲスト)。ゲストの役割や予測されるシステム負荷によっては、ゲストがより多くの割り当て CPU やメモリーを必要とすることもあります。
入出力要件と入出力タイプ
ゲスト仮想マシンの中には、とくに高い入出力要件があるものや、入出力タイプ (例: 通常のディスクブロックサイズのアクセスまたはクライアント数) に応じてさらに注意や追加の予測が必要なものもあります。
ストレージ
ゲスト仮想マシンの中には、ストレージやより高速なディスクタイプへの優先度の高いアクセスを必要とするものもあります。ストレージのデプロイとメンテナンス時には、ゲストが使用するストレージ容量も定期的に監視して考慮することをお勧めします。『Red Hat Enterprise Linux 7 仮想化セキュリティーガイド』に説明されているすべての留意事項を確認してください。また、お使いの物理ストレージによって仮想ストレージのオプションが制限される可能性があることについても留意しておくことは重要です。
ネットワークおよびネットワークインフラストラクチャー
ゲスト仮想マシンの環境によっては、他のゲストより高速のネットワークリンクを必要とするものもあります。帯域幅や待ち時間はゲストのデプロイおよびメンテナンス時に考慮すべき要素になることが多く、要件や負荷が変化する場合はとくにそう言えます。
リクエスト要件
virtio ドライブがディスク全体をベースとし、以下の例のようにディスクデバイスパラメーターが ドメイン XML ファイルlun に設定されている場合にのみ、SCSI リクエストは virtio ドライブ上のゲスト仮想マシンに発行されます。
<devices>
  <emulator>/usr/libexec/qemu-kvm</emulator>
  <disk type='block' device='lun'>
                

3.2. virt-install を使用したゲストの作成

virt-install コマンドを使用して仮想マシンを作成し、コマンドラインからこれらの仮想マシン上でオペレーティングシステムをインストールできます。virt-install を対話的またはスクリプトの一部として使用すると、仮想マシンの作成を自動化できます。対話的なグラフィカルインストールを使用する場合は、virt-install を実行する前に virt-viewer をインストールする必要があります。さらに、virt-install をキックスタートファイルと使用すると、仮想マシンのオペレーティングシステムの無人インストールを開始できます。

注記

一部の virt-install コマンドが正常に完了するには、root 権限が必要になることがあります。
virt-install ユーティリティーは複数のコマンドラインオプションを使用しますが、ほとんどの virt-install オプションは必要ありません。
ゲスト仮想マシンのインストールに必要となる主なオプションは、以下のとおりです。
--name
仮想マシンの名前。
--memory
ゲストに割り当てられたメモリー (RAM) の容量 (MiB 単位)。
ゲストストレージ
以下のゲストストレージオプションのいずれかを使用します。
  • --disk
    仮想マシンのストレージ設定の詳細を指定します。--disk none オプションを使うと、ディスク領域を確保せずに仮想マシンが作成されます。
  • --filesystem
    ゲスト仮想マシンのファイルシステムへのパスを指定します。
インストール方法
以下のインストール方法のいずれかを使用します。
  • --location
    インストールメディアの場所を指定します。
  • --cdrom
    仮想 CD-ROM デバイスとして使われるファイルまたはデバイスを指定します。ISO イメージへのパスまたは CD-ROM デバイスへのパスのどちらかを指定することができます。最小限のブート ISO イメージを取得またはアクセスする URL を指定することもできます。
  • --pxe
    ゲストのインストールプロセスを開始するために、PXE ブートプロトコルを使用して初期 ramdisk およびカーネルをロードします。
  • --import
    OS のインストールプロセスをスキップし、既存のディスクイメージを利用してゲストを構築します。ブートに使用するデバイスは、disk または filesystem オプションで最初に指定するデバイスです。
  • --boot
    インストール後の VM ブート設定を指定します。このオプションでは、ブートデバイスの順序を指定し、オプションのカーネル引数を使ってカーネルおよび initrd を永続的にブートオフし、BIOS ブートメニューを有効にすることが可能です。
オプションの全リストを表示するには、以下のコマンドを入力します。
# virt-install --help
オプションの属性の全リストを表示するには、以下のコマンドを入力します。
# virt install --option=?
virt-installの man ページにも、各コマンドのオプション、重要な変数、および例が記載されています。
virt-install の実行前に、qemu-img を使用してストレージオプションを設定する必要があることもあります。qemu-img の使用に関する手順は、14章qemu-img の使用 を参照してください。

3.2.1. ISO イメージから仮想マシンをインストール

以下の例では、ISO イメージから仮想マシンがインストールされます。
# virt-install \ 
  --name guest1-rhel7 \ 
  --memory 2048 \ 
  --vcpus 2 \ 
  --disk size=8 \ 
  --cdrom /path/to/rhel7.iso \ 
  --os-variant rhel7 
--cdrom /path/to/rhel7.iso オプションを指定すると、特定の場所にある CD または DVD イメージから仮想マシンがインストールされます。

3.2.2. 仮想マシンイメージのインポート

以下の例では、仮想ディスクイメージから仮想マシンがインポートされます。
# virt-install \ 
  --name guest1-rhel7 \ 
  --memory 2048 \ 
  --vcpus 2 \ 
  --disk /path/to/imported/disk.qcow \ 
  --import \ 
  --os-variant rhel7 
--import オプションを指定すると、--disk /path/to/imported/disk.qcow オプションによって指定された仮想ディスクイメージから仮想マシンがインポートされます。

3.2.3. ネットワークから仮想マシンをインストール

以下の例では、ネットワークロケーションから仮想マシンがインストールされます。
# virt-install \ 
  --name guest1-rhel7 \ 
  --memory 2048 \ 
  --vcpus 2 \ 
  --disk size=8 \ 
  --location http://example.com/path/to/os \ 
  --os-variant rhel7 
--location http://example.com/path/to/os オプションは指定のネットワークの場所にあるインストールツリーを指定します。

3.2.4. PXE を使用した仮想マシンのインストール

PXE ブートプロトコルを使って仮想マシンをインストールする場合は、ブリッジネットワークを指定する --network オプションおよび --pxe オプションの両方を指定する必要があります。
以下の例では、PXE を使って仮想マシンがインストールされます。
# virt-install \ 
  --name guest1-rhel7 \ 
  --memory 2048 \ 
  --vcpus 2 \ 
  --disk size=8 \ 
  --network=bridge:br0 \ 
  --pxe \ 
  --os-variant rhel7 

3.2.5. キックスタートを使った仮想マシンのインストール

以下の例では、キックスタートファイルを使って仮想マシンがインストールされます。
# virt-install \ 
  --name guest1-rhel7 \ 
  --memory 2048 \ 
  --vcpus 2 \ 
  --disk size=8 \ 
  --location http://example.com/path/to/os \ 
  --os-variant rhel7 \
  --initrd-inject /path/to/ks.cfg \ 
  --extra-args="ks=file:/ks.cfg console=tty0 console=ttyS0,115200n8" 
initrd-inject および extra-args オプションを指定すると、仮想マシンはキックスタートファイルを使用してインストールされます。

3.2.6. ゲストの作成中にゲスト仮想マシンのネットワークを設定

ゲスト仮想マシンを作成する場合、仮想マシン用のネットワークを指定して設定することができます。このセクションでは、ゲスト仮想マシン用の主なネットワークタイプの各オプションについて説明します。

NAT を用いるデフォルトのネットワーク

デフォルトのネットワークは libvirtd のネットワークアドレス変換 (NAT) の仮想ネットワークスイッチを使用します。NAT の詳細については、「libvirt を使用した Network Address Translation (NAT)」 を参照してください。
NAT を用いるデフォルトのネットワークでゲスト仮想マシンを作成する前に、libvirt-daemon-config-network パッケージがインストールされていることを確認してください。
ゲスト仮想マシン用に NAT ネットワークを設定するには、virt-install の以下のオプションを使います。
--network default

注記

network オプションを指定しないと、ゲスト仮想マシンは NAT を用いるデフォルトのネットワークで設定されます。

DHCP を用いるブリッジネットワーク

ブリッジネットワーク用に設定された場合、ゲストは外部の DHCP サーバーを使用します。ホストが静的なネットワーキング設定で、ゲストがローカルエリアネットワーク (LAN) との完全な受送信接続を必要とする場合は、このオプションを使う必要があります。ゲスト仮想マシンを使ってライブマイグレーションを実施する場合は、このオプションを使う必要があります。ゲスト仮想マシン用に DHCP を用いるブリッジネットワークを設定するには、以下のオプションを使います。
--network br0

注記

virt-install を実行する前に、別途ブリッジを作成しておく必要があります。ネットワークブリッジ作成の詳細については、「Red Hat Enterprise Linux 7 ホストでのブリッジネットワークの設定」を参照してください。

静的な IP アドレスを用いるブリッジネットワーク

ブリッジネットワークを使って、ゲストが静的 IP アドレスを使うように設定することもできます。ゲスト仮想マシン用に静的な IP アドレスを用いるブリッジネットワークを設定するには、以下のオプションを使います。
--network br0 \
--extra-args "ip=192.168.1.2::192.168.1.1:255.255.255.0:test.example.com:eth0:none"
ネットワークブートオプションの詳細については、『Red Hat Enterprise Linux 7 インストールガイド』を参照してください。

ネットワーク設定なし

ゲスト仮想マシンにネットワークインターフェースを設定しない場合は、以下のオプションを使います。
--network=none

3.3. virt-manager を使用したゲストの作成

virt-manager としても知られる仮想マシンマネージャーは、ゲスト仮想マシンを作成し、管理するグラフィカルツールです。
このセクションでは、virt-manager を使用して Red Hat Enterprise Linux 7 ホスト上で Red Hat Enterprise Linux 7 ゲスト仮想マシンをインストールする方法を説明します。
以下の手順では、KVM ハイパーバイザーや他の必要なパッケージすべてがインストールされており、ホストが仮想化用に設定されていることを前提としてします。仮想化パッケージのインストールについての詳細は、2章仮想化パッケージのインストール を参照してください。

3.3.1. virt-manager によるインストールの概要

新しい仮想マシン ウィザードでは、仮想マシン作成が 5つ のステップで行われます。
  1. ハイパーバイザーとインストール方法の選択
  2. インストールメディアの場所の選択と設定
  3. メモリーと CPU オプションの設定
  4. 仮想マシンのストレージの設定
  5. 仮想マシンの名前、ネットワーク、アーキテクチャー、他のハードウェアの設定
次に進む前に、virt-manager がインストールメディアにアクセスできることを確認してください (ローカルまたはネットワーク経由)。

3.3.2. virt-manager を使用した Red Hat Enterprise Linux 7 ゲストの作成

以下の手順では、ローカルに保存されているインストール用 DVD や DVD イメージを使って Red Hat Enterprise Linux 7 のゲスト仮想マシンを作成する方法を説明します。Red Hat Enterprise Linux 7 の DVD イメージは、Red Hat カスタマーポータル から入手できます。

手順3.1 virt-manager およびローカルインストールメディアを使用した Red Hat Enterprise Linux 7 ゲスト仮想マシンの作成

  1. オプション: 準備

    仮想マシン用のストレージ環境を用意します。ストレージの準備に関する詳細は、13章仮想マシンのストレージ管理 を参照してください。

    重要

    ゲスト仮想マシンの保存には、様々な種類のストレージを使用することができます。しかし、仮想マシンで移行機能を使用できるようにするには、ネットワーク接続されたストレージ上に仮想マシンを作成する必要があります。
    Red Hat Enterprise Linux 7 には、少なくとも 1GB のストレージ領域が必要です。しかし Red Hat は、Red Hat Enterprise Linux 7 のインストールと本ガイドの手順で 5GB 以上のストレージ領域を使用することを推奨しています。
  2. virt-manager を開き、ウィザードを開始します。

    virt-manager を開くには、root で virt-manager コマンドを実行するか、または アプリケーションシステムツール仮想マシンマネージャー を開きます。
    仮想マシンマネージャーのウィンドウ

    図3.1 仮想マシンマネージャーのウィンドウ

    オプションとして、ハイパーバイザーを選択し、接続 (Connect) ボタンをクリックしてリモートハイパーバイザーを開きます。
    をクリックして、新規の仮想化ゲストウィザードを開始します。
    新しい仮想マシン ウィンドウが開きます。
  3. インストール方法を指定します。

    インストールの方法を選択します。
    ローカルのインストールメディア (ISO イメージまたは CD-ROM ドライブ)
    この方法では、CD-ROM か DVD、またはインストールディスクのイメージを使用します (例: .iso)。
    ネットワークインストール (HTTP、FTP、または NFS)
    この方法では、ミラー化された Red Hat Enterprise Linux または Fedora インストールツリーを使ってゲストをインストールします。インストールツリーには、HTTP または FTP、または NFS のいずれかでアクセスできる必要があります。
    ネットワークインストール を選択する場合には、インストール URL およびカーネルオプション (必要な場合) を指定します。
    ネットワークブート (PXE)
    この方法では、Preboot eXecution Environment (PXE) サーバーを使用してゲスト仮想マシンをインストールします。PXE サーバーの設定は、『Red Hat Enterprise Linux 7 インストールガイド』で説明されています。ネットワークブートでインストールするには、ゲストがルーティング可能な IP アドレスまたは共有ネットワークデバイスを備えている必要があります。
    ネットワークブート を選択する場合は、ステップ 5 に進みます。すべてのステップが完了すると DHCP 要求は送信され、有効な PXE サーバーが見つかる場合はゲスト仮想マシンのインストールプロセスが開始します。
    既存のディスクイメージをインポート
    この方法では、新しいゲスト仮想マシンを作成し、そこにディスクイメージ (インストール済みの起動可能なオペレーティングシステムを含む) をインポートできます。
    仮想マシンのインストール方法

    図3.2 仮想マシンのインストール方法

    進む をクリックして先に進みます。
  4. インストールソースを選択します。

    1. ローカルのインストールメディア (ISO イメージまたは CD-ROM ドライブ) を選択した場合、目的のローカルインストールメディアを指定します。
      ローカル ISO イメージのインストール

      図3.3 ローカル ISO イメージのインストール

      • CD-ROM または DVD からインストールする場合は、CD-ROM または DVD を使用 ラジオボタンを選択し、利用可能なドライブのドロップダウンリストから適切なディスクドライブを選択します。
      • ISO イメージからインストールする場合は、ISO イメージを使用 を選択し、参照... ボタンをクリックして ISO メディアボリュームの検索 ウィンドウを開きます。
        使用するインストールイメージを選択し、ボリュームの選択 をクリックします。
        ISO メディアボリュームの検索 ウィンドウにイメージが表示されない場合、ローカルを参照 ボタンをクリックしてホストマシンにあるインストールイメージまたはインストールディスクのある DVD ドライブを参照します。インストールイメージまたはインストールディスクのある DVD ドライブを選択して 開く をクリックします。使用するボリュームが選択され、新しい仮想マシンを作成 ウィザードに戻ります。

        重要

        ISO イメージファイルまたはゲストストレージファイルの推奨される場所は、/var/lib/libvirt/images/ です。それ以外の場所を指定する場合、SELinux による追加の設定が必要になる可能性があります。SELinux の設定に関する詳細は、『Red Hat Enterprise Linux 7 仮想化セキュリティーガイド』または『Red Hat Enterprise Linux 7 SELinux ユーザーおよび管理者のガイド』を参照してください。
    2. Network Install を選択した場合には、インストールソースの URL および希望するカーネルオプション (必要な場合) を入力します。URL は、インストールツリーのルートディレクトリーをポイントしている必要があります。また、インストールツリーには、HTTP、FTP、または NFS のいずれかでアクセスできる必要があります。
      キックスタートインストールを実施するには、カーネルのオプション でキックスタートファイルの URL を指定します (ks= で始めます)。
      ネットワーク経由のキックスタートインストール

      図3.4 ネットワーク経由のキックスタートインストール

      注記

      カーネルオプションの全リストは、『Red Hat Enterprise Linux 7 インストールガイド』を参照してください。
    次に、インストールする OS の種類バージョン を選びます。仮想マシンに適したオペレーティングシステムの種類を選択することを確認してください。これは、インストールメディアに応じて、仮想マシン内の OS の種類を自動判別する (Automatically detect operating system based on install media) チェックボックスを選択して手動で指定することができます。
    進む をクリックして先に進みます。
  5. メモリー (RAM) および 仮想 CPU を設定します。

    仮想マシンに割り当てる CPU の数とメモリー (RAM) の容量を設定します。ウィザードでは、割り当て可能な CPU の数とメモリー量が表示されます。これらの値はホストとゲストのパフォーマンスに影響を与えます。
    仮想マシンの効率的かつ効果的な実行には、十分な物理メモリー (RAM) が必要です。Red Hat は、仮想マシンの最小 512MB の RAM をサポートします。1 論理コアあたりでは最小 1024MB の RAM を推奨します。
    十分な数の仮想 CPU を仮想マシンに割り当てます。仮想マシンがマルチスレッドアプリケーションを実行する場合は、ゲスト仮想マシンの効果的な実行に必要な数の仮想 CPU を割り当てます。
    ホストシステムで利用可能な物理プロセッサー (またはハイパースレッド) よりも多くの仮想 CPU を割り当てることはできません。利用可能な仮想 CPU 数は、X 個まで使用できます フィールドに表示されます。
    メモリーと CPU の設定

    図3.5 メモリーと CPU の設定

    メモリーと CPU の設定を行った後に、進む をクリックして次に進みます。

    注記

    メモリーと仮想 CPU はオーバーコミットすることができます。オーバーコミットに関する詳細は、7章KVM でのオーバーコミット を参照してください。
  6. ストレージを設定します。

    仮想マシンと必要とされるアプリケーションに十分な領域を有効にし、その割り当てを実行します。デスクトップインストールの場合は少なくとも 5GB を割り当て、最小インストールの場合は少なくとも 1GB を割り当てます。
    仮想ストレージの設定

    図3.6 仮想ストレージの設定

    注記

    ライブおよびオフラインマイグレーションの場合は、仮想マシンを共有ネットワークストレージにインストールする必要があります。仮想マシン用の共有ストレージの設定に関する詳細は、「共有ストレージの例: 単純な移行に NFS を使用する」を参照してください。
    1. デフォルトのローカルストレージを使用

      コンピューターのハードディスク上にディスクイメージを作成する ラジオボタンを選択し、デフォルトのストレージプールの /var/lib/libvirt/images/ ディレクトリーにファイルベースのイメージを作成します。作成するディスクイメージのサイズを入力します。今すぐディスク全体を割り当てる チェックボックスが選択されていると、指定されたサイズのディスクイメージが即時に作成されます。選択されていない場合は、ディスクイメージは要求に応じて大きくなります。

      注記

      ストレージプールは仮想コンテナーであるものの、qemu-kvm によって許可される最大サイズとホストの物理マシン上のディスクサイズの 2 つの要素によって制限されます。ストレージプールはホスト物理マシンのディスクサイズを超えることはできません。最大サイズは以下のようになります。
      • virtio-blk = 2^63 バイトまたは 8 エクサバイト (raw ファイルまたはディスクを使用)
      • Ext4 = ~ 16 TB (using 4 KB block size)
      • XFS = ~8 Exabytes
      • qcow2 とホストファイルシステムはそれぞれ独自のメタデータを維持します。非常に大きなイメージサイズを使用する場合はスケーラビリティーの評価または調整を行う必要があります。raw ディスクを使用すると、スケーラビリティーや最大サイズに影響を与える可能性のある層の数が少なくなります。
      進む をクリックしてローカルのハードドライブにディスクイメージを作成します。または、管理しているストレージか、他の既存のストレージを選択する を選択してから 参照 を選択し、管理しているストレージを設定します。
    2. ストレージプールの使用

      ストレージプールの使用に 管理しているストレージか、他の既存のストレージを選択する を選択し、参照 をクリックすると、ストレージボリュームの検索または作成 ウィンドウが開きます。
      「ストレージボリュームの選択」ウィンドウ

      図3.7 「ストレージボリュームの選択」ウィンドウ

      1. ストレージプール 一覧からストレージプールを選択します。
      2. オプション: をクリックして新しいストレージボリュームを作成します。ストレージボリュームを作成 (Add a Storage Volume) 画面が表示されます。新しいストレージボリュームの名前を入力します。
        フォーマット ドロップダウンメニューからフォーマットのオプションを選択します。フォーマットオプションには、raw、qcow2 および qed があります。必要に応じて他のフィールドも調整します。ここで使用されている qcow2 バージョンはバージョン 3 であることに注意してください。qcow バージョンを変更するには、「target 要素の設定」を参照してください。
        「ストレージボリュームを作成 (Add a Storage Volume)」ウィンドウ

        図3.8 「ストレージボリュームを作成 (Add a Storage Volume)」ウィンドウ

    新規ボリュームを選択し、ボリュームの選択 をクリックします。次に、完了 をクリックして 新しい仮想マシン ウィザードに戻ります。進む をクリックして次に進みます。
  7. 名前を付けて最終設定を行います。

    仮想マシンに名前を付けます。仮想マシンの名前には、文字、数字、およびアンダースコア (_)、ピリオド (.)、ハイフン (-) などの文字を使用することができます。仮想マシンを移行するには、仮想マシンの名前は一意でなければならず、数字のみの名前は使用できません。
    デフォルトで、仮想マシンは 'default' というネットワークについて Network Address Translation (NAT) を使用して作成されます。ネットワークの選択を変更するには、Network selection をクリックしてホストデバイスとソースモードを選択します。
    仮想マシンの設定を確認し、問題がなければ完了 をクリックします。指定されたネットワーク設定、仮想化の種類およびアーキテクチャーで仮想マシンが作成されます。
    設定の確認

    図3.9 設定の確認

    または、仮想マシンのハードウェアをさらに設定する場合は、インストールの前に設定をカスタマイズする チェックボックスにチェックを入れます。これによりゲストのストレージまたはネットワークデバイスの変更や、準仮想化 (virtio) ドライバーの使用や、ドライバーの追加を実行できます。ここから別のウィザードが開き、仮想マシンのハードウェア設定で追加や削除、設定が可能になります。

    注記

    Red Hat Enterprise Linux 4 または Red Hat Enterprise Linux 5 のゲスト仮想マシンは、グラフィカルモードを使用してインストールすることができません。そのため、ビデオカードには「QXL」ではなく「Cirrus」を選択する必要があります。
    仮想マシンのハードウェアを設定した後に 適用 をクリックします。virt-manager が指定されたハードウェア設定で仮想マシンを作成します。

    警告

    Red Hat Enterprise Linux 7 のゲスト仮想マシンを、設定済みの TCP/IP 接続なしにリモートメディアからインストールすると、インストールは失敗します。ただし、この状況で Red Hat Enterprise Linux 5 または 6 のゲスト仮想マシンをインストールすると、インストーラーは「Configure TCP/IP (TCP/IP の設定)」インターフェースを開きます。
    この違いについての詳細は、関連するナレッジベース記事 を参照してください。
    完了 ボタンをクリックして Red Hat Enterprise Linux インストールを継続します。Red Hat Enterprise Linux 7 のインストール方法の詳細は、『Red Hat Enterprise Linux 7 インストールガイド』を参照してください。
これで ISO インストールディスクイメージから Red Hat Enterprise Linux 7 ゲスト仮想マシンが作成されました。

3.4. virt-install および virt-manager のインストールオプションの比較

以下の表は、仮想マシンのインストール時のオプションとして、同等のvirt-installvirt-manager のインストールオプションを比較しています。
ほとんどの virt-install オプションは必須ではありません。最小要件として、--name--memory、ゲストストレージ (--disk--filesystem、または --disk none)、およびインストール方法 (--location--cdrom--pxe--import、または boot) が必要になります。これらのオプションは引数によってさらに詳細化されます。コマンドオプションと関連する引数の詳細の一覧を表示するには、以下のコマンドを入力します。
# virt-install --help
virt-manager では、最小要件として、名前、インストール方法、メモリー (RAM)、仮想 CPU (vCPU)、ストレージが必要になります。

表3.1 ゲストのインストールに関する virt-install と virt-manager の設定の比較

仮想マシンの設定virt-install オプションvirt-manager インストールウィザードのラベルとステップ番号
仮想マシン名--name, -n名前 (ステップ 5)
割り当てる RAM (MiB)--ram, -rメモリー (RAM) (ステップ 3)
ストレージ - ストレージメディアの指定--diskこの仮想マシンにストレージデバイスを割り当てます。→ コンピューターのハードディスク上にディスクイメージを作成する、または管理しているか、他の既存のストレージを選択する (ステップ 4)
ストレージ - ホストのディレクトリーをゲストにエクスポート--filesystemこの仮想マシンにストレージデバイスを割り当てます。→ 管理しているか、他の既存のストレージを選択する (ステップ 4)
ストレージ - ゲストにローカルのディスクストレージを設定しない--nodisks「この仮想マシンにストレージデバイスを割り当てます。」チェックボックスの選択解除 (ステップ 4)
インストールメディアの場所 (ローカルインストール)--fileローカルのインストールメディア → インストールメディアの場所 (ステップ 1-2)
ディストリビューションツリーからのインストール (ネットワークインストール)--locationネットワークインストール → URL (ステップ 1-2)
PXE を使用したゲストのインストール--pxeネットワークブート (ステップ 1)
仮想 CPU 数--vcpusCPU (ステップ 3)
ホストのネットワーク--network「詳細なオプション (Advanced options)」ドロップダウンメニュー (ステップ 5)
オペレーティングシステムのバリアント/バージョン--os-variantバージョン (ステップ 2)
グラフィカル表示の方法--graphics, --nographics* virt-manager は GUI インストールのみを提供します

第4章 仮想マシンのクローン作成

ゲストのコピーを作成する場合、2 種類のゲスト仮想マシンのインスタンスが使われます。
  • クローン は単一の仮想マシンのインスタンスです。クローンは、同一の仮想マシンのネットワークを設定するのに使うことができ、別の場所に分散させることもできます。
  • テンプレート は、クローン作成元として使われるように作られた仮想マシンのインスタンスです。テンプレートから複数のクローンを作成し、それぞれのクローンに若干の変更を加えることができます。このことは、これらの変更がシステムに及ぼす影響を把握する場合に役立ちます。
クローンおよびテンプレートは、共に仮想マシンのインスタンスです。両者の違いは、その使われ方です。
作成したクローンが正常に機能するためには、クローンを作成する前にクローン作成元の仮想マシンに固有な情報および設定を削除する必要があります。削除すべき情報は、クローンの使われ方によって異なります。
削除すべき情報および設定は、以下に示すレベルのいずれかに属します。
  • プラットフォームレベル の情報および設定は、仮想化ソリューションによって仮想マシンに割り当てられたものです。ネットワークインターフェースカード (NIC) の番号およびその MAC アドレス等が含まれます。
  • ゲストオペレーティングシステムレベル の情報および設定は、仮想マシン内で設定されたものです。SSH キー等が含まれます。
  • アプリケーションレベル の情報および設定は、仮想マシンにインストールされたアプリケーションによって設定されたものです。アクティベーションコードおよび登録情報などが含まれます。

    注記

    本章では、アプリケーションレベルの情報および設定を削除する手順については説明しません。情報および考え方がアプリケーションごとに異なるためです。
したがって、一部の情報および設定は仮想マシン内で削除する必要があり、一方、仮想化環境 (仮想マシンマネージャーまたは VMware 等) を使って仮想マシンから削除しなければならない情報および設定もあります。

注記

ストレージボリュームのクローン作成についての情報は、「virsh を使用したストレージボリュームの作成」 を参照してください。

4.1. 仮想マシンのクローン作成準備

仮想マシンのクローンを作成する前に、そのディスクイメージの virt-sysprep ユーティリティーを実行するか、以下の手順を使って準備を行う必要があります。

手順4.1 仮想マシンのクローン作成準備

  1. 仮想マシンの設定

    1. クローンまたはテンプレートに使われる仮想マシンを構築します。
      • クローンで必要となるソフトウェアをすべてインストールします。
      • オペレーティングシステムに固有ではない設定をすべて定義します。
      • アプリケーションに固有ではない設定をすべて定義します。
  2. ネットワーク設定の削除

    1. 以下のコマンドを使って、永続的な udev ルールをすべて削除します。
      # rm -f /etc/udev/rules.d/70-persistent-net.rules

      注記

      udev ルールが削除されない場合は、1 番目の NIC の名前が eth0 ではなく eth1 の可能性があります。
    2. /etc/sysconfig/network-scripts/ifcfg-eth[x] を以下のように編集して、ifcfg スクリプトから固有のネットワーク情報を削除します。
      1. HWADDR および Static 行を削除します

        注記

        HWADDR と新しいゲストの MAC アドレスが一致していないと、ifcfg は無視されます。したがって、ファイルから HWADDR を削除することが重要です。
        DEVICE=eth[x]
        BOOTPROTO=none
        ONBOOT=yes
        #NETWORK=10.0.1.0       <- REMOVE
        #NETMASK=255.255.255.0  <- REMOVE
        #IPADDR=10.0.1.20       <- REMOVE
        #HWADDR=xx:xx:xx:xx:xx  <- REMOVE
        #USERCTL=no             <- REMOVE
        # Remove any other *unique* or non-desired settings, such as UUID.
      2. HWADDR または固有の情報が削除され、DHCP 設定が維持されていることを確認します。
        DEVICE=eth[x]
        BOOTPROTO=dhcp
        ONBOOT=yes
      3. ファイルに以下の行が含まれていることを確認します。
        DEVICE=eth[x]
        ONBOOT=yes
    3. 以下のファイルが存在する場合は、内容が同じであることを確認します。
      • /etc/sysconfig/networking/devices/ifcfg-eth[x]
      • /etc/sysconfig/networking/profiles/default/ifcfg-eth[x]

      注記

      仮想マシンで NetworkManager または何らかの特殊な設定が使われた場合には、その他すべての固有の情報が ifcfg スクリプトから削除されていること確認します。
  3. 登録情報の削除

    1. 以下のいずれかの方法で、登録情報を削除します。
      • Red Hat Network (RHN) に登録されたゲスト仮想マシンの場合は、以下のコマンドを実行します。
        # rm /etc/sysconfig/rhn/systemid
      • Red Hat サブスクリプションマネージャー (RHSM) に登録されたゲスト仮想マシンの場合:
        • クローン元の仮想マシンが使われない場合は、以下のコマンドを実行します。
          # subscription-manager unsubscribe --all
          # subscription-manager unregister
          # subscription-manager clean
        • クローン元の仮想マシンが使われる場合は、以下のコマンドだけを実行します。
          # subscription-manager clean

          注記

          元の RHSM プロファイルはポータルに残されます。
  4. その他の固有情報の削除

    1. 以下のコマンドを使って、sshd パブリック/プライベートキーのペアを削除します。
      # rm -rf /etc/ssh/ssh_host_*

      注記

      SSH キーを削除することで、SSH クライアントがこれらのホストを信頼しないという問題を防ぐことができます。
    2. アプリケーション固有の識別子、または複数のマシンで実行した場合に競合する恐れのある設定をすべて削除します。
  5. 次回起動時に設定ウィーザードを実行するように仮想マシンを設定

    1. 以下のいずれかの方法で、次回起動時に適切な設定ウィザードが実行されるように、仮想マシンを設定します。
      • Red Hat Enterprise Linux 6 およびそれ以前のバージョンでは、以下のコマンドを使って、ルートファイルシステムに .unconfigured という名前の空ファイルを作成します。
        # touch /.unconfigured
      • Red Hat Enterprise Linux 7 では、次のコマンドを実行して first boot および initial-setup ウィザードを有効にします。
        # sed -ie 's/RUN_FIRSTBOOT=NO/RUN_FIRSTBOOT=YES/' /etc/sysconfig/firstboot
        # systemctl enable firstboot-graphical
        # systemctl enable initial-setup-graphical

      注記

      次回起動時に実行されるウィザードは、仮想マシンから削除された設定により異なります。また、クローンの初回起動時に、ホスト名を変更することを推奨します。

4.2. 仮想マシンのクローン作成

クローン作成手順を進める前に、仮想マシンをシャットダウンします。virt-clone または virt-manager を使って仮想マシンのクローンを作成することができます。

4.2.1. virt-clone を使用したゲストのクローン作成

virt-clone を使って、コマンドラインから仮想マシンのクローンを作成できます。
virt-clone を正しく完了するには、root 権限が必要となることに注意してください。
virt-clone コマンドは、コマンドラインで渡すことのできる数多くのオプションを提供します。これらには、一般的なオプション、ストレージ設定のオプション、ネットワーク設定のオプション、およびその他のオプションが含まれます。必須となるのは --original のみです。オプションの詳細の一覧を表示するには、以下のコマンドを入力します。
# virt-clone --help
virt-cloneの man ページにも、各コマンドのオプション、重要な変数、および例が記載されています。
以下の例は、デフォルト接続で「demo」というゲスト仮想マシンをクローン作成する方法を示しています。新規の名前とディスクのクローンパスが自動生成されます。

例4.1 virt-clone を使用したゲストのクローン作成

# virt-clone --original demo --auto-clone
以下の例は、複数のディスクと共に「demo」という QEMU ゲスト仮想マシンをクローン作成する方法を示しています。

例4.2 virt-clone を使用したゲストのクローン作成

# virt-clone --connect qemu:///system --original demo --name newdemo --file /var/lib/libvirt/images/newdemo.img --file /var/lib/libvirt/images/newdata.img

4.2.2. virt-manager を使用したゲストのクローン作成

以下の手順では、virt-manager ユーティリティーを使用してゲスト仮想マシンのクローンを作成する方法を説明します。

手順4.2 virt-manager を使用した仮想マシンのクローン作成

  1. virt-manager を開きます。

    virt-manager を開始します。アプリケーション メニューを開き、システムツール サブメニューから 仮想マシンマネージャー アプリケーションを起動します。または、root で virt-manager コマンドを実行します。
    Virtual Machine Manager のゲスト仮想マシンの一覧からクローン作成するゲスト仮想マシンを選択します。
    クローン作成するゲスト仮想マシンを右クリックして、クローン を選択します。「仮想マシンのクローンを作成」ウィンドウが開きます。
    「仮想マシンのクローンを作成」ウィンドウ

    図4.1 「仮想マシンのクローンを作成」ウィンドウ

  2. クローンを設定します。

    • クローンの名前を変更するには、クローンの新規の名前を入力します。
    • ネットワーク設定を変更するには、詳細 をクリックします。
      クローンの新しい MAC アドレスを入力します。
      OK をクリックします。
      「MAC アドレスを変更」ウィンドウ

      図4.2 「MAC アドレスを変更」ウィンドウ

    • クローン作成されたゲスト仮想マシンのそれぞれのディスクについて、以下のオプションのいずれかを選択します。
      • Clone this disk: ディスクのクローンはクローン作成されたゲスト仮想マシンから作成されます。
      • Share disk with guest virtual machine name: ディスクは、クローン作成されるゲスト仮想マシンとそのクローンによって共有されます。
      • Details: 「ストレージパスを変更」ウィンドウが開きます。ここからディスクの新規パスを選択できます。
        「storage pathを変更」ウィンドウ

        図4.3 「storage pathを変更」ウィンドウ

  3. ゲスト仮想マシンのクローンを作成します。

    クローン をクリックします。

第5章 KVM 準仮想化 (virtio) ドライバー

準仮想化ドライバーはゲストのパフォーマンスを強化し、I/O 待ち時間を短縮すると共に、スループットをベアメタルレベル近くにまで高めます。I/O 負荷の高いタスクとアプリケーションを実行する完全仮想マシンには、準仮想化ドライバーの使用が推奨されます。
virtio ドライバーは、KVM ホスト上で実行されるゲスト仮想マシンに利用できる KVM の準仮想化デバイスドライバーです。これらのドライバーは、virtio パッケージに含まれています。virtio パッケージは、ブロック (ストレージ) デバイスとネットワークインターフェースコントローラーに対応しています。

注記

PCI デバイスは、仮想化システムアーキテクチャーによる制限を受けます。割り当てデバイスの使用時の追加の制限については、16章ゲスト仮想マシンデバイスの設定 を参照してください。

5.1. 既存ストレージデバイスでの KVM virtio ドライバーの使用

ゲストに割り当てられている既存ハードディスクデバイスを変更して、仮想化 IDE ドライバーの代わりに virtio ドライバーを使用することができます。このセクションの例では、libvirt 設定ファイルを編集します。これらのステップを実行するためにゲスト仮想マシンをシャットダウンする必要はありませんが、変更が適用されるには、ゲストを完全にシャットダウンして再起動する必要があります。

手順5.1 既存デバイスでの KVM virtio ドライバーの使用

  1. この手順を実行する前に、適切なドライバー (viostor) がインストールされていることを確認してください。
  2. root で virsh edit guestname コマンドを実行し、デバイスの XML 設定ファイルを編集します。たとえば、virsh edit guest1 のようになります。設定ファイルは、/etc/libvirt/qemu/ ディレクトリーにあります。
  3. 以下の例は、仮想化 IDE ドライバーを使用したファイルベースのブロックデバイスです。これは、virtio ドライバーを使用しない仮想マシンの通常のエントリーです。
    <disk type='file' device='disk'>
    	 ...
       <source file='/var/lib/libvirt/images/disk1.img'/>
       <target dev='hda' bus='ide'/>
    	 <address type='pci' domain='0x0000' bus='0x00' slot='0x07' function='0x0'/>
    </disk>
  4. virtio デバイスを使用するために、bus= エントリーを virtio に変更します。ディスクが以前に IDE だった場合は、hdahdbhdc などと同様のターゲットを持ちます。bus=virtio に変更する場合は、ターゲットもそれに応じて vdavdbvdc に変更する必要があります。
    <disk type='file' device='disk'>
       ...
       <source file='/var/lib/libvirt/images/disk1.img'/>
       <target dev='vda' bus='virtio'/>
    	 <address type='pci' domain='0x0000' bus='0x00' slot='0x07' function='0x0'/>
    </disk>
  5. disk タグ内の address タグを削除します。これは、この手順が動作するために必要な作業です。仮想マシンの次回起動時に、libvirt が適切に address タグを再生成します。
別の方法としては、virtio ドライバーを使用して virt-managervirsh attach-disk、または virsh attach-interface で新規デバイスを追加することもできます。
Virtio の使用方法の詳細については、libvirt の web サイト http://www.linux-kvm.org/page/Virtio を参照してください。

5.2. 新規ストレージデバイスでの KVM virtio ドライバーの使用

ここでは、KVM virtio ドライバーを使用した virt-manager での新規ストレージデバイスの作成について説明します。
別の方法としては、virtio ドライバーを使用し、virsh attach-disk または virsh attach-interface コマンドでデバイスを割り当てることもできます。

重要

新規デバイスのインストールに進む前に、ゲストにドライバーがインストールされていることを確認してください。ドライバーが利用可能でない場合、デバイスは認識されず、動作しません。

手順5.2 virtio ストレージドライバーを使用したストレージデバイスの追加

  1. virt-manager でゲスト名をダブルクリックしてゲスト仮想マシンを開きます。
  2. をクリックして、仮想マシンの情報を表示 タブを開きます。
  3. 仮想マシンの情報を表示 タブで、ハードウェアを追加 ボタンをクリックします。
  4. ハードウェアの種類を選択します。

    ストレージハードウェアの種類 を選びます。
    The Add new virtual hardware wizard with Storage selected as the hardware type.

    図5.1 新しい仮想ハードウェアを追加ウィザード

  5. ストレージデバイスとドライバーの選択

    新規ディスクイメージを作成するか、ストレージプールボリュームを選択します。
    デバイスの種類ディスクデバイス に、バスの種類VirtIO に設定して virtio ドライバーを使用します。
    The Add new virtual hardware wizard Storage window, with "Create a disk image on the computer's hard drive" selected.

    図5.2 新しい仮想ハードウェアを追加ウィザード

    完了 をクリックして終了します。

手順5.3 virtio ネットワークドライバーを使用したネットワークデバイスの追加

  1. virt-manager でゲスト名をダブルクリックしてゲスト仮想マシンを開きます。
  2. をクリックして、仮想マシンの情報を表示 タブを開きます。
  3. 仮想マシンの情報を表示 タブで、ハードウェアを追加 ボタンをクリックします。
  4. ハードウェアの種類を選択します。

    ネットワークハードウェアの種類 を選びます。
    The Add new virtual hardware wizard with Network selected as the hardware type.

    図5.3 新しい仮想ハードウェアを追加ウィザード

  5. ネットワークデバイスとドライバーを選択します。

    Device model (デバイスのモデル)virtio に設定して virtio ドライバーを使用します。必要な ホストデバイス を選択します。
    The Add new virtual hardware wizard Network window, with Device model set to virtio.

    図5.4 新しい仮想ハードウェアを追加ウィザード

    完了 をクリックして終了します。
すべての新規デバイスが追加されたら、仮想マシンを再起動します。仮想マシンはゲストが再起動するまでデバイスを認識しない可能性があります。

5.3. ネットワークインターフェースデバイスでの KVM virtio ドライバーの使用

ネットワークインターフェースが KVM virtio ドライバーを使用する場合、KVM はネットワークハードウェアをエミュレートしないため、処理のオーバーヘッドが発生せず、ゲストのパフォーマンスを向上することができます。Red Hat Enterprise Linux 7 では、virtio はデフォルトのネットワークインターフェースタイプとして使用されますが、ご使用のシステムで virtio の設定が異なる場合は以下の手順を使用できます。
  • ゲストに virtio ネットワークデバイスを割り当てる 場合は、virsh attach-interface コマンドで model --virtio オプションを使用します。
    この代わりに、virt-manager インターフェースでゲストの 仮想ハードウェアの詳細 画面に移動し、ハードウェアを追加 をクリックすることもできます。新しい仮想ハードウェアを追加 画面で ネットワーク を選択し、デバイスのモデルvirtio に変更します。
  • 既存のインターフェースの種類を virtio に変更するには、virsh edit コマンドを使用して目的のゲストの XML 設定を編集し、model type 属性を virtio に変更します。例を以下に示します。
      <devices>
        <interface type='network'>
          <source network='default'/>
          <target dev='vnet1'/>
          <model type='virtio'/>
          <driver name='vhost' txmode='iothread' ioeventfd='on' event_idx='off'/>
        </interface>
      </devices>
      ...
    この代わりに、virt-manager インターフェースでゲストの 仮想ハードウェアの詳細 画面に移動し、NIC を選択した後、デバイスのモデルvirtio に変更します。

注記

再起動後にゲスト内のネットワークインターフェースの名前が一貫していない場合は、ゲストに提供されたすべてのインターフェースが同じデバイスモデル (virtio-net を推奨) であるようにしてください。詳細は Red Hat ナレッジベース を参照してください。

第6章 ネットワーク設定

本章では、libvirt ベースのゲスト仮想マシンによって使用される一般的なネットワーク設定を紹介します。
Red Hat Enterprise Linux 7 は以下の仮想化ネットワーク設定に対応しています。
  • Network Address Translation (NAT) を使用した仮想ネットワーク
  • PCI デバイス割り当てを使用して直接割り当てられた物理デバイス
  • PCIe SR-IOV を使用して直接割り当てられた仮想機能
  • ブリッジネットワーク
ゲスト仮想マシン上のネットワークサービスに外部ホストがアクセスできるようにするには、NAT またはネットワークブリッジングを有効にするか、または PCI デバイスを直接割り当てる必要があります。

6.1. libvirt を使用した Network Address Translation (NAT)

ネットワーク接続を共有する最も一般的な方法の 1 つは、Network Address Translation (NAT) 転送 (別名、仮想ネットワーク) の使用です。
ホストの設定

標準的な libvirt インストールはすべて、デフォルトの仮想ネットワークとして 仮想マシンへのNAT ベースの接続を提供します。これが virsh net-list --all コマンドで利用可能であること確認します。

# virsh net-list --all
Name                 State      Autostart
-----------------------------------------
default              active     yes
これが存在しない場合、以下をゲストの XML 設定ファイル (/etc/libvirtd/qemu/myguest.xml など) で使用できます。
# ll /etc/libvirt/qemu/
total 12
drwx------. 3 root root 4096 Nov  7 23:02 networks
-rw-------. 1 root root 2205 Nov 20 01:20 r6.4.xml
-rw-------. 1 root root 2208 Nov  8 03:19 r6.xml
デフォルトのネットワークは /etc/libvirt/qemu/networks/default.xml で定義されています。
デフォルトのネットワークが自動的に開始するようマークします。
# virsh net-autostart default
Network default marked as autostarted
デフォルトのネットワークを開始します。
# virsh net-start default
Network default started
libvirt デフォルトのネットワークが実行されると、分離されたブリッジデバイスが表示されます。このデバイスには、物理インターフェースが追加されて いません 。新規デバイスは、NAT および IP 転送を使用して物理ネットワークに接続します。新規インターフェースを追加しないでください。
# brctl show
bridge name     bridge id               STP enabled     interfaces
virbr0          8000.000000000000       yes
libvirtiptables ルールを追加します。このルールは、virbr0INPUTFORWARDOUTPUT チェーンで POSTROUTING デバイスに割り当てられたゲスト仮想マシンから/へのトラフィックを可能にするものです。次に libvirt は、ip_forward パラメーターの有効化を試みます。別のアプリケーションが ip_forward を無効にする場合もあるので、/etc/sysctl.conf に以下を追加することが最善の選択肢です。
 net.ipv4.ip_forward = 1
ゲスト仮想マシンの設定

ホスト設定が完了したら、ゲスト仮想マシンはその名前をベースにした仮想ネットワークに接続できます。ゲストを「デフォルト」の仮想ネットワークに接続するには、ゲストの XML 設定ファイル (/etc/libvirtd/qemu/myguest.xml など) で以下を使用します。

<interface type='network'>
   <source network='default'/>
</interface>

注記

MAC アドレスの定義はオプションです。定義されない場合、MAC アドレスは自動生成され、ネットワークが使用するブリッジデバイスの MAC アドレスとして使用されます。MAC アドレスの手動設定は、環境内での一貫性や参照の容易さを保ち、競合の極めて低い可能性を回避するのに役立つことがあります。
<interface type='network'>
  <source network='default'/>
  <mac address='00:16:3e:1a:b3:4a'/>
</interface>

6.2. vhost-net の無効化

vhost-net モジュールは virtio ネットワーキング用のカーネルレベルのバックエンドで、virtio パケット処理タスクをユーザー領域 (QEMU プロセス) からカーネル (vhost-net ドライバー) に移すことで仮想化のオーバーヘッドを低減します。vhost-net は、virtio ネットワークインターフェースでのみ利用可能です。vhost-net カーネルモジュールがロードされている場合、デフォルトですべての virtio インターフェース用に有効化されています。ただし、vhost-net の使用時に特定のワークロードのパフォーマンスが低下した場合は、インターフェース設定で無効にできます。
具体的には、UDP トラフィックがホストマシンからホスト上のゲスト仮想マシンに送信された場合、ゲスト仮想マシンのデータ処理速度がホストマシンの送信速度より遅いと、パフォーマンスが低下する可能性があります。この状況で vhost-net を有効にすると、UDP ソケットの受信バッファーをより早くオーバーフローさせることになり、多大なパケットロスにつながります。このため、この状況ではトラフィックを遅らせ、全体のパフォーマンスを上げるために、vhost-net を無効にすることが適切です。
vhost-net を無効にするには、ゲスト仮想マシンの XML 設定ファイルにある <interface> サブ要素を編集し、ネットワークを以下のように定義します。
<interface type="network">
   ...
   <model type="virtio"/>
   <driver name="qemu"/>
   ...
</interface>
ドライバー名を qemu に設定するとパケット処理が QEMU ユーザー領域で強制されるため、そのインターフェースでは vhost-net が事実上無効になります。

6.3. vhost-net zero-copy の有効化

Red Hat Enterprise Linux 7 では、vhost-net zero-copy はデフォルトで無効にされています。このアクションを永続的に有効にするには、以下の内容を含む新規ファイル vhost-net.conf/etc/modprobe.d に追加します。
options vhost_net  experimental_zcopytx=1
これを再び無効にする場合は、以下を実行します。
modprobe -r vhost_net
modprobe vhost_net experimental_zcopytx=0
最初のコマンドは古いファイルを削除し、2 つ目のファイルは新規ファイル (上記のようなファイル) を作成し、ゼロコピーを無効にします。このコマンドを使って有効にすることもできますが、その場合変更は永続化されません。
有効になったことを確認するには、cat /sys/module/vhost_net/parameters/experimental_zcopytx の出力を確認します。以下のように表示されるはずです。
$ cat /sys/module/vhost_net/parameters/experimental_zcopytx
0

6.4. ブリッジネットワーク

ブリッジネットワーク (ネットワークブリッジングまたは仮想ネットワークスイッチとも呼ばれます) は、仮想マシンのネットワークインターフェースを物理インターフェースと同じネットワーク上に置くために使用されます。ブリッジには最小の設定が必要であり、仮想マシンを既存のネットワーク上に表示させるため、管理オーバーヘッドとネットワークの複雑性が軽減されます。ブリッジにはコンポーネントや設定変数がほとんど含まれていないため、それらは理解しやすく、必要な場合はトラブルシューティングを実行しやすい透過的なセットアップを提供します。
ブリッジは virt-manager または libvirt などの標準的な Red Hat Enterprise Linux ツールを使用して仮想化環境で設定できます。以下のセクションでこれについて説明します。
ただし、仮想化環境の場合でも、ホストオペレーティングシステムのネットワークツールを使用した方がブリッジをより簡単に作成できる場合があります。このブリッジの作成方法についての詳細は、『Red Hat Enterprise Linux 7 ネットワークガイド」を参照してください。

6.4.1. Red Hat Enterprise Linux 7 ホストでのブリッジネットワークの設定

ブリッジネットワークは、仮想化管理ツールを使わずに Red Hat Enterprise Linux ホスト上の仮想マシンに設定できます。このような設定は主に、仮想化ブリッジがホストの唯一のネットワークインターフェースであるか、またはホストの管理ネットワークインターフェースである場合に推奨されます。
仮想化ツールを使わずにネットワークブリッジングを設定する手順については、『Red Hat Enterprise Linux 7 ネットワークガイド』を参照してください。

6.4.2. 仮想マシンマネージャーを使用したブリッジネットワーク

このセクションでは、virt-manager を使用してホストマシンのインターフェースからゲスト仮想マシンへのブリッジを作成する方法を説明します。

注記

ご使用の環境によっては、Red Hat Enterprise Linux 7 で libvirt ツールを使用してブリッジをセットアップするためにネットワークマネージャーを無効にする必要がある場合がありますが、これは Red Hat では推奨していません。また、libvirt で作成したブリッジでは、ブリッジがネットワークの接続を維持できるよう libvirtd が実行中である必要があります。
Red Hat Enterprise Linux 7 ネットワークガイド』で説明されているようにブリッジネットワークを Red Hat Enterprise Linux の物理ホストに設定することが推奨されます。ブリッジ作成後に libvirt を使用して仮想マシンインターフェースをブリッジに追加します。

手順6.1 virt-manager を使用したブリッジの作成

  1. virt-manager メインメニューから、編集 ⇒ 接続の詳細 をクリックして 接続の詳細 ウィンドウを開きます。
  2. ネットワークインターフェース タブをクリックします。
  3. ウィンドウの下部にある + をクリックして、新規ネットワークインターフェースを設定します。
  4. インターフェースの種類 ドロップダウンメニューで、Bridge を選択してから 進む をクリックして継続します。
    ブリッジの追加

    図6.1 ブリッジの追加

    1. 名前 フィールドに、br0 などのブリッジの名前を入力します。
    2. ドロップダウンメニューから 開始モード を選択します。以下のいずれかから選択します。
      • none - ブリッジを非アクティブ化します。
      • onboot - 次回のゲスト仮想マシンの再起動時にブリッジをアクティブ化します。
      • hotplug - ゲスト仮想マシンが実行中の場合でもブリッジをアクティブ化します。
    3. 今すぐ有効に チェックボックスにチェックを入れ、ブリッジをただちにアクティブにします。
    4. IP の設定 または ブリッジの設定 のいずれかを設定するには、該当する 設定 ボタンをクリックします。別のウィンドウが開き、ここで必要な設定を指定することができます。必要な変更を加えてから OK をクリックします。
    5. 仮想マシンに接続する物理インターフェースを選択します。インターフェースが別のゲスト仮想マシンで使用されている場合には、警告メッセージが送信されます。
  5. 完了 をクリックするとウィザードが閉じます。これにより、Connections (接続) メニューに戻ります。
    ブリッジの追加

    図6.2 ブリッジの追加

使用するブリッジを選択して Apply をクリックし、ウィザードを終了します。
インターフェースを停止するには、インターフェースの停止 キーをクリックします。ブリッジが停止した後にインターフェースを削除するには、インターフェースの削除 キーをクリックします。

6.4.3. libvirt を使用したブリッジネットワーク

ご使用の環境によっては、Red Hat Enterprise Linux 7 で libvirt ツールを使用してブリッジをセットアップするためにネットワークマネージャーを無効にする必要がある場合がありますが、これは Red Hat では推奨していません。また、ブリッジが作動するには libvirtd が実行中である必要があります。
Red Hat Enterprise Linux 7 ネットワークガイド』で説明されているようにブリッジネットワークを Red Hat Enterprise Linux の物理ホストに設定することが推奨されます。

重要

libvirt は新規のカーネル調整可能パラメーターを使用してホストブリッジのフォワーディングデータベース (FDB) エントリーを管理できるため、複数仮想マシンでのブリッジの実行時にシステムのネットワークのパフォーマンスが強化されます。ホストの XML 設定ファイルでネットワークの macTableManager 要素の <bridge> 属性を 'libvirt' に設定します。
<bridge name='br0' macTableManager='libvirt'/>
これにより、すべてのブリッジポートで学習 (フラッド) モードがオフになり、libvirt は必要に応じて FDB に対するエントリーの追加または削除を行います。MAC アドレスの適切な転送ポートについての学習に関するオーバーヘッドを削減すると共に、カーネルがネットワークへのブリッジ接続をしている物理デバイスでプロミスキャスモードを無効にできるため、さらにオーバーヘッドが削減されます。

第7章 KVM でのオーバーコミット

7.1. はじめに

KVM ハイパーバイザーにより、CPU およびメモリーが自動的にオーバーコミットされます。つまり、システム上の物理リソース以上に、仮想化 CPU およびメモリーを仮想マシンに割り当てることができます。このことが可能になる理由は、ほとんどのプロセスで割り当てられたリソースを常に 100% 必要としている訳ではないからです。
その結果、使用率の低い仮想化サーバーやデスクトップをより少数のホストで実行することができるため、リソースとしてのシステム数を節約でき、節電効果や冷却効果、およびサーバーのハードウェアに対する投資効果などの実質的な効果を得ることができます。

7.2. メモリーのオーバーコミット

KVM ハイパーバイザーで実行しているゲスト仮想マシン群には、そのマシン群専用に割り当てられた物理的な RAM ブロックはありません。代わりに、各ゲスト仮想マシンはホスト物理マシンの Linux プロセスとして動作します。つまり、メモリーが要求された場合にのみホスト物理マシンの Linux カーネルによってメモリーが割り当てられます。また、ホストのメモリー管理機能により、物理的なメモリーと swap 領域間でゲスト仮想マシンのメモリーを移動させることができます。
オーバーコミットを採用する際は、ホスト物理マシンのプロセス処理用に十分なメモリーを確保するだけでなく、すべてのゲスト仮想マシンに対応できるようにホスト物理マシン上に十分な swap 領域を配分する必要があります。原則として、ホスト物理マシンのオペレーティングシステムには最大 4GB のメモリーと最小 4GB の swap 領域が必要となります。適切な swap パーティションサイズ把握に関する詳細な説明は、Red Hat ナレッジベース を参照してください。

重要

オーバーコミットが、全般的なメモリー関連の問題に対する理想的なソリューションとなるわけではありません。メモリー不足に対処するため推奨される方法は、ゲストにより少ないメモリーを割り当てるか、ホストにより多くの物理メモリーを追加するか、または swap 領域を使用することです。
スワップが頻繁に行われると、仮想マシンの動作が遅くなる場合があります。また、オーバーコミットによりシステムがメモリーを使い果たし (OOM)、Linux カーネルが重要なプロセスをシャットダウンする可能性があります。メモリーのオーバーコミットを実行する場合は、テストを十分に実施するようにしてください。オーバーコミットに関して支援が必要な場合は Red Hat サポートにお問い合わせください。
オーバーコミットはすべての仮想マシンで機能する訳ではありませんが、集中的なメモリー使用が最小限となるデスクトップ仮想化のセットアップや、複数の同一設定のゲスト仮想マシンを KSM で実行する場合などに有効であることが確認されています。KSM およびオーバーコミットの詳細については、『Red Hat Enterprise Linux 7 仮想化のチューニングと最適化ガイド』を参照してください。

重要

デバイス割り当て が使用されている場合、割り当てデバイスで直接メモリーアクセス (DMA) を有効にするには、すべての仮想マシンメモリーの静的な事前割り当てを行う必要があります。このため、メモリーのオーバーコミットはデバイス割り当てと一緒にはサポートされません。

7.3. 仮想化 CPU のオーバーコミット

KVM ハイパーバイザーは、仮想化 CPU (vCPU) のオーバーコミットに対応しています。仮想化 CPU は、ゲスト仮想マシンで許可される負荷の限界までオーバーコミットすることができます。vCPU をオーバーコミットする際は、負荷が 100% に近づくと要求がドロップされたり、長すぎる応答時間が発生する恐れがあるため十分に注意してください。
Red Hat Enterprise Linux 7 では、複数の仮想 CPU を持つゲスト (対称型マルチプロセッシング (SMP) のゲスト仮想マシンとも呼ばれる) をオーバーコミットできます。ただし、実際の物理 CPU にある数よりも多くのコアを仮想マシンで実行すると、パフォーマンスが大幅に低下する可能性があります。
たとえば、仮想 CPU 数が 4 つの仮想マシンは、デュアルコアではなくクアッドコアプロセッサーのホストマシンで実行すべきです。実際の物理プロセッシングコア数を超えた SMP 仮想マシンをオーバーコミットすると、プログラムに割り当てられる CPU 時間が必要な時間に満たなくなるためにパフォーマンスが大幅に低下する原因となります。また、物理プロセッサーコア 1 つあたり合計 10 個を超える仮想 CPU を割り当てることは推奨されません。
SMP ゲストでは、一部の固有の処理オーバーヘッドが引き継がれます。タイムスライスを使用してリソースをゲストに割り当てるとゲスト内の CPU 間の通信速度が低下する可能性があるため、CPU のオーバーコミットにより SMP オーバーヘッドが増える可能性があります。このオーバーヘッドは、多数の仮想 CPU を持つか、またはオーバーコミットの割合の高いゲストの場合に増加します。
仮想化 CPU のオーバーコミットを行う最適な状態は、単一のホストに複数のゲストがあり、各ゲストにホスト CPU 数と比較した場合の少数の仮想 CPU (vCPU) がある場合です。KVM が安全にサポートするのは単一ホストにおいて、負荷が 100% 未満のゲストで、(5 台の仮想マシン上の) 5 つの仮想 CPU に対して1 つの物理 CPU という割合の場合です。KVM はすべての仮想マシン間で切り替えを実行し、負荷のバランスを取ります。
最適なパフォーマンスを得るために、各ゲスト内のプログラムを実行するのに必要な数の仮想 CPU のみをゲストに割り当てることを推奨します。

重要

オーバーコミットしている環境では、メモリーやプロセッシングリソースを 100% 使用するアプリケーションは不安定になる可能性があります。実稼働環境でメモリーまたは CPU をオーバーコミットする際は、十分なテストを行ってから実行してください。CPU のオーバーコミットの割合と SMP の量はワークロードによって異なるためです。

第8章 KVM ゲストのタイミング管理

仮想化には、ゲスト仮想マシンの時刻管理におけるさまざまな課題が伴います。
  • 仮想マシン内の割り込みは実際の割り込みではなく、ホストマシンがゲスト仮想マシンに挿入しているものです。このため、割り込みは常に同時かつ即時にすべてのゲスト仮想マシンに配信される訳ではありません。
  • ホストは別のゲスト仮想マシンを実行していたり、別のプロセスを実行している場合もあり、したがって割り込みに通常必要となる正確なタイミングを得ることが常に可能であるとは限りません。
セッションの妥当性や移行その他のネットワークアクティビティーの正確性を維持するにはタイムスタンプに依存する必要があるため、正確な時刻管理機能を実行していないゲスト仮想マシンには、ネットワークアプリケーションおよびプロセスに関連した問題が発生する可能性があります。
KVM では、ゲスト仮想マシンに準仮想化クロック (kvm-clock) を提供することでこの問題を回避します。しかし、タイミングをテストしてから、時刻管理が不正確な場合に影響を受ける可能性のあるアクティビティー (ゲストマイグレーション等) を実行することが依然として重要です。

重要

上記の問題を回避するには、ネットワークタイムプロトコル (NTP) をホスおよびとゲスト仮想マシン上で設定する必要があります。Red Hat Enterprise Linux 6 以下を使用するゲストの場合、NTP は ntpd サービスによって実装されます。詳細は、『Red Hat Enterprise 6 Deployment Guide』を参照してください。
Red Hat Enterprise Linux 7 を使用したシステムでは、NTP 時刻同期サービスは ntpd または chronyd サービスで提供することができます。仮想マシン上で Chrony を使用する利点はいくつかあります。詳細については、Red Hat Enterprise Linux 7『システム管理者のガイド』の 「chrony スイートを使用した設定」および「ntpd を使用した NTP 設定」を参照してください
ゲスト仮想マシンの同期のしくみ

デフォルトで、ゲストは以下のようにハイパーバイザーと時間を同期します。

  • ゲストシステムが起動すると、ゲストはエミュレートされた RTC (リアルタイムクロック) から時間を読み取ります。
  • NTP プロトコルが開始されていると、ゲストのクロックは自動的に同期されます。それ以降、ゲストが通常の動作をしている間、NTP はゲストのクロック調整を実施します。
  • ゲストが一時停止または復元プロセスの後に再起動する場合は、管理ソフトウェア (virt-manager など) によって、ゲストのクロックを特定の値に同期させるコマンドが実行される必要があります。この同期プロセスは、QEMU ゲストエージェント がゲストにインストールされ、その機能をサポートしている場合に限り動作します。通常は、ゲストのクロックをホストのクロック値に同期します。

一定のタイムスタンプカウンター (TSC: Time Stamp Counter)

最新の Intel と AMD の CPU は、不変タイムスタンプカウンター (TSC) を提供します。不変 TSC のカウント頻度は、たとえば CPU コア自体が節電ポリシーに従うために周波数を変更しても変わりません。不変 TSC の周波数を持つ CPU は、KVM ゲストのクロックソースとして TSC を使用するために必要です。

constant_tsc フラグが付いている場合、CPU に Constant TSC があります。CPU に constant_tsc フラグが付いているかどうかを確認するには、以下のコマンドを実行します。
$ cat /proc/cpuinfo | grep constant_tsc
いずれかの出力が表示される場合は、CPU には constant_tsc ビットがあることになります。出力がない場合は、以下の説明にしたがいます。
Constant TSC を搭載していないホストの設定

Constant TSC の周波数のないシステムは、仮想マシンのクロックソースに TSC を使用できず、追加設定が必要になります。電源管理機能により正確な時刻管理が妨げられるので、KVM を使用してゲスト仮想マシンの正確な時間を管理するには、この機能を無効にする必要があります。

重要

以下に説明する手順は、AMD リビジョン F の CPU のみが対象となります。
CPU に constant_tsc ビットがない場合は、電源管理機能をすべて無効にします。各システムには、時刻管理に使用する複数のタイマーがあります。TSC はホスト上では安定していません。これは、cpufreq の変化やディープ C ステート、より高速の TSC を搭載したホストへの移行などが原因となる場合があります。ディープ C スリープ状態に入ると、TSC が停止する可能性があります。カーネルがディープ C ステートを使用しないようにするには、カーネルブートに processor.max_cstate=1 を追加します。この変更を永続化させるには、/etc/default/grub ファイルの GRUB_CMDLINE_LINUX キーの値を編集します。たとえば、毎回の起動時に緊急モード (emergency mode) を有効にするには、以下のようにエントリーを編集します。
GRUB_CMDLINE_LINUX="emergency"
GRUB 2 ブートメニューに複数のパラメーターを追加する際と同様に、GRUB_CMDLINE_LINUX キーには複数のパラメーターを指定できることに注意してください。
cpufreq を無効にするには (constant_tsc なしのホスト上の場合のみ必要)、kernel-toolsをインストールし、cpupower.service (systemctl enable cpupower.service) を有効にします。ゲスト仮想マシンが起動されるたびにこのサービスを無効にするには、/etc/sysconfig/cpupower の設定ファイルを変更し、CPUPOWER_START_OPTS および CPUPOWER_STOP_OPTS を変更します。有効な制限については、/sys/devices/system/cpu/cpuid/cpufreq/scaling_available_governors ファイルを参照してください。このパッケージまたは電源管理およびガバナーについての詳細は、『Red Hat Enterprise Linux 7 電力管理ガイド』を参照してください。

8.1. ホスト全体の時刻同期

KVM ゲストの仮想ネットワークデバイスはハードウェアタイムスタンプをサポートしていません。そのため、NTP や PTP などのネットワークプロトコルを使用するゲストのクロックを数十マイクロ秒よりも正確に同期することが難しくなります。
ゲストにより正確な同期が必要な場合は、NTP や PTP を使用するホストのクロックをハードウェアタイムスタンプで同期し、直接ゲストをホストに同期することが推奨されます。Red Hat Enterprise Linux 7.5 以上には、1 ミリ秒未満の精度でゲストをホストに同期できる仮想 PTP ハードウェアクロック (PHC) が提供されます。
PHCデバイスを有効にするには、次の手順を実行します。
  1. 再起動後にロードする ptp_kvm モジュールを設定します。
    # echo ptp_kvm > /etc/modules-load.d/ptp_kvm.conf
  2. chrony 設定への参照として /dev/ptp0 クロックを追加します。
    # echo "refclock PHC /dev/ptp0 poll 2" >> /etc/chrony.conf
  3. chrony デーモンを再起動します。
    # systemctl restart chronyd
  4. ホストとゲスト時間の同期が適切に設定されたことを確認するには、ゲスト上で chronyc sources コマンドを使用します。以下のような出力が表示されます。
    # chronyc sources
    210 Number of sources = 1
    MS Name/IP address         Stratum Poll Reach LastRx Last sample
    ===============================================================================
    #* PHC0                          0   2   377     4     -6ns[   -6ns] +/-  726ns

8.2. Red Hat Enterprise Linux ゲストで必要な時刻管理パラメーター

一部の Red Hat Enterprise Linux ゲスト仮想マシンでは、システムの時刻を正しく同期させるために追加のカーネルパラメーターが必要です。これらのパラメーターをゲスト仮想マシンにある /etc/grub2.cfg ファイルの /kernel 行の末尾に追加して設定します。

注記

Red Hat Enterprise Linux 5.5 以降、Red Hat Enterprise Linux 6.0 以降、および Red Hat Enterprise Linux 7 は、デフォルトのクロックソースに kvm-clock を使用します。kvm-clock を実行すると追加のカーネルパラメーターが必要なくなるので、Red Hat ではこれを推奨しています。
以下の表は、Red Hat Enterprise Linux のバージョンと各システムで必要となるパラメーターを表示しています。

表8.1 カーネルパラメーターの要件

Red Hat Enterprise Linux バージョンゲストの追加カーネルパラメーター
AMD64 および Intel 64 システム上の 7.0 およびそれ以降 (kvm-clock を実行)追加のパラメーターは必要ありません
AMD64 および Intel 64 システム上の 6.1 およびそれ以降 (kvm-clock を実行)追加のパラメーターは必要ありません
AMD64 および Intel 64 システム上の 6.0 (kvm-clock を実行)追加のパラメーターは必要ありません
AMD64 および Intel 64 システム上の 6.0 (kvm-clock を実行せず)notsc lpj=n

注記

lpj パラメーターは、ゲスト仮想マシンが稼働する特定の CPU の loops per jiffy 値と同じ値を必要とします。この値が不明な場合は、lpj パラメーターを設定しないでください。

8.3. スチールタイムアカウンティング

steal 時間とは、ゲスト仮想マシンが必要とする CPU 時間のうち、ホストが提供しない時間のことです。steal 時間は、ホストがこれらのリソースを別のゲストなどに割り当てると発生します。
steal 時間は、/proc/stat の CPU 時間フィールドに報告されます。これは、topvmstat などのユーティリティーによって自動的に報告されます。これは「%st」として表示されるか、または「st」列に表示されます。steal 時間はオフにできないことに注意してください。
steal 時間が多いと CPU の競合の原因となり、ゲストのパフォーマンスが低下する可能性があります。CPU の競合を解消するには、ゲストの CPU 優先度または CPU 割り当てのレベルを上げるか、ホスト上で実行するゲストの数を減らします。

第9章 libvirt を使用したネットワークブート

ゲスト仮想マシンは、PXE を有効にして起動できます。PXE により、ゲスト仮想マシンの起動が可能になり、ネットワーク自体から設定をロードできるようになります。このセクションでは、libvirt を使って PXE ゲストを設定する基本的なステップを説明します。
このセクションでは、ブートイメージの作成や PXE サーバーは説明されません。ここでは、プライベートまたはブリッジネットワークで libvirt を設定し、PXE ブートを有効にしてゲスト仮想マシンを起動する方法を説明します。

警告

ここでの手順は、例としてのみ示されています。次に進む前に、十分なバックアップがなされていることを確認してください。

9.1. ブートサーバーの準備

本章のステップを実行するには、以下が必要となります。
  • PXE サーバー (DHCP および TFTP) - これは libvirt 内部サーバー、手動設定のDHCP および TFTP、dnsmasq、Cobbler 設定のサーバー、他のサーバーのいずれでも可能です。
  • ブートイメージ - 手動設定または Cobbler 設定の PXELINUX

9.1.1. プライベート libvirt ネットワーク上での PXE ブートサーバーの設定

以下の例では デフォルト ネットワークを使用します。以下のステップを実行してください。

手順9.1 PXE ブートサーバーの設定

  1. PXE ブートイメージおよび設定内容を /var/lib/tftpboot に配置します。
  2. 以下のコマンドを入力します。
    # virsh net-destroy default
    # virsh net-edit default
  3. <ip>デフォルト ネットワークの設定ファイルで 要素を編集し、適切なアドレス、ネットワークマスク、DHCP アドレス範囲および起動ファイルを組み込みます。ここで、BOOT_FILENAME はゲスト仮想マシンの起動に使用するファイル名を表します。
    <ip address='192.168.122.1' netmask='255.255.255.0'>
       <tftp root='/var/lib/tftpboot' />
       <dhcp>
          <range start='192.168.122.2' end='192.168.122.254' />
          <bootp file='BOOT_FILENAME' />
       </dhcp>
    </ip>
  4. 以下を実行します。
    # virsh net-start default
  5. PXE を使用してゲストを起動します (「PXE を使用したゲストの起動」 を参照)。

9.2. PXE を使用したゲストの起動

このセクションでは、PXE を使用してゲスト仮想マシンを起動する方法を説明します。

9.2.1. ブリッジネットワークの使用

手順9.2 PXE およびブリッジネットワークを使用したゲストの起動

  1. ブリッジが有効にされており、PXE ブートサーバーがネットワーク上で利用可能なことを確認します。
  2. PXE ブートが有効な状態でゲスト仮想マシンを起動します。以下のコマンド例のように、virt-install コマンドを使用して PXE ブートが有効にされている新規の仮想マシンを作成することができます。
    virt-install --pxe --network bridge=breth0 --prompt
    または、ゲストネットワークがブリッジネットワークを使用するように設定されており、以下の例のように XML ゲスト設定ファイルの <boot dev='network'/> 要素内に <os> 要素があることを確認します。
    <os>
       <type arch='x86_64' machine='pc-i440fx-rhel7.0.0'>hvm</type>
       <boot dev='network'/>
       <boot dev='hd'/>
    </os>
    <interface type='bridge'>
       <mac address='52:54:00:5a:ad:cb'/>
       <source bridge='breth0'/>
       <target dev='vnet0'/>
       <alias name='net0'/>
       <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
    </interface>

9.2.2. プライベート libvirt ネットワークの使用

手順9.3 プライベート libvirt ネットワークの使用

  1. 「プライベート libvirt ネットワーク上での PXE ブートサーバーの設定」 で説明されているように libvirt 上で PXE ブートを設定します。
  2. PXE ブートが有効な状態で libvirt を使用してゲスト仮想マシンを起動します。以下のように virt-install コマンドを実行し、PXE を使用して新規の仮想マシンを作成し、インストールすることができます。
    virt-install --pxe --network network=default --prompt
または、ゲストネットワークがプライベートネットワークを使用するように設定されており、以下の例のように XML ゲスト設定ファイルの <boot dev='network'/> 要素内に <os> 要素があることを確認します。
<os>
   <type arch='x86_64' machine='pc-i440fx-rhel7.0.0'>hvm</type>
   <boot dev='network'/>
   <boot dev='hd'/>
</os>
また、ゲスト仮想マシンがプライベートネットワークに接続されていることを確認します。
<interface type='network'>
   <mac address='52:54:00:66:79:14'/>
   <source network='default'/>
   <target dev='vnet0'/>
   <alias name='net0'/>
   <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
</interface>

第10章 ハイパーバイザーおよび仮想マシンの登録

Red Hat Enterprise Linux 6 および 7 では、すべてのゲストに同じレベルのサブスクリプションサービスが割り当てられるようにすべてのゲスト仮想マシンが特定のハイパーバイザーにマップされる必要があります。これを実行するには、インストールおよび登録済みの各 KVM ハイパーバイザー上のすべてのゲスト仮想マシン (VM) を自動検出するサブスクリプションエージェントをインストールする必要があります。これにより、ホスト上に置かれるマッピングファイルが作成されます。このマッピングファイルにより、すべてのゲスト仮想マシンに以下の利点が提供されます。
  • 仮想システムに固有のサブスクリプションはすぐに利用可能となり、関連付けられた仮想マシンすべてに適用できます。
  • ハイパーバイザーから継承できるサブスクリプションの利点すべてはすぐに利用可能となり、関連付けられた仮想マシンすべてに適用できます。

注記

本章で提供される情報は Red Hat Enterprise Linux サブスクリプションのみに該当します。Red Hat Virtualization サブスクリプションまたは Red Hat Satellite サブスクリプションをお持ちの場合には、それらのサブスクリプションで提供されている virt-who の情報も参照してください。Red Hat Subscription Management についての詳細は、カスタマーポータルから入手できる Red Hat Subscription Management に関するガイドも参照してください。

10.1. ホスト物理マシンへの virt-who のインストール

  1. KVM ハイパーバイザーを登録します。

    KVM ハイパーバイザーは、ホスト物理マシンのターミナルで root ユーザーとして subscription-manager register [options] コマンドを実行して登録します。# subscription-manager register --help メニューを使用するとさらに多くのオプションを利用できます。ユーザー名とパスワードを使用する場合には、サブスクリションマネージャーが認識する認証情報を使用します。サブスクリプションの初回使用時でユーザーアカウントがない場合には、カスタマーサポートにお問い合わせください。たとえば、「admin」としてパスワード「secret」を使用して仮想マシンを登録する場合は以下のコマンドを入力します。
    [root@rhel-server ~]# subscription-manager register --username=admin --password=secret --auto-attach --type=hypervisor
  2. virt-who パッケージをインストールします。

    ホスト物理マシンで以下のコマンドを実行することで virt-who パッケージをインストールします。
    # yum install virt-who
  3. virt-who 設定ファイルを作成します。

    各ハイパーバイザーの /etc/virt-who.d/ ディレクトリーに設定ファイルを追加します。最低でも、ファイルには次のスニペットが含まれている必要があります。
    [libvirt]
    type=libvirt
    virt-who の設定に関する詳細は、virt-who の設定」 を参照してください。
  4. virt-who サービスを起動します。

    ホスト物理マシンで以下のコマンドを実行することで virt-who サービスを起動します。
    # systemctl start virt-who.service
    # systemctl enable virt-who.service
  5. virt-who サービスがゲスト情報を受信していることを確認します。

    この時点で、virt-who サービスはホストからドメインの一覧の取得を開始します。ホスト物理マシンで /var/log/rhsm/rhsm.log ファイルをチェックし、ファイルにゲスト仮想マシンの一覧が含まれることを確認します。例を以下に示します。
    2015-05-28 12:33:31,424 DEBUG: Libvirt domains found: [{'guestId': '58d59128-cfbb-4f2c-93de-230307db2ce0', 'attributes': {'active': 0, 'virtWhoType': 'libvirt', 'hypervisorType': 'QEMU'}, 'state': 5}]

手順10.1 カスタマーポータルでのサブスクリプション管理

  1. ハイパーバイザーのサブスクライブ

    仮想マシンはハイパーバイザーと同じサブスクリプションの利点を受けることができるため、ハイパーバイザーに有効なサブスクリプションがあることを確認し、そのサブスクリプションを仮想マシンが使用できることを確認するのは重要です。
    1. カスタマーポータルにログインします。

      https://access.redhat.com/ の Red Hat カスタマーポータルにログインし、ページの上部にある サブスクリプション ボタンをクリックします。
    2. 「システム」のリンクをクリックします。

      サブスクリプション管理の システム リンクをクリックします。
    3. ハイパーバイザーを選択します。

      「システム」ページには、サブスクライブ済みシステムの一覧が表示されます。ハイパーバイザーの名前 (例: localhost.localdomain) をクリックします。サブスクリプションのアタッチ をクリックし、一覧表示されたサブスクリプションをすべて選択します。選択項目のアタッチ をクリックします。これにより、ホストの物理サブスクリプションがハイパーバイザーに割り当てられ、ゲストがサブスクリプションを利用できるようになります。
  2. ゲスト仮想マシンのサブスクライブ: 初回時の使用

    このステップは、新規サブスクリプションを持つが、一度もゲスト仮想マシンをサブスクライブしたことのない場合に適用できます。仮想マシンを追加する場合にはこのステップを省略してください。virt-who サービスを実行するマシン上でハイパーバイザープロファイルに割り当てられたサブスクリプションを消費するには、ゲスト仮想マシンのターミナルで root で以下のコマンドを実行して自動サブスクライブを実行します。
    [root@virt-who ~]# subscription-manager attach --auto
  3. 追加ゲスト仮想マシンのサブスクライブ

    サブスクライブを初めて実行した場合にはこのステップを省略してください。仮想マシンを追加する場合は、このコマンドを実行しても、必ずしも同じサブスクリプションがゲスト仮想マシンに再アタッチされる訳ではないことに注意してください。これは、特定のゲスト仮想マシンに必要な分を解決するためにすべてのサブスクリプションを削除してから自動アタッチを許可することで、以前と異なるサブスクリプションが消費される可能性があるためです。お使いのシステムには影響しない場合もありますが、この点には留意する必要があります。以下に説明していませんが、アタッチの手動の手順に従って仮想マシンをアタッチする場合、自動アタッチが機能しないため、それらの仮想マシンを手動で再アタッチする必要があります。以下のコマンドを使用して、古いゲストのサブスクリプションを削除してから自動アタッチを使用してサブスクリプションをすべてのゲストにアタッチします。ゲスト仮想マシンで以下のコマンドを実行します。
    [root@virt-who ~]# subscription-manager remove --all
    [root@virt-who ~]# subscription-manager attach --auto
  4. サブスクリプションがアタッチされていることを確認します。

    ゲスト仮想マシンで以下のコマンドを実行して、サブスクリプションがハイパーバイザーに割り当てられていることを確認します。
    [root@virt-who ~]# subscription-manager list --consumed
    以下のような出力が表示されます。サブスクリプションの詳細に注意してください。「Subscription is current」と記載されているはずです。
    [root@virt-who ~]#  subscription-manager list --consumed
    +-------------------------------------------+
       Consumed Subscriptions
    +-------------------------------------------+
    Subscription Name:	Awesome OS with unlimited virtual guests
    Provides: 		Awesome OS Server Bits
    SKU: 			awesomeos-virt-unlimited
    Contract: 		0
    Account: 		######### Your account number #####
    Serial: 		######### Your serial number ######
    Pool ID: 		XYZ123                                             1
    Provides Management: 	No
    Active: 		True
    Quantity Used: 		1
    Service Level:
    Service Type:
    Status Details:		Subscription is current                       2
    Subscription Type:
    Starts: 		01/01/2015
    Ends: 			12/31/2015
    System Type: 		Virtual

    1

    システムにアタッチするサブスクリプションの ID がここに表示されます。ID は手動でサブスクリプションをアタッチする場合に必要になります。

    2

    サブスクリプションが最新であるかどうかを示します。サブスクリプションが最新でない場合、エラーメッセージが表示されます。この例の 1 つが、ゲストがどのホストでも報告されず、一時的なマップされていないゲストのサブスクリプションを使用している場合です。この場合、ゲストをサブスクライブする必要があります。その他の場合は 「サブスクリプションステータスでエラーが出ました。どうすればよいですか?」 に記載されている情報を参照してください。
  5. 追加ゲストの登録

    ハイパーバイザーに新規のゲスト仮想マシンをインストールする場合、ゲスト仮想マシンで以下のコマンドを実行して新規の仮想マシンを登録し、ハイパーバイザーにアタッチされているサブスクリプションを使用する必要があります。
    # subscription-manager register
    # subscription-manager attach --auto
    # subscription-manager list --consumed

10.1.1. virt-who の設定

virt-who サービスは、以下のファイルを使用して設定されます。
  • /etc/virt-who.conf - 接続されているハイパーバイザーの変更を確認する間隔など、一般的な設定情報が含まれています。
  • /etc/virt-who.d/hypervisor_name.conf - 特定のハイパーバイザーの設定情報が含まれています。
Web ベースのウィザードは、ハイパーバイザーの設定ファイルと、virt-who.conf に必要なスニペットを生成するために提供されます。カスタマーポータルの Red Hat Virtualization Agent (virt-who) Configuration Helper でウィザードを実行できます。
ウィザードの 2 ページ目で、次のオプションを選択します。
  • Where does your virt-who report to?: Subscription Asset Manager
  • Hypervisor Type: libvirt
ウィザードにしたがって設定を完了します。設定が正しく行われた場合、virt-who は指定のハイパーバイザーで既存および将来的なゲストに選択されたサブスクリプションを自動的に提供します。
ハイパーバイザーの設定ファイルの詳細は、virt-who-config man ページを参照してください。

10.2. 新規ゲスト仮想マシンの登録

新規ゲスト仮想マシンがすでに登録済みで実行中のホストで作成される場合には、virt-who サービスも実行中である必要があります。これにより、virt-who サービスがゲストをハイパーバイザーにマップできるため、システムは仮想システムとして適切に登録されます。仮想マシンを登録するには、以下のコマンドを実行します。
[root@virt-server ~]# subscription-manager register --username=admin --password=secret --auto-attach

10.3. ゲスト仮想マシンのエントリーの削除

ゲスト仮想マシンが実行中の場合、ゲストのターミナルで root として以下のコマンドを実行し、システムの登録を解除します。
[root@virt-guest ~]# subscription-manager unregister
システムが削除されている場合は、仮想サービスはサービスが削除されたのか、または一時停止になっているのかを判別できません。その場合、以下のステップに従って、システムをサーバー側から手動で削除する必要があります。
  1. サブスクリプションマネージャーにログインします。

    サブスクリプションマネージャーは Red Hat カスタマーポータル 上にあります。画面上部にあるログインアイコンをクリックし、ユーザー名とパスワードを使用してカスタマーポータルにログインします。
  2. 「サブスクリプション」タブをクリックします。

    サブスクリプション タブをクリックします。
  3. 「システム」のリンクをクリックします。

    ページを下にスクロールし、システム をクリックします。
  4. システムを削除します。

    システムプロファイルを削除するには、表内でシステムのプロファイルを見つけ、その名前の横にあるチェックボックスを選択し、削除をクリックします。

10.4. virt-who の手動インストール

このセクションでは、ハイパーバイザーが提供するサブスクリプションを手動でアタッチする方法について説明します。

手順10.2 サブスクリプションを手動でアタッチする方法

  1. サブスクリプション情報を一覧表示し、プール ID を見つけます。

    まず、仮想タイプの利用可能なサブスクリプションを一覧表示する必要があります。以下のコマンドを入力します。
    [root@server1 ~]# subscription-manager list --avail --match-installed | grep 'Virtual' -B12
    Subscription Name: Red Hat Enterprise Linux ES (Basic for Virtualization)
    Provides:          Red Hat Beta
                       Oracle Java (for RHEL Server)
                       Red Hat Enterprise Linux Server
    SKU:               -------
    Pool ID:           XYZ123
    Available:         40
    Suggested:         1
    Service Level:     Basic
    Service Type:      L1-L3
    Multi-Entitlement: No
    Ends:              01/02/2017
    System Type:       Virtual
    表示されるプール ID に注目してください。この ID は次のステップで必要になるのでコピーしておいてください。
  2. プール ID を選択してサブスクリプションをアタッチします。

    直前のステップでコピーしておいたプール ID を使用して、attach コマンドを実行します。Pool ID XYZ123 を取得したプール ID に置き換えます。ターミナルで以下のコマンドを入力します。
    [root@server1 ~]# subscription-manager attach --pool=XYZ123
    
    Successfully attached a subscription for: Red Hat Enterprise Linux ES (Basic for Virtualization)

10.5. virt-who のトラブルシューティング

10.5.1. ハイパーバイザーのステータスが「red」になっているのはなぜですか?

シナリオ: サーバー側では、サブスクリプションを持たないハイパーバイザーにゲストをデプロイします。24 時間後にはハイパーバイザーはそのステータスを「red」とします。この状況を解決するには、そのハイパーバイザー用にサブスクリプションを取得する必要があります。または、ゲストをサブスクリプションを持つハイパーバイザーに永久的に移行します。

10.5.2. サブスクリプションステータスでエラーが出ました。どうすればよいですか?

シナリオ: 以下のエラーメッセージのいずれかが表示されます。
  • System not properly subscribed (システムが正しくサブスクライブされていません)
  • Status unknown (ステータス不明)
  • Late binding of a guest to a hypervisor through virt-who (host/guest mapping) (virt-who によるゲストのハイパーバイザーへの遅延バインディング (ホスト/ゲストのマッピング))
エラーの原因を確認するには、/var/log/rhsm/ ディレクトリーにある rhsm.log という virt who ログファイルを開きます。

第11章 QEMU ゲストエージェントおよび SPICE エージェントによる仮想化の強化

QEMU ゲストエージェントや SPICE エージェントなどの Red Hat Enterprise Linux のエージェントは、システム上で仮想化ツールをより最適に実行するのに役立ちます。本章では、これらのエージェントについて説明します。

注記

ホストおよびゲストのパフォーマンスをさらに最適化し、調整するには、『Red Hat Enterprise Linux 7 仮想化のチューニングと最適化ガイド』を参照してください。

11.1. QEMU ゲストエージェント

QEMU ゲストエージェントは、ゲスト内で実行され、ホストマシンが libvirt を使用してゲストオペレーティングシステムに対してコマンドを実行できるようにします。これにより、ファイルシステムのフリーズおよびフリーズ解除などの機能を容易に実行できます。ゲストオペレーティングシステムはその後、これらのコマンドに非同期的に応答します。QEMU ゲストエージェントパッケージの qemu-guest-agent はデフォルトで Red Hat Enterprise Linux 7 にインストールされます。
このセクションでは、libvirt コマンドとゲストエージェントが利用できる各種オプションについて説明します。

重要

信頼されるゲストによって実行される場合にのみ、QEMU ゲストエージェントは安全であることに注意してください。信頼されていないゲストはゲストエージェントのプロトコルを悪意のある方法で無視したり、これを誤用したりする可能性があります。ホスト上のサービス拒否攻撃を回避するためのビルトイン保護プログラムは存在しますが、ホストは、操作が予想どおりに実行されるためにゲストの連携を必要とします。
QEMU ゲストエージェントは、ゲストの実行中に仮想 CPU (vCPU) を有効/無効にするために使用できるため、ホットプラグおよびホットアンプラグ機能を使用せずに vCPU の数を調整できます。詳細は 「仮想 CPU 数の設定」 を参照してください。

11.1.1. QEMU ゲストエージェントとホスト間の通信設定

ホストマシンは、ホストとゲストマシン間の VirtIO シリアル接続で QEMU ゲストエージェントと通信します。VirtIO シリアルチャンネルは、キャラクターデバイスドライバー (通常 Unix ソケット) 経由でホストに接続し、ゲストはこのシリアルチャンネルでリッスンします。

注記

qemu-guest-agent は、ホストが VirtIO シリアルチャネルをリッスンしているかどうかを検知しません。ただし、このチャネルは現在ホストとゲスト間のイベントをリッスンするために使用されるため、リスナーのないチャネルに書き込みすることでゲスト仮想マシンに問題が発生する可能性は極めて低くなります。さらに、qemu-guest-agent プロトコルには、コマンドの実行時にホスト物理マシンがゲスト仮想マシンを強制的に同期に戻すことができる同期マーカーが含まれています。libvirt はこれらのマーカーをすでに使用しているため、ゲスト仮想マシンは保留状態の未達の応答を安全に破棄することができます。

11.1.1.1. Linux ゲスト上での QEMU ゲストエージェントの設定

QEMU ゲストエージェントは実行中またはシャットダウンした仮想マシンで設定できます。実行中のゲストに設定される場合、ゲストはゲストエージェントをすぐに使用し始めます。ゲストがシャットダウンしている場合は、QEMU ゲストエージェントが次回の起動時に有効にされます。
virsh または virt-manager を使用すると、ゲストと QEMU ゲストエージェント間の通信を設定できます。以下に、QEMU ゲストエージェントを Linux ゲストで設定する方法を説明します。

手順11.1 シャットダウンした Linux ゲストで virsh を使用したゲストエージェントとホスト間の通信設定

  1. 仮想マシンをシャットダウンします。

    QEMU ゲストエージェントを設定する前に、仮想マシン (この例では rhel7) がシャットダウンしていることを確認します。
    # virsh shutdown rhel7 
  2. QEMU ゲストエージェントチャンネルをゲスト XML 設定に追加します。

    QEMU ゲストエージェントの詳細を追加できるようゲストの XML ファイルを編集します。
    # virsh edit rhel7
    以下をゲストの XML ファイルに追加し、変更を保存します。
    <channel type='unix'>
       <target type='virtio' name='org.qemu.guest_agent.0'/>
    </channel>
  3. 仮想マシンを起動します。

    # virsh start rhel7
  4. ゲストに QEMU ゲストエージェントをインストールします。

    QEMU ゲストエージェントがゲスト仮想マシンにまだインストールされていない場合は、これをインストールします。
    # yum install qemu-guest-agent
  5. ゲスト内の QEMU ゲストエージェントを起動します。

    ゲスト内の QEMU ゲストエージェントサービスを起動します。
    # systemctl start qemu-guest-agent
別の方法として、以下のステップに従って QEMU ゲストエージェントを実行中のゲストで設定することもできます。

手順11.2 実行中の Linux ゲストでのゲストエージェントとホスト間の通信設定

  1. QEMU ゲストエージェントの XML ファイルを作成します。

    # cat agent.xml
    <channel type='unix'>
       <target type='virtio' name='org.qemu.guest_agent.0'/>
    </channel>
  2. QEMU ゲストエージェントを仮想マシンに割り当てます。

    以下のコマンドを実行して、QEMU ゲストエージェントを実行中の仮想マシン (この例では rhel7) に割り当てます。
    # virsh attach-device rhel7 agent.xml
  3. ゲストに QEMU ゲストエージェントをインストールします。

    QEMU ゲストエージェントがゲスト仮想マシンにまだインストールされていない場合は、これをインストールします。
    # yum install qemu-guest-agent
  4. ゲスト内の QEMU ゲストエージェントを起動します。

    ゲスト内の QEMU ゲストエージェントサービスを起動します。
    # systemctl start qemu-guest-agent

手順11.3 virt-manager を使用した QEMU ゲストエージェントとホスト間の通信設定

  1. 仮想マシンをシャットダウンします。

    QEMU ゲストエージェントの設定前に仮想マシンがシャットダウンしていることを確認します。
    仮想マシンをシャットダウンするには、Virtual Machine Manager の仮想マシンの一覧からシャットダウンする仮想マシンを選択し、メニューバーにあるスイッチアイコンをクリックします。
  2. QEMU ゲストエージェントチャンネルをゲストに追加します。

    ゲストウインドウの上部にある電球アイコンをクリックして仮想マシンのハードウェアの詳細画面を開きます。
    ハードウェアを追加 ボタンをクリックして 新しい仮想ハードウェアを追加 ウインドウを開き、チャンネル を選択します。
    名前 ドロップダウンリストから QEMU ゲストエージェントを選択し、完了 をクリックします。
    QEMU ゲストエージェントチャンネルデバイスの選択

    図11.1 QEMU ゲストエージェントチャンネルデバイスの選択

  3. 仮想マシンを起動します。

    仮想マシンを起動するには、Virtual Machine Managerの仮想マシンのリストから起動する仮想マシンを選択し、メニューバーの をクリックします。
  4. ゲストに QEMU ゲストエージェントをインストールします。

    virt-manager でゲストを開き、QEMU ゲストエージェントがゲスト仮想マシンにまだインストールされていない場合は、インストールします。
    # yum install qemu-guest-agent
  5. ゲスト内の QEMU ゲストエージェントを起動します。

    ゲスト内の QEMU ゲストエージェントサービスを起動します。
    # systemctl start qemu-guest-agent
QEMU ゲストエージェントが rhel7 仮想マシンに設定されました。

11.2. libvirt による QEMU ゲストエージェントの使用

QEMU ゲストエージェントをインストールすると、さまざまな libvirt コマンドがより強力になります。ゲストエージェントは以下の virsh コマンドを強化します。
  • virsh shutdown --mode=agent - QEMU ゲストエージェントで使用される virsh shutdown は連携するゲストをクリーンな状態でシャットダウンするように保証されているため、このシャットダウン方法は virsh shutdown --mode=acpi よりも信頼性が高くなります。エージェントがない場合、libvirt は ACPI シャットダウンイベントの挿入に依存しなければなりませんが、一部のゲストはそのイベントを無視し、シャットダウンされません。
    virsh reboot と同じ構文で使用できます。
  • virsh snapshot-create --quiesce - スナップショットが作成される前に、ゲストがその I/O を安定した状態にフラッシュできるようにします。これにより、fsck を実行したり、部分的なデータベーストランザクションを失わずにスナップショットを使用することが可能になります。ゲストエージェントは、ゲストの連携を可能にして、ディスクコンテンツの高度な安定性を実現します。
  • virsh domfsfreeze および virsh domfsthaw - 分離中のゲストファイルシステムを静止します。
  • virsh domfstrim - ファイルシステムをトリミングするようゲストを指示します。
  • virsh domtime - ゲストのクロックをクエリーまたは設定します。
  • virsh setvcpus --guest - CPU をオフラインにするようゲストを指示します。
  • virsh domifaddr --source agent - ゲストエージェントを介して、ゲストオペレーティングシステムの IP アドレスをクエリーします。
  • virsh domfsinfo - 実行中のゲスト内にマウントされたファイルシステムの一覧を表示します。
  • virsh set-user-password - ゲストのユーザーアカウントのパスワードを設定します。

11.2.1. ゲストディスクバックアップの作成

libvirtqemu-guest-agent と通信し、ゲスト仮想マシンファイルシステムのスナップショットが内部で一貫性を保ち、随時使用できるようにします。ゲストシステムの管理者はアプリケーション固有のフリーズ/フリーズ解除のフックスクリプトを作成およびインストールすることができます。ファイルシステムをフリーズする前に、qemu-guest-agent は主なフックスクリプト (qemu-guest-agent パッケージに含まれる) を呼び出します。フリーズプロセスは、すべての仮想マシンアプリケーションを一時的に非アクティブにします。
スナップショットプロセスは以下のステップで構成されています。
  • ファイルシステムのアプリケーション/データベースは作業バッファーを仮想ディスクにフラッシュし、クライアント接続の受け入れを停止します。
  • アプリケーションはそれらのデータファイルを一貫性のある状態にします。
  • メインフックスクリプトが返されます。
  • qemu-guest-agent はファイルシステムをフリーズし、管理スタックはスナップショットを取得します。
  • スナップショットが確認されます。
  • ファイルシステムの機能が再開します。
フリーズ解除が逆の順序で生じます。
ゲストのファイルシステムのスナップショットを作成するには、virsh snapshot-create --quiesce --disk-onlyコマンドを実行します。この代わりに、virsh snapshot-create-as guest_name --quiesce --disk-only を実行することもできますが、詳細は 「現在のゲスト仮想マシンのスナップショットの作成」 を参照してください。

注記

アプリケーション固有のフックスクリプトを正常に実行するには、各種の SELinux パーミッションを必要とする場合があります。これは、データベースと対話するためにスクリプトをソケットに接続する必要がある場合と同様です。通常、このような目的に対応するローカルの SELinux ポリシーを作成し、インストールしておく必要があります。表11.1「QEMU ゲストエージェントのパッケージコンテンツ」/etc/qemu-ga/fsfreeze-hook.d/ に説明のある restorecon -FvvR コマンドを実行した後、追加設定なしでファイルシステムノードにアクセスできます。
qemu-guest-agent バイナリー RPM には以下のファイルが含まれます。

表11.1 QEMU ゲストエージェントのパッケージコンテンツ

ファイル名説明
/usr/lib/systemd/system/qemu-guest-agent.serviceQEMU ゲストエージェント用のサービス制御スクリプト (開始/停止)。
/etc/sysconfig/qemu-ga/usr/lib/systemd/system/qemu-guest-agent.service 制御スクリプトで読み取られる QEMU ゲストエージェントの設定ファイル。設定内容はシェルスクリプトのコメントと共にファイルに記載されます。
/usr/bin/qemu-gaQEMU ゲストエージェントのバイナリーファイル。
/etc/qemu-gaフックスクリプトの root ディレクトリー。
/etc/qemu-ga/fsfreeze-hookメインフックスクリプト。これに必要な変更はありません。
/etc/qemu-ga/fsfreeze-hook.d個別の、アプリケーション固有フックスクリプトのディレクトリー。ゲストのシステム管理者はこのディレクトリーにフックスクリプトを手動でコピーし、適切なファイルモードビットであることを確認してから、このディレクトリー上で restorecon -FvvR を実行する必要があります。
/usr/share/qemu-kvm/qemu-ga/サンプルスクリプト (サンプルとしての使用のみを想定) を含むディレクトリー。ここに含まれるスクリプトは実行されません。
主なフックスクリプトである /etc/qemu-ga/fsfreeze-hook は独自のメッセージや、アプリケーション固有のスクリプトの標準出力およびエラーメッセージを /var/log/qemu-ga/fsfreeze-hook.log ログファイルに記録します。詳細は libvirt アップストリームの web サイト を参照してください。

11.3. SPICE エージェント

SPICE エージェントは、ゲストオペレーティングシステムを SPICE クライアントに統合することで、virt-manager などのグラフィカルアプリケーションをよりスムーズに実行できるようにします。
たとえば、virt-manager でウィンドウのサイズを変更する場合、SPICE エージェントは、クライアントの解像度に対する X セッションの解像度の自動調整を可能にします。また SPICE エージェントはホストとゲスト間のコピーアンドペーストのサポートを提供し、マウス操作とカーソル操作のずれの発生を防ぎます。
SPICE エージェントの各種機能に関するシステム固有の情報については、spice-vdagent パッケージの README ファイルを参照してください。

11.3.1. SPICE エージェントとホスト間の通信設定

SPICE エージェントは実行中またはシャットダウンした仮想マシンで設定できます。実行中のゲストに設定される場合、ゲストはゲストエージェントをすぐに使用し始めます。ゲストがシャットダウンしている場合は、SPICE エージェントが次回の起動時に有効にされます。
ゲストと SPICE エージェント間で通信を設定するには、virshまたは virt-manager を使用できます。以下に、SPICE エージェントを Linux ゲストで設定する方法を説明します。

手順11.4 Linux ゲストで virsh を使用したゲストエージェントとホスト間の通信設定

  1. 仮想マシンをシャットダウンします。

    SPICE エージェントを設定する前に、仮想マシン (この例では rhel7) がシャットダウンしていることを確認します。
    # virsh shutdown rhel7 
  2. SPICE エージェントチャンネルをゲスト XML 設定に追加します。

    SPICE エージェントの詳細を追加できるようゲストの XML ファイルを編集します。
    # virsh edit rhel7
    以下をゲストの XML ファイルに追加し、変更を保存します。
    <channel type='spicevmc'>
       <target type='virtio' name='com.redhat.spice.0'/>
    </channel>
  3. 仮想マシンを起動します。

    # virsh start rhel7
  4. ゲストに SPICE エージェントをインストールします。

    SPICE エージェントがゲスト仮想マシンにまだインストールされていない場合は、これをインストールします。
    # yum install spice-vdagent
  5. ゲスト内の SPICE エージェントを起動します。

    ゲスト内の SPICE エージェントサービスを起動します。
    # systemctl start spice-vdagent
別の方法として、以下のステップに従って SPICE エージェントを実行中のゲストで設定することもできます。

手順11.5 実行中の Linux ゲストでの SPICE エージェントとホスト間の通信設定

  1. SPICE エージェントの XML ファイルを作成します。

    # cat agent.xml
    <channel type='spicevmc'>
       <target type='virtio' name='com.redhat.spice.0'/>
    </channel>
  2. SPICE エージェントを仮想マシンに割り当てます。

    以下のコマンドを実行して、SPICE エージェントを実行中の仮想マシン (この例では rhel7) に割り当てます。
    # virsh attach-device rhel7 agent.xml
  3. ゲストに SPICE エージェントをインストールします。

    SPICE エージェントがゲスト仮想マシンにまだインストールされていない場合は、これをインストールします。
    # yum install spice-vdagent
  4. ゲスト内の SPICE エージェントを起動します。

    ゲスト内の SPICE エージェントサービスを起動します。
    # systemctl start spice-vdagent

手順11.6 virt-manager を使用した SPICE エージェントとホスト間の通信設定

  1. 仮想マシンをシャットダウンします。

    SPICE エージェントの設定前に仮想マシンがシャットダウンしていることを確認します。
    仮想マシンをシャットダウンするには、Virtual Machine Manager の仮想マシンの一覧からシャットダウンする仮想マシンを選択し、メニューバーにあるスイッチアイコンをクリックします。
  2. SPICE エージェントチャンネルをゲストに追加します。

    ゲストウインドウの上部にある電球アイコンをクリックして仮想マシンのハードウェアの詳細画面を開きます。
    ハードウェアを追加 ボタンをクリックして 新しい仮想ハードウェアを追加 ウインドウを開き、チャンネル を選択します。
    名前 ドロップダウンリストから SPICE エージェントを選択し、チャンネルアドレスを編集して 完了 をクリックします。
    SPICE エージェントチャンネルデバイスの選択

    図11.2 SPICE エージェントチャンネルデバイスの選択

  3. 仮想マシンを起動します。

    仮想マシンを起動するには、Virtual Machine Managerの仮想マシンのリストから起動する仮想マシンを選択し、メニューバーの をクリックします。
  4. ゲストに SPICE エージェントをインストールします。

    virt-manager でゲストを開き、SPICE エージェントがゲスト仮想マシンにまだインストールされていない場合は、インストールします。
    # yum install spice-vdagent
  5. ゲスト内の SPICE エージェントを起動します。

    ゲスト内の SPICE エージェントサービスを起動します。
    # systemctl start spice-vdagent
SPICE エージェントが rhel7 仮想マシンに設定されました。

第12章 ネストされた仮想化

12.1. 概要

Red Hat Enterprise Linux 7.5 では、ネストされた仮想化 を KVM ゲスト仮想マシンのテクノロジープレビューとして利用できます。この機能を使うと、物理ホスト (レベル 0 または L0 とも言う) で実行されるゲスト仮想マシン (レベル 1 または L1) はハイパーバイザーとして機能し、独自のゲスト仮想マシン (L2) を作成できます。
ネストされた仮想化は、制限のある環境でハイパーバイザーをデバッグしたり、数に制限のある物理リソース上の規模の大きい仮想デプロイメントをテストしたりするのに役立ちます。ただし、ネストされた仮想化はユーザーの本番稼動環境ではサポートされず、推奨もされておらず、これは主に開発およびテスト目的で使用されることが意図されていることに注意してください。
ネストされた仮想化はホストの仮想化拡張機能に依存した状態で機能します。これをQEMU Tiny Code Generator (TCG) エミュレーションを使用して仮想想環境でゲストを実行することと混同しないようにしてください。後者は、Red Hat Enterprise Linux ではサポートされません。

12.2. 設定

以下のステップに従って、ネストされた仮想化を有効にし、これを設定して使用を開始してください。
  1. 有効化: この機能はデフォルトで無効にされています。有効にするには、L0 ホスト物理マシンで以下の手順を実行してください。
    Intel の場合:
    1. ネストされた仮想化がホストシステムで利用できるかどうかを確認します。
      $ cat /sys/module/kvm_intel/parameters/nested
      このコマンドが Y または 1 を返す場合、この機能は有効にされています。
      コマンドが 0 または N を返す場合、ステップ b および c を使用します。
    2. kvm_intel モジュールをアンロードします。
      # modprobe -r kvm_intel
    3. ネスト機能をアクティブにします。
      # modprobe kvm_intel nested=1
    4. ネスト機能は L0 ホストの次回起動時まで有効になります。これを永続的に有効化するには、以下の行を /etc/modprobe.d/kvm.conf ファイルに追加します。
      options kvm_intel nested=1
    AMD の場合:
    1. ネストされた仮想化がシステムで利用できるかどうかを確認します。
      $ cat /sys/module/kvm_amd/parameters/nested
      このコマンドが Y または 1 を返す場合、この機能は有効にされています。
      コマンドが 0 または N を返す場合、ステップ b および c を使用します。
    2. kvm_amd モジュールをアンロードします。
      # modprobe -r kvm_amd
    3. ネスト機能をアクティブにします。
      # modprobe kvm_amd nested=1
    4. ネスト機能は L0 ホストの次回起動時まで有効になります。これを永続的に有効化するには、以下の行を /etc/modprobe.d/kvm.conf ファイルに追加します。
      options kvm_amd nested=1
  2. 以下の方法のいずれかを使用して、仮想化のネスト化に向けて L1 仮想マシンを 設定 します。
    virt-manager
    1. 目的のゲストの GUI を開き、仮想マシンの情報を表示 アイコンをクリックします。
    2. Processor メニューを選択し、設定 セクションの host-passthroughモデルl フィールドに と入力してから (ドロップダウンの選択項目を使用しないでください)、適用 をクリックします。
    ドメイン XML
    以下の行をゲストのドメイン XML ファイルに追加します。
    <cpu mode='host-passthrough'/>
    ゲストの XML 設定ファイルに <cpu> 要素がすでに含まれる場合は、これを書き直してください。
  3. ネストされた仮想化の 使用を開始 するには、L1 ゲスト内に L2 ゲストをインストールします。これを実行するには、L1 ゲストのインストール時と同じ手順に従います。詳細は、3章仮想マシンの作成 を参照してください。

12.3. 制約および制限事項

  • L0 ホストおよび L1 ゲストでは Red Hat Enterprise Linux 7.2 以降を実行することを強く推奨します。L2 ゲストには Red Hat でサポートされる任意のゲストシステムを含めることができます。
  • L1 または L2 ゲストの移行はサポートされません。
  • ハイパーバイザーとしての L2 ゲストの使用と L3 ゲストの作成はサポートされません。
  • ホストで利用できるすべての機能が L1 ハイパーバイザーで使用できる訳ではありません。たとえば、IOMMU/VT-d または APICv は L1 ハイパーバイザーで使用することはできません。
  • ネストされた仮想化を使用するには、ホスト CPU に必要な機能フラグがなければなりません。L0 および L1 ハイパーバイザーが正常に設定されている場合、L0 および L1 の両方で cat /proc/cpuinfo コマンドを使用し、以下のフラグが両方のハイパーバイザーのそれぞれの CPU について一覧表示されていることを確認します。
    • Intel の場合: vmx (Hardware Virtualization; ハードウェア仮想化) および ept (Extended Page Tables; 拡張ページテーブル)
    • AMD の場合: svm (vmx と同等) および npt (ept と同等)

パート II. 管理

第13章 仮想マシンのストレージ管理

この章では、仮想マシンのストレージについて説明します。仮想ストレージは仮想マシンの接続に割り当てられた物理ストレージから抽象化されます。ストレージは、準仮想化またはエミュレートされたブロックデバイスドライバーを使用して仮想マシンに接続されます。

13.1. ストレージの概念

ストレージプールとは、ゲスト仮想マシンが使用するために確保しておくストレージの量のことです。ストレージプールは、ストレージボリュームに分割されます。各ストレージボリュームは、ゲストバス上のブロックデバイスとしてゲスト仮想マシンに割り当てられます。
ストレージプールとボリュームはlibvirt を使用して管理されます。libvirt のリモートプロトコルを用いると、ゲスト仮想マシンのライフサイクルのあらゆる側面と、ゲスト仮想マシンが必要とするリソースの構成を管理できます。これらの操作は、リモートホスト上で実行することができます。そのため、libvirt を使用する 仮想マシンマネージャー などの管理アプリケーションによって、ユーザーはゲスト仮想マシンのホスト物理マシンの設定するために必要なタスクをすべて実行できます。これらのタスクには、リソースの割り当て、ゲスト仮想マシンの実行や終了、およびリソースの割り当て解除が含まれ、シェルへのアクセスやその他の制御チャネルを必要としません。
libvirt API を使用すると、ストレージプールのボリュームリストに対してクエリーを実行でき、ストレージプールの容量、割り当て、および利用可能なストレージに関する情報を取得できます。ストレージプールのストレージボリュームは、割り当てや容量などの情報を取得するためにクエリーが行われることがあり、スパース (sparse) ボリュームでは異なることがあります。

注記

スパース (Sparse) ボリュームの詳細については、『仮想化スタートガイド』を参照してください。
サポートするストレージプールの場合、libvirt API を使用してストレージボリュームの作成、クローン、サイズ変更、および削除を行うことができます。また、API を使用してストレージボリュームへのデータのアップロード、ストレージボリュームからのデータのダウンロード、またはストレーボリュームからのデータの消去を行うこともできます。
ストレージプールの開始後、ドメイン XML のボリュームへのホストパスの代わりにストレージプール名とストレージボリューム名を使用して、ストレージボリュームをゲストに割り当てることができます。

注記

ドメイン XML の詳細は 23章ドメイン XML の操作 を参照してください。
ストレージプールは停止 (破棄) することができます。これにより、データの抽象化は削除されますが、データは保持されます。
たとえば、mount -t nfs nfs.example.com:/path/to/share /path/to/data を使用する NFS サーバーの場合、担当のストレージ管理者は仮想化ホストで NFS ストレージプールを定義し、エスクポートされたサーバーのパスとクライアントターゲットのパスを定義できます。これにより、libvirtlibvirt の起動時に自動的にマウントを実行するか、libvirt の実行中に必要に応じてマウントを実行することができます。NFS サーバーのエクスポートされたディレクトリーは、NFS ストレージプール内のストレージボリュームとしてリストされます。
ストレージボリュームがゲストに追加されると、管理者は、ボリュームへのターゲットパスを追加する必要はありません。名前を使ってストレージプールおよびストレージボリュームを追加する必要があります。そのため、ターゲットクライアントのパスが変更された場合でも仮想マシンには影響しません。
ストレージプールが開始されると、libvirt は共有を指定のディレクトリー上にマウントします。これは、システム管理者がログインし、mount nfs.example.com:/path/to/share /vmdata を実行した場合と同様です。ストレージプールが自動起動するよう設定されている場合、libvirtlibvirt の起動時に NFS 共有ディスクが指定されたディレクトリー上にマウントされるようにします。
ストレージプールが開始されると、NFS 共有ディスク内のファイルはストレージボリュームとして報告され、libvirt API を使用してストレージボリューのパスに対してクエリーが実行されることがあります。その後、ゲスト仮想マシンのブロックデバイスのソースストレージを記述するゲスト仮想マシンの XML 定義にストレージボリュームのパスをコピーすることができます。NFS の場合、libvirt API を使用するアプリケーションは、プールのサイズの限界まで (NFS 共有のストレージ容量) ストレージプール (NFS 共有のファイル) のストレージボリュームを作成および削除できます。
すべてのストレージプールの種類がボリュームの作成および削除をサポートする訳ではありません。ストレージプールを停止 (pool-destroy) すると、開始操作が取り消され、この場合は NFS 共有がアンマウントされます。共有上のデータは destroy 操作では編集されません。詳細は「man virsh」を参照してください。

手順13.1 ストレージの作成および割り当て

ここでは、仮想マシンゲストのストレージを作成および割り当てるのに必要な手順の概要を説明します。
  1. ストレージプールの作成

    使用可能なストレージメディアから 1 つ以上のストレージプールを作成します。詳細は 「ストレージプールの使用」 を参照してください。
  2. ストレージボリュームの作成

    使用可能なストレージプールから 1 つ以上のストレージボリュームを作成します。詳細は 「ストレージボリュームの使用」 を参照してください。
  3. ストレージデバイスを仮想マシンに割り当てます。

    ストレージボリュームから抽象化した 1 つ以上のストレージデバイスをゲスト仮想マシンに割り当てます。詳細は 「ストレージデバイスのゲストへの追加」 を参照してください。

13.2. ストレージプールの使用

ここでは、仮想マシンでのストレージプールの使用に関する情報を提供します。概念と、virsh コマンドと 仮想管理マネージャー を使用してストレージプールを作成設定、および削除 する方法の詳細を説明します。

13.2.1. ストレージプールの概念

ストレージプールは libvirt によって管理されるファイル、ディレクトリー、またはストレージデバイスで、仮想マシンにストレージを提供します。ストレージプールは仮想マシンのイメージを格納するストレージボリュームに分割されるか、追加のストレージとして仮想マシンに接続されます。複数のゲストは同じストレージプールを共有できるため、ストレージリソースの割り当てが向上されます。
ストレージプールはローカルまたはネットワークベース (共有) のいずれかになります。
ローカルストレージプール
ローカルストレージプールは、ホストサーバーに直接アタッチされています。これに含まれるのは、ローカルディレクトリー、直接アタッチされたディスク、物理パーティション、ローカルデバイス上の論理ボリューム管理 (LVM) のボリュームグループです。ローカルストレージプールは開発、テスト、移行や多数の仮想マシンを必要としない小規模開発などに役立ちます。ローカルストレージプールは、ライブマイグレーションに使用できないため、多くの本番環境に適切でない可能性があります。
ネットワーク (共有) ストレージプール
ネットワークストレージプールは、標準のプロトコルを使用したネットワーク上の共有ストレージデバイスを含みます。ネットワークストレージは、virt-manager を使ってホスト間で仮想マシンを移行するときに必要になりますが、virsh を使って移行する場合は任意になります。
仮想マシンの移行の詳細は 15章KVM の移行 を参照してください。
Red Hat Enterprise Linux でサポートされるストレージプールは次のとおりです。
  • ディレクトリベースのストレージプール
  • ディスクベースのストレージプール
  • パーティションベースのストレージプール
  • GlusterFS ストレージプール
  • iSCSI ベースのストレージプール
  • LVM ベースのストレージプール
  • NFS ベースのストレージプール
  • SCSI デバイスとの vHBA ベースのストレージプール
Red Hat Enterprise Linux でサポートサポートされない libvirt ストレージプールタイプは次のとおりです。
  • マルチパスベースのストレージプール
  • RBD ベースのストレージプール
  • Sheepdog ベースのストレージプール
  • Vstorage ベースのストレージプール
  • ZFS ベースのストレージプール

注記

サポートされないストレージプールタイプの一部は 仮想管理マネージャー に表示されますが、使用しないでください。

13.2.2. ストレージプールの作成

ここでは、virsh および 仮想マシンマネージャー を使用した、一般的なストレージプールの作成手順を説明します。virsh を使用するとすべてのパラメーターを指定でき、仮想マシンマネージャー では GUI で簡単なストレージプールを作成できます。

13.2.2.1. virsh を使用したストレージプールの作成

注記

ここでは、例としてパーティションベースのストレージプールを作成します。

手順13.2 virsh を使用したストレージプールの作成

  1. 推奨事項を読み、前提条件をすべて満たしているようにしてください。

    一部のストレージプールでは、特定の慣例に従うことが推奨されます。さらに、ストレージプールのタイプによっては特定の前提条件があります。推奨事項と前提条件を確認するには、「ストレージプール固有の情報」 を参照してください。
  2. ストレージプールを定義します。

    ストレージプールは永続または一時になります。永続ストレージプールは、ホストマシンのシステムの再起動後も保持されます。一時ストレージプールは、ホストが再起動されるまで存在します。
    次のいずれかを行います。
    • XML ファイルを使用してストレージプールを定義します。
      a. 新規デバイスに必要となるストレージプール情報が含まれる一時 XML ファイルを作成します。
      XML ファイルには、ストレージプールタイプに応じた特定のフィールドが含まれる必要があります。詳細は 「ストレージプール固有の情報」 を参照してください。
      以下はストレージプール定義の XML ファイルの例になります。この例では、ファイルは ~/guest_images.xml に保存されます。
      <pool type='fs'>
        <name>guest_images_fs</name>
        <source>
          <device path='/dev/sdc1'/>
        </source>
        <target>
          <path>/guest_images</path>
        </target>
      </pool> 
      b. virsh pool-defineコマンドを使用して永続ストレージプールを作成するか、virsh pool-create コマンドを使用して一時ストレージプールを作成および開始します。
      # virsh pool-define ~/guest_images.xml
      Pool defined from guest_images_fs
      または
      # virsh pool-create ~/guest_images.xml
      Pool created from guest_images_fs
      c. a. で作成した XML ファイルを削除します。
    • virsh pool-define-asコマンドを使用して永続ストレージプールを作成するか、virsh pool-create-as コマンドを使用して一時ストレージプールを作成します。
      以下の最初の例は、/guest_images ディレクトリーから /dev/sdc1 にマップされる、ファイルシステムベースの永続ストレージプールを作成し、2 つ目の例は同様にマップされるファイルシステムベースの一時ストレージプールを作成します。
      # virsh pool-define-as guest_images_fs fs - - /dev/sdc1 - "/guest_images"
      Pool guest_images_fs defined
      または
      # virsh pool-create-as guest_images_fs fs - - /dev/sdc1 - "/guest_images"
      Pool guest_images_fs created

      注記

      virsh インターフェースを使用する場合、コマンドのオプション名は任意です。オプション名を使用しない場合は、指定する必要のないフィールドにダッシュを使用します。
  3. プールが作成されたことを確認します。

    virsh pool-list --all を使用して、既存のストレージプールをすべてリストします。
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    guest_images_fs      inactive   no
  4. ストレージプールのターゲットパスを定義します。

    virsh pool-build コマンドを使用して事前にフォーマットされたファイルシステムストレージプールのターゲットパスを作成します。ストレージソースデバイスを初期化し、データ形式を定義します。その後、virsh pool-list コマンドを使用してストレージプールが表示されることを確認します。
    # virsh pool-build guest_images_fs
    Pool guest_images_fs built
    # ls -la /guest_images
    total 8
    drwx------.  2 root root 4096 May 31 19:38 .
    dr-xr-xr-x. 25 root root 4096 May 31 19:38 ..
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    guest_images_fs      inactive   no

    注記

    ターゲットパスの構築は、ディスクベースのストレージプール、ファイルシステムベースのストレージプール、および論理ストレージプールにのみ必要です。libvirt によって、ソースストレージデバイスのデータ形式が選択したストレージプールの種類とは異なることが判明した場合、overwrite オプションが指定されていないと構築に失敗します。
  5. ストレージプールを起動します。

    virsh pool-start コマンドを使用して、ソースデバイスの使用を準備します。
    アクションはストレージプールの種類によって異なります。たとえば、ファイルシステムベースのストレージプールの場合、virsh pool-start コマンドがファイルシステムをマウントします。LVM ベースのストレージプールでは、virsh pool-start コマンドが vgchange コマンドを使用してボリュームグループをアクティベートします。
    その後、virsh pool-list command を使用してストレージプールがアクティブであることを確認します。
    # virsh pool-start guest_images_fs
    Pool guest_images_fs started
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    guest_images_fs      active     no

    注記

    virsh pool-start コマンドは、永続ストレージプールにのみ必要です。一時ストレージプールは、作成時に自動的に起動されます。
  6. 自動起動をオンにします (任意)。

    デフォルトでは、virsh で定義されたストレージプールは、libvirtd の起動時に毎回自動的に起動されるよう設定されていません。virsh pool-autostart コマンドを使用すると、ストレージプールが自動的に起動するよう設定することができます。
    # virsh pool-autostart guest_images_fs
    Pool guest_images_fs marked as autostarted
    
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    guest_images_fs      active     yes
    libvirtd の起動時に毎回ストレージプールが自動的に起動されるようになりました。
  7. ストレージプールを確認します。

    ストレージプールが正しく作成されたこと、およびサイズが予測される値で報告されていること、さらに状態が running として報告されていることを確認します。ファイルシステム上のターゲットパスに、デバイスがマウントされたことを示す「lost+found」ディレクトリーがあることを確認します。
    # virsh pool-info guest_images_fs
    Name:           guest_images_fs
    UUID:           c7466869-e82a-a66c-2187-dc9d6f0877d0
    State:          running
    Persistent:     yes
    Autostart:      yes
    Capacity:       458.39 GB
    Allocation:     197.91 MB
    Available:      458.20 GB
    # mount | grep /guest_images
    /dev/sdc1 on /guest_images type ext4 (rw)
    # ls -la /guest_images
    total 24
    drwxr-xr-x.  3 root root  4096 May 31 19:47 .
    dr-xr-xr-x. 25 root root  4096 May 31 19:38 ..
    drwx------.  2 root root 16384 May 31 14:18 lost+found

13.2.2.2. 仮想マシンマネージャーでのストレージプールの作成

注記

ここでは、例としてディスクベースのストレージプールを作成します。

手順13.3 仮想マシンマネージャーでのストレージプールの作成

  1. ストレージプールが作成されるメディアを準備します。

    これは、ストレージプールの種類によって異なります。詳細は 「ストレージプール固有の情報」 を参照してください。
    この例では、GUID パーティションテーブル でディスクを再度ラベル付けする必要があることがあります。
  2. ストレージ設定を開きます。

    1. 仮想マシンマネージャーで、設定するホスト接続を選択します。
      編集 メニューを開き、接続の詳細 を選択します。
    2. 接続の詳細 ウインドウの ストレージ タブをクリックします。
      「ストレージ」タブ

      図13.1 「ストレージ」タブ

  3. 新しいストレージプールを作成します。

    注記

    仮想マシンマネージャー では永続ストレージプールのみを作成できます。一時ストレージプールは virsh を使用してのみ作成できます。
    1. 新しいストレージプールを追加します (パート 1)

      ウィンドウの下部にある ボタンをクリックします。新しいストレージプールを追加 ウィザードが表示されます。
      ストレージプールの 名前 を入力します。この例では名前として guest_images_fs を使用します。
      種類 ドロップダウンリストから作成するストレージプールの種類を選択します。この例では fs: 事前フォーマット済みブロックデバイス を使用します。
      ストレージプールの名前と種類

      図13.2 ストレージプールの名前と種類

      進む ボタンをクリックして続行します。
    2. 新規プールの追加 (パート 2)

      ストレージプールのパス

      図13.3 ストレージプールのパス

      関連するパラメーターを持つストレージプールを設定します。ストレージプールの各種類のパラメーターに関する情報は、「ストレージプール固有の情報」 を参照してください。
      ストレージプールの種類によっては プールを構築 チェックボックスがダイアログに表示されることがあります。ストレージからストレージプールを構築する場合は、プールを構築 チェックボックスにチェックマークを入れます。
      詳細を確認し、完了 ボタンをクリックしてストレージプールを作成します。

13.2.3. ストレージプール固有の情報

ここでは、前提条件、パラメーター、その他の情報など、ストレージプールの各種類に固有する情報を提供します。以下のトピックが含まれます。

13.2.3.1. ディレクトリベースのストレージプール

パラメーター
以下の表には、ディレクトリーベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.1 ディレクトリーベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='dir'>[type] ディレクトリーdir: ファイルシステムディレクトリー
ストレージプールの名前<name>name</name>[name] name名前
ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>target_path</path>
</target>

target path_to_poolターゲットパス
virsh を使用してストレージプールを作成している場合、プールが作成されたことを確認して続行します。
以下は、/guest_images ディレクトリーを基にしたストレージプールの XML ファイルの例になります。
<pool type='dir'>
  <name>dirpool</name>
  <target>
    <path>/guest_images</path>
  </target>
</pool>  
以下は、/guest_images ディレクトリーを基にしたストレージプール作成のコマンドの例になります。
# virsh pool-define-as dirpool dir --target "/guest_images"
Pool FS_directory defined
以下のイメージは、/guest_images ディレクトリーを基にしたストレージプールを作成するための 仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの例になります。
新しいディレクトリーベースのストレージプールの追加例

図13.4 新しいディレクトリーベースのストレージプールの追加例

13.2.3.2. ディスクベースのストレージプール

推奨
以下の点に注意してディスクベースのストレージプールを作成してください。
  • 使用されている libvirt のバージョンによっては、ディスクをストレージプール専用にすると、ディスクデバイスに現在保存されているすべてのデータが再フォーマットまたは消去されることがあります。ストレージデバイスのデータをバックアップしてからストレージプールを作成することが強く推奨されます。
  • ゲストにはディスクまたはブロックデバイス全体 (例: /dev/sdb) の書き込み権限を与えないでください。パーティション (例: /dev/sdb1) または LVM ボリュームを使用してください。
    ゲストにブロックデバイス全体を渡した場合、ゲストはそれにパーティションを設定するか、またはその上に独自の LVM グループを作成する可能性があります。これは、ホスト物理マシンがこれらのパーティションや LVM グループを検出し、エラーを出す原因になります。
前提条件

注記

ここの手順は、virsh pool-build コマンドを実行しない場合のみ必要になります。
ディスクのラベルを GPT (GUID パーティションテーブル) ディスクラベルに変更しないと、ディスクベースのストレージプールをホストディスク上に作成できません。GPT ディスクラベルでは、各デバイスに最大 128 個のパーティションを作成できます。
# parted /dev/sdb
GNU Parted 2.1
Using /dev/sdb
Welcome to GNU Parted! Type 'help' to view a list of commands.
(parted) mklabel
New disk label type? gpt
(parted) quit
Information: You may need to update /etc/fstab.
#
ディスクのラベルを変更したら、ストレージプールを定義して ストレージプールの作成を続行します。
パラメーター
以下の表には、ディスクベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.2 ディスクベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='disk'>[type] ディスクdisk: 物理ディスクデバイス
ストレージプールの名前<name>name</name>[name] name名前
ストレージデバイスを指定するパス (例: /dev/sdb)。

<source>
  <device path=/dev/sdb/>
<source>

source-dev path_to_diskソースパス
ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>/path_to_pool</path>
</target>

target path_to_poolターゲットパス
virsh を使用してストレージプールを作成している場合、ストレージプールの定義 を続行します。
以下は、ディスクベースストレージプールの XML ファイルの例になります。
<pool type='disk'>
  <name>phy_disk</name>
  <source>
    <device path='/dev/sdb'/>
    <format type='gpt'/>
  </source>
  <target>
    <path>/dev</path>
  </target>
</pool>  
以下は、ディスクベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as phy_disk disk gpt --source-dev=/dev/sdb --target /dev
Pool phy_disk defined
以下のイメージは、ディスクベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しいディスクベースのストレージプールの追加例

図13.5 新しいディスクベースのストレージプールの追加例

13.2.3.3. ファイルシステムベースのストレージプール

推奨
ディスク全体をストレージプールとして割り当てる場合は、ここの手順を使用しないでください (例: /dev/sdb)。ゲストにはディスクまたはブロックデバイス全体への書き込み権限を与えないでください。この方法はパーティション (例: /dev/sdb1) をストレージプールに割り当てるためにのみ使用してください。
前提条件

注記

これは、virsh pool-build コマンドを実行しない場合のみ必要になります。
パーティションからストレージプールを作成するには、ファイルシステムを ext4 にフォーマットします。
# mkfs.ext4 /dev/sdc1
ファイルシステムをフォーマットしたら、ストレージプールを定義して ストレージプールの作成を続行します。
パラメーター
以下の表には、ファイルシステムベースのストレージプールをパーティションから作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.3 ファイルシステムベースストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='fs'>[type] fsfs: 事前フォーマント済みブロックデバイス
ストレージプールの名前<name>name</name>[name] name名前
パーティションを指定するパス (例: dev/sdc1)

<source>
  <device path='source_path' />

[source] path_to_partitionソースパス
ファイルシステムの種類 (例: ext4)。

  <format type='fs_type' />
</source>

[source format] FS-format該当なし
ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>/path_to_pool</path>
</target>

[target] path_to_poolターゲットパス
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、ファイルシステムベースストレージプールの XML ファイルの例になります。
<pool type='fs'>
  <name>guest_images_fs</name>
  <source>
    <device path='/dev/sdc1'/>
    <format type='auto'/>
  </source>
  <target>
    <path>/guest_images</path>
  </target>
</pool>  
以下は、パーティションベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as guest_images_fs fs --source-dev /dev/sdc1 --target /guest_images
Pool guest_images_fs defined
以下のイメージは、ファイルシステムベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しいファイルシステムベースのストレージプールの追加例

図13.6 新しいファイルシステムベースのストレージプールの追加例

13.2.3.4. GlusterFS ベースのストレージプール

推奨
GlusterFS は、File System in Userspace (FUSE) を使用する user space ファイルシステムです。
前提条件
GlusterFS ベースのストレージプールをホスト上に作成できるようにするには、最初に Gluster サーバーを準備する必要があります。

手順13.4 Gluster サーバーの準備

  1. 次のコマンドを使って、状態を一覧表示し、Gluster サーバーの IP アドレスを取得します。
    # gluster volume status
    Status of volume: gluster-vol1
    Gluster process						Port	Online	Pid
    ------------------------------------------------------------------------------
    Brick 222.111.222.111:/gluster-vol1 			49155	Y	18634
    
    Task Status of Volume gluster-vol1
    ------------------------------------------------------------------------------
    There are no active volume tasks
  2. glusterfs-fuse パッケージがインストールされていない場合はインストールします。
  3. virt_use_fusefs ブール値が有効になっていない場合は有効にします。有効になっているか確認してください。
    # setsebool virt_use_fusefs on
    # getsebool virt_use_fusefs
    virt_use_fusefs --> on
必要なパッケージがインストールされ、有効になっていることを確認したら、ストレージプールを定義 して、引き続きストレージプールの作成を行います。
パラメーター
以下の表には、GlusterFS ベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および 仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.4 GlusterFS ベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='gluster'>[type] glusterGluster: Gluster ファイルシステム
ストレージプールの名前<name>name</name>[name] name名前
Gluster サーバーのホスト名または IP アドレス

<source>
  <hostname='hostname' />

source-host hostnameホスト名
Gluster サーバーの名前  <name='Gluster-name' />source-name Gluster-nameソース名
ストレージプールに使用される Gluster サーバーのパス。

  <dir path='Gluster-path' />
</source>

source-path Gluster-pathソースパス
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、GlusterFS ベースストレージプールの XML ファイルの例になります。
<pool type='gluster'>
  <name>Gluster_pool</name>
  <source>
    <host name='111.222.111.222'/>
    <dir path='/'/>
    <name>gluster-vol1</name>
  </source>
</pool>  
以下は、GlusterFS ベースのストレージプールを作成するコマンドの例になります。
# pool-define-as --name Gluster_pool --type gluster --source-host 111.222.111.222 --source-name gluster-vol1 --source-path /
Pool Gluster_pool defined
以下のイメージは、Gluster ベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しい GlusterFS ベースのストレージプールの追加例

図13.7 新しい GlusterFS ベースのストレージプールの追加例

13.2.3.5. iSCSI ベースのストレージプール

推奨
iSCSI (Internet Small Computer System Interface) とは、ストレージデバイスを共有するためのネットワークプロトコルです。iSCSI では、IP 層全体での SCSI の指示を使用してイニシエーター (ストレージクライアント) をターゲット (ストレージサーバー) に接続します。
iSCSI ベースのデバイスを使用してゲスト仮想マシンを格納すると、ブロックストレージデバイスとして iSCSI を使用するなど、より柔軟にストレージを使用することができます。iSCSI デバイスは、Linux のマルチプロトコル SCSI ターゲットである Linux-IO (LIO) ターゲットを使用します。iSCSI のほかにも、LIO はファイバーチャネルおよびファイバーチャネルオーバーイーサネット (FCoE: Fibre Channel over Ethernet) もサポートします。
前提条件
iSCSI ベースのストレージプールを作成できるようにするには、最初に iSCSI ターゲットを作成する必要があります。iSCSI ターゲットは targetcli パッケージを使用して作成されます。このパッケージは、ソフトウェアベースの iSCSI ターゲットを作成するためのコマンドセットを提供します。

手順13.5 iSCSI ターゲットの作成

  1. targetcli パッケージのインストール

    # yum install targetcli
  2. targetcli コマンドセットを起動します。

    # targetcli
  3. ストレージオブジェクトの作成

    ストレージプールを使用して、3 つのストレージオブジェクトを作成します。
    1. ブロックストレージオブジェクトの作成
      1. /backstores/block ディレクトリーに移動します。
      2. create コマンドを実行します。
        # create [block-name][filepath]
        例を以下に示します。
        # create block1 dev=/dev/sdb1
    2. fileio オブジェクトの作成
      1. /fileio ディレクトリーに移動します。
      2. create コマンドを実行します。
        # create [fileio-name][image-name] [image-size]
        例を以下に示します。
        # create fileio1 /foo.img 50M
    3. ram ディスクオブジェクトの作成
      1. /ramdisk ディレクトリーに移動します。
      2. create コマンドを実行します。
        # create [ramdisk-name] [ramdisk-size]
        例を以下に示します。
        # create ramdisk1 1M
    4. ここで作成するディスクの名前を書き留めておきます。これは後ほど使用します。
  4. iSCSI ターゲットの作成

    1. /iscsi ディレクトリーに移動します。
    2. ターゲットを以下の 2 つの方法のいずれかで作成します。
      • パラメーターを使用せずに create コマンドを実行します。
        iSCSI 修飾名 (IQN) が自動的に生成されます。
      • 以下の例のように、IQN とサーバーを指定して create コマンドを実行します。
        # create iqn.2010-05.com.example.server1:iscsirhel7guest
  5. ポータル IP アドレスの定義

    iSCSI 上でブロックストレージをエクスポートするには、最初にポータル、LUN、および アクセス制御リスト ACL を設定する必要があります。
    ポータルには、ターゲットが監視する IP アドレスおよび TCPと、ポータルが接続するイニシエーターが含まれます。iSCSI は 3260 番ポートを使用します。このポートはデフォルトで設定されています。
    3260 番ポートに接続するには、以下を行います。
    1. /tpg ディレクトリーに移動します。
    2. 次のコマンドを実行します。
      # portals/ create
      このコマンドは、利用可能な IP アドレスがすべて 3260 番ポートをリッスンするようにします。
      1 つの IP アドレスのみが 3260 番ポートをリッスンするようにするには、以下の例のように IP アドレスをコマンドの最後に追加します。
      # portals/ create 143.22.16.33
  6. LUN を設定し、ストレージオブジェクトをファブリックに割り当てます。

    このステップでは、「ストレージオブジェクトの作成」で作成したストレージオブジェクトを使用します。
    1. 以下の例のように、「ポータル IP アドレスの定義」で作成した TPG の luns ディレクトリーに移動します。
      # iscsi>iqn.iqn.2010-05.com.example.server1:iscsirhel7guest
    2. 以下の例のように、最初の LUN ram ディスクに割り当てます。
      # create /backstores/ramdisk/ramdisk1
    3. 以下の例のように、2 番目の LUN をブロックディスクに割り当てます。
      # create /backstores/block/block1
    4. 以下の例のように、3 番目の LUN を fileio ディスクに割り当てます。
      # create /backstores/fileio/fileio1
    5. 結果の LUN を一覧表示します。
      /iscsi/iqn.20...csirhel7guest ls
      
      o- tgp1 ............................................................[enabled, auth]
        o- acls...................................................................[0 ACL]
        o- luns..................................................................[3 LUNs]
        | o- lun0......................................................[ramdisk/ramdisk1]
        | o- lun1...............................................[block/block1 (dev/vdb1)]
        | o- lun2................................................[fileio/file1 (foo.img)]
        o- portals.............................................................[1 Portal]
          o- IP-ADDRESS:3260.........................................................[OK]
  7. 各イニシエーターに ACL を作成

    イニシエーターの接続時に認証を有効にします。指定の LUN を指定のイニシエーターに制限することもできます。ターゲットとイニシエーターの名前は一意です。iSCSI イニシエーターは IQN を使用します。
    1. 以下の例のように、イニシエーター名を使用して iSCSI イニシエーターの IQN を検索します。
      # cat /etc/iscsi/initiator2.iscsi
      InitiatorName=create iqn.2010-05.com.example.server1:iscsirhel7guest
      この IQN は、ACL の作成に使用されます。
    2. acls ディレクトリーに移動します。
    3. 以下のいずれかを実行して ACL を作成します。
      • パラメーターを使用せずに create コマンドを実行して、すべての LUN およびイニシエーターに対して ACL を作成します。
        # create
      • 特定の LUN およびイニシエーターに対して ACL を作成するには、以下のように iSCSI イニシエーターの IQN を指定して create コマンドを実行します。
        # create iqn.2010-05.com.example.server1:888
      • すべてのイニシエーターに 1 つのユーザー ID とパスワードを使用するよう、カーネルターゲットを設定します。
        # set auth userid=user_ID
        # set auth password=password
        # set attribute authentication=1
        # set attribute generate_node_acls=1
    この手順を完了した後、ストレージプールをセキュア化して作業を続けます。
  8. 設定の保存

    以前のブート設定を上書きして、設定を永続化します。
    # saveconfig
  9. サービスの有効化

    保存した設定を次回のブート時に適用するには、サービスを有効にします。
    # systemctl enable target.service
任意の手順
iSCSI ベースのストレージプールを作成する前に、iSCSI ターゲットを使用して実行できる任意の手順が複数あります。

手順13.6 RAID アレイ上の論理ボリュームの設定

  1. RAID5 アレイの作成

    RAID5 アレイの作成に関する情報は、『Red Hat Enterprise Linux 7 ストレージ管理ガイド』を参照してください。
  2. RAID5 アレイ上の LVM 論理ボリュームの作成

    RAID 5 アレイ上での LVM 論理ボリュームの作成に関する詳細は、『Red Hat Enterprise Linux 7 論理ボリュームマネージャーの管理』を参照してください。

手順13.7 検出可能性のテスト

  • 新規の iSCSI デバイスが検出可能であるかを確認します。

    # iscsiadm --mode discovery --type sendtargets --portal server1.example.com
    143.22.16.33:3260,1 iqn.2010-05.com.example.server1:iscsirhel7guest

手順13.8 デバイス割り当てのテスト

  1. 新規 iSCSI デバイスの割り当て

    新規デバイス (iqn.2010-05.com.example.server1:iscsirhel7guest) を割り当て、デバイスが割り当て可能であるかどうかを判別します。
    # iscsiadm -d2 -m node --login
    scsiadm: Max file limits 1024 1024
    
    Logging in to [iface: default, target: iqn.2010-05.com.example.server1:iscsirhel7guest, portal: 143.22.16.33,3260]
    Login to [iface: default, target: iqn.2010-05.com.example.server1:iscsirhel7guest, portal: 143.22.16.33,3260] successful.
  2. デバイスの接続を解除します。

    # iscsiadm -d2 -m node --logout
    scsiadm: Max file limits 1024 1024
    
    Logging out of session [sid: 2, target: iqn.2010-05.com.example.server1:iscsirhel7guest, portal: 143.22.16.33,3260
    Logout of [sid: 2, target: iqn.2010-05.com.example.server1:iscsirhel7guest, portal: 143.22.16.33,3260] successful.

手順13.9 iSCSI ストレージプールの libvert シークレットの使用

注記

この手順は、iSCSI ターゲットの作成時に user_ID および password が定義された場合に必要となります。
virsh を使ってユーザー名およびパスワードパラメーターを設定することにより、iSCSI ストレージプールのセキュリティーを保護することができます。これは、プールを定義する前後に設定できますが、認証設定を有効にするには、プールが起動している必要があります。
  1. libvirt シークレットファイルを作成します。

    以下の例のように、チャレンジハンドシェイク認証プロトコル (CHAP) のユーザー名を使用して libvirt シークレットファイルを作成します。
    <secret ephemeral='no' private='yes'>
        <description>Passphrase for the iSCSI example.com server</description>
        <usage type='iscsi'>
            <target>iscsirhel7secret</target>
        </usage>
    </secret>    
  2. シークレットの定義

    # virsh secret-define secret.xml
  3. UUID の検証

    # virsh secret-list
    UUID                                  Usage
    --------------------------------------------------------------------------------
    2d7891af-20be-4e5e-af83-190e8a922360  iscsi iscsirhel7secret
  4. シークレットの UID への割り当て

    以下のコマンドを使用して、以前の手順の出力にある UUID にシークレットを割り当てます。これにより、CHAP ユーザー名およびパスワードが libvirt によって制御されるシークレットリストに確実に記載されるようにします。
    # MYSECRET=`printf %s "password123" | base64`
    # virsh secret-set-value 2d7891af-20be-4e5e-af83-190e8a922360 $MYSECRET
  5. 認証エントリーをストレージプールに追加します。

    virsh edit を使用してストレージプールの XML ファイルの <source> エントリーを変更し、authentication typeusername、および secret usage を指定して <auth> 要素を追加します。
    例を以下に示します。
    <pool type='iscsi'>
      <name>iscsirhel7pool</name>
        <source>
           <host name='192.168.122.1'/>
           <device path='iqn.2010-05.com.example.server1:iscsirhel7guest'/>
           <auth type='chap' username='redhat'>
              <secret usage='iscsirhel7secret'/>
           </auth>
        </source>
      <target>
        <path>/dev/disk/by-path</path>
      </target>
    </pool>     

    注記

    <auth> サブ要素は、ゲスト XML の <pool> および <disk> 要素内の複数の異なる場所に存在します。<pool> の場合、<auth> は、認証が一部のプールソース (iSCSI および RBD) のプロパティーであり、プールソースの検索方法を記述しているため、<source> 要素内に指定されます。ドメインのサブ要素である <disk> の場合、iSCSI または RBD ディスクへの認証はディスクのプロパティーになります。
    さらに、ディスクの <auth> サブ要素はストレージプールのものとは異なります。
    <auth username='redhat'>
      <secret type='iscsi' usage='iscsirhel7secret'/>
    </auth>  
  6. 変更のアクティブ化

    以下の変更をアクティブにするには、ストレージプールを起動している必要があります。
    • ストレージプールをまだ起動していない場合は、「virsh でのストレージプールの作成」の手順にしたがってストレージプールを定義および起動します。
    • プールがすでに起動している場合は、以下のコマンドを実行してストレージプールを停止し、再起動します。
      # virsh pool-destroy iscsirhel7pool
      # virsh pool-start iscsirhel7pool
パラメーター
以下の表には、iSCSI ベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.5 iSCSI ベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='iscsi'>[type] iscsiiscsi: iSCSI Target
ストレージプールの名前<name>name</name>[name] name名前
ホストの名前

<source>
  <host name='hostname' />

source-host hostnameホスト名
iSCSI の IQN。

  device path="iSCSI_IQN" />
</source>

source-dev iSCSI_IQNソース IQN
ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>/dev/disk/by-path</path>
</target>

target path_to_poolターゲットパス
(任意) iSCSI イニシエーターの IQN。ACL が特定のイニシエーターへの LUN を制限する場合のみ必要です。

<initiator>
  <iqn name='initiator0' />
</initiator>

以下の注記を参照してください。イニシエーター IQN

注記

iSCSI イニシエーターの IQN を判断するには、virsh find-storage-pool-sources-as iscsi コマンドを使用します。
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、iSCSI ベースストレージプールの XML ファイルの例になります。
<pool type='iscsi'>
  <name>iSCSI_pool</name>
  <source>
    <host name='server1.example.com'/>
    <device path='iqn.2010-05.com.example.server1:iscsirhel7guest'/>
  </source>
  <target>
    <path>/dev/disk/by-path</path>
  </target>
</pool>
  
以下は、iSCSI ベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as --name iSCSI_pool --type iscsi --source-host server1.example.com --source-dev iqn.2010-05.com.example.server1:iscsirhel7guest --target /dev/disk/by-path
Pool iSCSI_pool defined
以下のイメージは、iSCSI ベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しい iSCSI ベースストレージプールの追加例

図13.8 新しい iSCSI ベースストレージプールの追加例

13.2.3.6. LVM ベースのストレージプール

推奨
以下の点に注意して LVM ベースのストレージプールを作成してください。
  • LVM ベースのストレージプールは LVM の完全な柔軟性を提供しません。
  • libvirt はシン論理ボリュームをサポートしますが、シンストレージプールの機能は提供しません。
  • LVM ベースのストレージプールはボリュームグループです。論理ボリュームマネージャーのコマンドまたは virsh コマンドを使用するとボリュームグループを作成できます。virsh インターフェースを使用してボリュームグループを管理するには、virsh コマンドを使用してボリュームグループを作成します。
    ボリュームグループに関する詳細は、Red Hat Enterprise Linux 7 論理ボリュームマネージャーの管理を参照してください。
  • LVM ベースのストレージプールは全面的なディスクパーティションを必要とします。この手順を使用して新しいパーティションおよびデバイスをアクティブ化する場合、パーティションはフォーマットされ、すべてのデータは消去されます。ホストの既存ボリュームグループ (VG) を使用する場合は、いずれのデータも消去されません。以下の手順を開始する前に、ストレージデバイスのバックアップを取っておくことが推奨されます。
    LVM ボリュームグループ作成の詳細については、Red Hat Enterprise Linux 7 論理ボリュームマネージャーの管理を参照してください。
  • 既存の VG 上に LVM ベースのストレージプールを作成する場合、pool-build コマンドを実行しないでください。
VG が準備されたことを確認したら、ストレージプールを定義 してストレージプールの作成を続行します。
パラメーター
以下の表には、LVM ベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.6 LVM ベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='logical'>[type] logicallogical: LVM Volume Group
ストレージプールの名前<name>name</name>[name] name名前
ストレージプールのデバイスへのパス

<source>
  <device path='device_path' />

source-dev device_pathソースパス
ボリュームグループの名前  <name='VG-name' />source-name VG-nameソースパス
仮想グループの形式

  <format type='lvm2' />
</source>

source-format lvm2該当なし
ターゲットパス

<target>
  <path='target-path' />
</target>

target target-pathターゲットパス

注記

論理ボリュームグループが複数のディスクパーティションで構成されている場合、複数のソースデバイスが表示されることがあります。例を以下に示します。
<source>
  <device path='/dev/sda1'/>
  <device path='/dev/sdb3'/>
  <device path='/dev/sdc2'/>
  ...
  </source> 
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、LVM ベースのストレージプールの XML ファイルの例になります。
<pool type='logical'>
  <name>guest_images_lvm</name>
  <source>
    <device path='/dev/sdc'/>
    <name>libvirt_lvm</name>
    <format type='lvm2'/>
  </source>
  <target>
    <path>/dev/libvirt_lvm</path>
  </target>
</pool>  
以下は、LVM ベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as guest_images_lvm logical --source-dev=/dev/sdc --source-name libvirt_lvm --target /dev/libvirt_lvm
Pool guest_images_lvm defined
以下のイメージは、LVM ベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しい LVM ベースのストレージプールの追加例

図13.9 新しい LVM ベースのストレージプールの追加例

13.2.3.7. NFS ベースのストレージプール

前提条件
ネットワークファイルシステム (NFS) ベースのストレージプールを作成するには、ホストマシンが使用できるよう NFS サーバーが準備済みである必要があります。NFS に関する詳細は、『Red Hat Enterprise Linux ストレージ管理ガイド』を参照してください。
NFS サーバーが適切に設定されていることを確認したら、ストレージプールを定義 してストレージプールの作成を続行します。
パラメーター
以下の表には、NFS ベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.7 NFS ベースのストレージプールのパラメーター

説明XMLpool-define-as仮想マシンマネージャー
ストレージプールの種類<pool type='netfs'>[type] netfsnetfs: Network Exported Directory
ストレージプールの名前<name>name</name>[name] name名前
マウントポイントがある NFS サーバーのホスト名。ホスト名または IP アドレスを指定できます。

<source>
  <host name='host_name' />

source-host host_nameホスト名
NFS サーバーで使用されるディレクトリー

  <dir path='source_path' />
</source>

source-path source_pathソースパス
ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>/target_path</path>
</target>

target target_pathターゲットパス
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、NFS ベースストレージプールの XML ファイルの例になります。
<pool type='netfs'>
  <name>nfspool</name>
  <source>
    <host name='localhost'/>
    <dir path='/home/net_mount'/>
  </source>
  <target>
    <path>/var/lib/libvirt/images/nfspool</path>
  </target>
</pool>  
以下は、NFS ベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as nfspool netfs --source-host localhost --source-path /home/net_mount --target /var/lib/libvirt/images/nfspool
Pool nfspool defined
以下のイメージは、NFS ベースのストレージプールを作成する、仮想マシンマネージャー の「新しいストレージプールを追加」ダイアログの仮想マシン XML 設定例になります。
新しい NFS ベースのストレージプールの追加例

図13.10 新しい NFS ベースのストレージプールの追加例

13.2.3.8. SCSI デバイスを使用した vHBA ベースのストレージプール

注記

SCSI デバイスを使用した vHBA ベースのストレージプールの作成に 仮想マシンマネージャー を使用することはできません。
推奨
N_Port ID 仮想化 (NPIV) は、1 つの物理ファイバーチャネルのホストバスアダプター (HBA) を共有できるようにするソフトウェア技術です。これにより、複数のゲストから複数物理ホストの同一ストレージを確認することが可能になり、ストレージの移行パスが容易になります。このため、適切なストレージパスが指定されていれば、移行でストレージを作成したりコピーしたりする必要がありません。
仮想化では、仮想ホストバスアダプター (vHBA) が仮想マシンの LUN (Logical Unit Number: 論理ユニット番号) を制御します。ホストが複数 KVM ゲスト間で 1 つのファイバーチャネルを共有するには、各仮想マシンに vHBA が作成される必要があります。単一の vHBA を複数の KVM ゲストで使用することはできません。
NPIV の各 vHBA は、その親 HBA および独自の World Wide Node Name (WWNN) と World Wide Port Name (WWPN) で識別されます。ストレージへのパスは、WWNN と WWPN の値で決定されます。親 HBA は、scsi_host# または WWNN/WWPN ペアで定義することができます。

注記

親 HBA を scsi_host# で定義しハードウェアがホストマシンに追加されると、scsi_host# の割り付けが変更される場合があります。したがって、親 HBA は WWNN/WWPN ペアを使って定義することが推奨されます。
vHBA 設定が保持されるため、vHBA を基にして libvirt ストレージプールを定義することが推奨されます。
libvirt ストレージプールを使用することには 2 つの主な利点があります。
  • libvirt コードにより、virsh コマンド出力から LUN のパスを簡単に特定できます。
  • 仮想マシンの移行には、ターゲットマシン上に同じ vHBA 名を持つストレージプールを定義し、起動することのみが必要になります。これを実行するには、vHBA LUN、libvirt ストレージプール、およびボリューム名を仮想マシンの XML 設定に指定する必要があります。例については、「SCSI デバイスを使用した vHBA ベースのストレージプール」 を参照してください。

注記

vHBA を作成する前に、ホスト LUN のストレージアレイ (SAN) 側のゾーン機能を設定してゲスト間を分離し、データが損傷する可能性を防ぐことをお勧めします。
vHBA の永続的な設定を作成するには、まず以下の形式を使用して libvirt 'scsi' ストレージプール XML ファイルを作成します。同一の物理 HBA 上のストレージプールを使用する単一の vHBA を作成する場合は、システム上の /dev/disk/by-{path|id|uuid|label} の場所のいずれかにするなど、<path> 値の安定した場所を使用することをお勧めします。
同一の物理 HBA 上のストレージプールを使用する複数の vHBA を使用する場合、<path> フィールドの値は /dev/ にしなければなりません。そうでないと、ストレージプールボリュームは vHBA のいずれかのみに表示され、ホストのデバイスを NPIV 設定で複数ゲストに表示することができなくなります。
<path> の詳細および <target> の要素については、アップストリームの libvirt ドキュメント を参照してください。
前提条件
SCSI デバイスで vHBA ベースのストレージプールを作成する前に、vHBA を 作成します。

手順13.10 vHBA の作成

  1. ホストシステム上で HBA を見つけます。

    ホストシステム上で HBA を見つけるには、virsh nodedev-list --cap vports コマンドを使用します。
    次の例は、vHBA をサポートする 2 つの HBA を持つホストを示しています。
    # virsh nodedev-list --cap vports
    scsi_host3
    scsi_host4
  2. HBA の詳細を確認します。

    virsh nodedev-dumpxml HBA_device コマンドを使って HBA の詳細を確認します。
    # virsh nodedev-dumpxml scsi_host3
    コマンドからの XML 出力には、<name><wwnn>、および <wwpn> フィールドの一覧が表示されます。これらのフィールドは vHBA を作成するために使用されます。<max_vports> 値は、サポートされる vHBA の最大数を示します。例を以下に示します。
    <device>
      <name>scsi_host3</name>
      <path>/sys/devices/pci0000:00/0000:00:04.0/0000:10:00.0/host3</path>
      <parent>pci_0000_10_00_0</parent>
      <capability type='scsi_host'>
        <host>3</host>
        <unique_id>0</unique_id>
        <capability type='fc_host'>
          <wwnn>20000000c9848140</wwnn>
          <wwpn>10000000c9848140</wwpn>
          <fabric_wwn>2002000573de9a81</fabric_wwn>
        </capability>
        <capability type='vport_ops'>
          <max_vports>127</max_vports>
          <vports>0</vports>
        </capability>
      </capability>
    </device>   
    この例では、<max_vports> 値は HBA 設定で使用できる 127 の仮想ポートがあることを示しています。<vports> 値は、現在使用中の仮想ポートの数を示します。これらの値は、vHBA 作成後に更新されます。
  3. vHBA ホストデバイスを作成します。

    vHBA ホスト用に以下のどちらかのような XML ファイルを作成します (この例では、ファイル名は vhba_host3.xml です)。
    この例では、親 vHBA を定義するのに scsi_host3 が使われています。
    # cat vhba_host3.xml
    <device>
      <parent>scsi_host3</parent>
      <capability type='scsi_host'>
        <capability type='fc_host'>
        </capability>
      </capability>
    </device>   
    この例では、親 vHBA を定義するのに WWNN/WWPN ペアが使われています。
    # cat vhba_host3.xml
    <device>
      <name>vhba</name>
      <parent wwnn='20000000c9848140' wwpn='10000000c9848140'/>
      <capability type='scsi_host'>
        <capability type='fc_host'>
        </capability>
      </capability>
    </device>   

    注記

    WWNN と WWPN の値は、手順13.10「vHBA の作成」 で確認した HBA 詳細の値と一致している必要があります。
    <parent> フィールドでは、この vHBA デバイスに関連付ける HBA デバイスを指定します。<device> タグ内の詳細は、ホスト用に新規の vHBA デバイスを作成するために次のステップで使用します。nodedev XML 形式についての詳細は、libvirt アップストリームページ を参照してください。
  4. vHBA ホストデバイス上で新規 vHBA を作成します。

    vhba_host3 をベースにして vHBA を作成するには、virsh nodedev-create コマンドを使用します。
    # virsh nodedev-create vhba_host3.xml
    Node device scsi_host5 created from vhba_host3.xml
  5. vHBA を確認します。

    新規 vHBA (scsi_host5) の詳細を virsh nodedev-dumpxml コマンドで確認します。
    # virsh nodedev-dumpxml scsi_host5
    <device>
      <name>scsi_host5</name>
      <path>/sys/devices/pci0000:00/0000:00:04.0/0000:10:00.0/host3/vport-3:0-0/host5</path>
      <parent>scsi_host3</parent>
      <capability type='scsi_host'>
        <host>5</host>
        <unique_id>2</unique_id>
        <capability type='fc_host'>
          <wwnn>5001a4a93526d0a1</wwnn>
          <wwpn>5001a4ace3ee047d</wwpn>
          <fabric_wwn>2002000573de9a81</fabric_wwn>
        </capability>
      </capability>
    </device>  
vHBA を検証した後、ストレージプールを定義 してストレージプールの作成を続行します。
パラメーター
以下の表には、vHBA ベースのストレージプールを作成するために、XML ファイル、virsh pool-define-as コマンド、および 仮想マシンマネージャー アプリケーションに必要なパラメーターの一覧が記載されています。

表13.8 vHBA ベースのストレージプールのパラメーター

説明XMLpool-define-as
ストレージプールの種類<pool type='scsi'>scsi
ストレージプールの名前<name>name</name>--adapter-name name
vHBA の識別子。parent 属性は任意です。

<source>
  <adapter type='fc_host'
  [parent=parent_scsi_device]
  wwnn='WWNN'
  wwpn='WWPN' />
</source>

[--adapter-parent parent]
--adapter-wwnn wwnn
--adapter-wpnn wwpn

ターゲットを指定するパス。これは、ストレージプールに使用されるパスになります。

<target>
  <path>target_path</path>
</target>

target path_to_pool

重要

<path> フィールドが /dev/ の場合、libvirt はボリュームデバイスパスの一意な短いデバイスパスを生成します (例: /dev/sdc)。そうでない場合は、物理ホストパスが使用されます (例: /dev/disk/by-path/pci-0000:10:00.0-fc-0x5006016044602198-lun-0)。一意な短いデバイスパスを使用すると、同じボリュームが複数のストレージプールによって複数のゲストに一覧表示されます。物理ホストパスが複数のゲストによって使用される場合は、デバイスの種類の重複に関する警告が発生する可能性があります。

注記

parent 属性を <adapter> フィールドで使用すると、物理 HBA の親を特定できます。そこからさまざまなパスで NPIV LUN を使用することができます。このフィールド scsi_hostNvports および max_vports 属性と組み合わされ、親の識別を完了します。parentparent_wwnnparent_wwpn、または parent_fabric_wwn 属性は、ホストの再起動後に同じ HBA が使用されることをさまざまな程度で保証します。
  • parent の指定がない場合は、libvirt は NPIV をサポートする最初の scsi_hostN アダプターを使用します。
  • parent のみが指定されていると、設定に追加の SCSI ホストアダプターが追加すると問題が発生することがあります。
  • parent_wwnn または parent_wwpn が指定されている場合、ホストの再起動後に同じ HBA が使用されます。
  • parent_fabric_wwn が使用された場合、使用された scsi_hostN に関係なく、ホストの再起動後に同じファブリックの HBA が選択されます。
virsh を使用してストレージプールを作成している場合、ストレージプールが作成されたことを確認して続行します。
以下は、vHBA ベースのストレージプールの XML ファイルの例になります。最初の例は、HBA で唯一のストレージプールを示しています。2 番目の例は、単一の vHBA を使用する複数のストレージプールの 1 つで、parent 属性を使用して SCSI ホストデバイスを識別するストレージプールを示しています。
<pool type='scsi'>
  <name>vhbapool_host3</name>
  <source>
    <adapter type='fc_host' wwnn='5001a4a93526d0a1' wwpn='5001a4ace3ee047d'/>
  </source>
  <target>
    <path>/dev/disk/by-path</path>
  </target>
</pool> 
<pool type='scsi'>
  <name>vhbapool_host3</name>
  <source>
    <adapter type='fc_host' parent='scsi_host3' wwnn='5001a4a93526d0a1' wwpn='5001a4ace3ee047d'/>
  </source>
  <target>
    <path>/dev/disk/by-path</path>
  </target>
</pool>  
以下は、vHBA ベースのストレージプールを作成するコマンドの例になります。
# virsh pool-define-as vhbapool_host3 scsi --adapter-parent scsi_host3 --adapter-wwnn 5001a4a93526d0a1 --adapter-wwpn 5001a4ace3ee047d --target /dev/disk/by-path
Pool vhbapool_host3 defined

注記

virsh コマンドは、parent_wwnnparent_wwpn、および parent_fabric_wwn を定義する方法を提供しません。
仮想マシンが vHBA LUN を使用するよう設定
vHBA のストレージプールを作成した後、vHBA LUN を仮想マシンの設定に追加する必要があります。
  1. 仮想マシンの XML に仮想マシンのディスクボリュームを作成します。
  2. <source> パラメーターで storage pool および storage volume を指定します。
例を以下に示します。
<disk type='volume' device='disk'>
  <driver name='qemu' type='raw'/>
  <source pool='vhbapool_host3' volume='unit:0:4:0'/>
  <target dev='hda' bus='ide'/>
</disk>    
disk ではなく lun デバイスを指定するには、以下の例を参照してください。
<disk type='volume' device='lun' sgio='unfiltered'>
  <driver name='qemu' type='raw'/>
  <source pool='vhbapool_host3' volume='unit:0:4:0' mode='host'/>
  <target dev='sda' bus='scsi'/>
  <shareable />
</disk>
SCSI LUN ベースのストレージをゲストに追加する際の XML 設定のサンプルについては、「SCSI LUN ベースのストレージのゲストへの追加」を参照してください。
ハードウェア故障の際に LUN への再接続を確実にするには、fast_io_fail_tmo および dev_loss_tmo オプションを編集することが推奨されます。詳細については、「ハードウェア故障後に公開されている LUN に再接続」を参照してください。

13.2.4. ストレージプールの削除

virsh コマンドまたは 仮想マシンマネージャー を使用するとストレージプールを削除できます。

13.2.4.1. ストレージプールを削除するための前提条件

削除するストレージプールを使用するその他のゲスト仮想マシンへの影響を避けるため、ストレージプールを停止し、そのストレージプールが使用するリソースを解放することが推奨されます。

13.2.4.2. virsh を使用したストレージプールの削除

  1. 定義したストレージプールを一覧で表示します。
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    guest_images_pool    active     yes
  2. 削除するストレージプールを停止します。
    # virsh pool-destroy guest_images_disk
  3. (任意): ストレージプールのタイプによっては、ストレージプールがあるディレクトリーを任意で削除することができます。
    # virsh pool-delete guest_images_disk
  4. ストレージプールの定義を削除します。
    # virsh pool-undefine guest_images_disk
  5. プールが定義されていないことを確認します。
    # virsh pool-list --all
    Name                 State      Autostart
    -----------------------------------------
    default              active     yes
    

13.2.4.3. 仮想マシンマネージャーを使用したストレージプールの削除

  1. 「接続の詳細」ウインドウ の「ストレージタブ」にあるストレージプールリストで、削除するストレージプールを選択します。
  2. 「ストレージ」ウィンドウの下部にある をクリックします。これにより、ストレージプールが停止され、ストレージプールによって使用されているリソースが解放されます。
  3. をクリックします。

    注記

    ストレージプールが停止した場合のみ アイコンが有効になります。
    ストレージプールが削除されます。

13.3. ストレージボリュームの使用

ここでは、ストレージボリュームの使用に関して説明します。概念的な情報の他に、virsh コマンドや 仮想マシンマネージャー を使用したストレージボリュームの作成、設定、および削除手順を詳しく説明します。

13.3.1. ストレージボリュームの概念

ストレージプールは ストレージボリューム に分割されます。ストレージボリュームは、物理パーティション、LVM 論理ボリューム、ファイルベースのディスクイメージ、および libvirt が対処するその他のストレージタイプを抽象化したものです。ストレージボリュームは、基盤のハードウェアに関係なく、ローカルストレージデバイスとしてゲスト仮想マシンに提供されます。

注記

ここでは、ストレージボリューの管理用に virsh が提供する可能なコマンドや引数をすべて取り上げるわけではありません。詳細は 「ストレージボリュームコマンド」 を参照してください。
ホストマシンでは、ストレージボリュームは名前と派生するストレージプールの識別子で参照されます。virsh コマンドラインでは、--pool storage_pool volume_name の形式を取ります。
たとえば、名前が firstimage というボリュームが guest_images プールにあるとします。
# virsh vol-info --pool guest_images firstimage
  Name:           firstimage
  Type:           block
  Capacity:       20.00 GB
  Allocation:     20.00 GB
追加のパラメーターおよび引数については、「ボリューム情報の一覧表示」を参照してくだい。

13.3.2. ストレージボリュームの作成

ここでは、virsh および 仮想マシンマネージャー を使用してストレージプールからストレージボリュームを作成する一般的な手順を説明します。ストレージボリュームの作成後、ストレージデバイスをゲストに追加することができます。

13.3.2.1. virsh を使用したストレージボリュームの作成

次のいずれかを行います。
  • XML ファイルを使用してストレージボリュームを定義します。
    a. 新規デバイスに必要となるストレージボリューム情報が含まれる一時 XML ファイルを作成します。
    XML ファイルには、以下を含む特定のフィールドが含まれている必要があります。
    • name: ストレージボリュームの名前。
    • allocation: ストレージボリュームのストレージ割り当ての合計。
    • capacity: ストレージボリュームの論理容量。ボリュームがスパースである場合、ボリュームが allocation の値とは異なることがあります。
    • target: ホストシステム上のストレージボリュームへのパス。任意でそのパーミッションとラベルが含まれます。
    以下はストレージボリューム定義の XML ファイルの例になります。この例では、ファイルは ~/guest_volume.xml に保存されます。
      <volume>
        <name>volume1</name>
        <allocation>0</allocation>
        <capacity>20G</capacity>
        <target>
          <path>/var/lib/virt/images/sparse.img</path>
        </target>
      </volume> 
    b. virsh vol-create コマンドを使用し、XML ファイルを基にしてストレージボリュームを作成します。
    # virsh vol-create guest_images_dir ~/guest_volume.xml
      Vol volume1 created
    c. a. で作成した XML ファイルを削除します。
  • virsh vol-create-as コマンドを使用して、ストレージボリュームを作成します。
    # virsh vol-create-as guest_images_dir volume1 20GB --allocation 0
  • virsh vol-clone コマンドを使用して既存のストレージボリュームをクローンします。virsh vol-clone コマンドには、クローンするストレージボリュームが含まれるストレージプールと、新たに作成されたストレージボリュームの名前を指定する必要があります。
    # virsh vol-clone --pool guest_images_dir volume1 clone1

13.3.2.2. 仮想マシンマネージャーでのストレージボリュームの作成

手順13.11 仮想マシンマネージャーでのストレージボリュームの作成

  1. ストレージ設定を開きます。

    1. 仮想マシンマネージャー で、編集 メニューを開き、接続の詳細 を選択します。
    2. 接続の詳細 ウインドウの ストレージ タブをクリックします。
      「ストレージ」タブ

      図13.11 「ストレージ」タブ

      接続の詳細 ウインドウの左側のペインにストレージプールの一覧が表示されます。
  2. ストレージボリュームを作成するストレージプールの選択

    ストレージプールの一覧で、ストレージボリュームを作成するストレージプールをクリックします。
    選択したストレージプールに設定されたストレージボリュームは、ウインドウの下部にある ボリューム ペインに表示されます。
  3. 新しいストレージボリュームの追加

    ボリューム リストの上にある ボタンをクリックします。ストレージボリュームを追加 ダイアログが表示されます。
    ストレージボリュームの作成

    図13.12 ストレージボリュームの作成

  4. ストレージボリュームの設定

    以下のパラメーターでストレージボリュームを設定します。
    • 名前 フィールドにストレージプールの名前を入力します。
    • フォーマット リストでストレージボリュームの形式を選択します。
    • 最大容量 フィールドにストレージボリュームの最大サイズを入力します。
  5. 作成の終了

    完了 をクリックします。ストレージボリュームを追加 ダイアログが閉じられ、ストレージボリュームが ボリューム リストに表示されます。

13.3.3. ストレージボリュームの表示

ストレージプールから複数のストレージボリュームを作成できます。virsh vol-list コマンドを使用してストレージプールのストレージボリュームを一覧表示することもできます。以下の例では、guest_images_disk に 3 つのボリュームが含まれています。
virsh vol-create-as guest_images_disk volume1 8G
Vol volume1 created

# virsh vol-create-as guest_images_disk volume2 8G
Vol volume2 created

# virsh vol-create-as guest_images_disk volume3 8G
Vol volume3 created

# virsh vol-list guest_images_disk
Name                 Path
-----------------------------------------
volume1              /home/VirtualMachines/guest_images_dir/volume1
volume2              /home/VirtualMachines/guest_images_dir/volume2
volume3              /home/VirtualMachines/guest_images_dir/volume3

13.3.4. データの管理

ここでは、ストレージボリュームでのデータの管理について説明します。

注記

ストレージボリュームのタイプによっては、すべてのデータ管理コマンドをサポートしないものがあります。特定の情報については、以下のセクションを参照してください。

13.3.4.1. ストレージボリュームのワイプ

ストレージボリュームのデータへアクセスできないようにするには、virsh vol-wipe コマンドを使用してストレージボリュームをワイプします。
virsh vol-wipe コマンドを使用してストレージボリュームをワイプします。
# virsh vol-wipe new-vol vdisk
デフォルトでは、データはゼロで上書きされます。しかし、ストレージボリュームのワイプでは指定できる方法が複数あります。virsh vol-wipe コマンドのすべてのオプションに関する詳細は、「ストレージボリュームの内容の削除」 を参照してください。

13.3.4.2. ストレージボリュームへのデータのアップロード

virsh vol-upload コマンドを使用するとデータを指定のローカルファイルからストレージボリュームにアップロードすることができます。
# virsh vol-upload --pool pool-or-uuid --offset bytes --length bytes vol-name-or-key-or-path local-file
主な virsh vol-upload のオプションは次のとおりです。
  • --pool pool-or-uuid: ボリュームが存在するストレージプールの名前または UUID。
  • vol-name-or-key-or-path : アップロードするボリュームの名前、キー、またはパス。
  • --offset bytes: データの書き込みを開始するストレージボリュームの位置。
  • --length length: アップロードするデータの容量の上限。

    注記

    local-file が指定の --length よりも大きいとエラーが発生します。

例13.1 ストレージボリュームへのデータのアップロード

# virsh vol-upload sde1 /tmp/data500m.empty disk-pool
この例では、sde1disk-pool のボリュームになります。/tmp/data500m.empty のデータは sde1 にコピーされます。

13.3.4.3. ストレージボリュームへのデータのダウンロード

virsh vol-upload コマンドを使用するとデータをストレージボリュームから指定のローカルファイルにダウンロードすることができます。
# vol-download --pool pool-or-uuid --offset bytes --length bytes vol-name-or-key-or-path local-file
主な virsh vol-download のオプションは次のとおりです。
  • --pool pool-or-uuid: ボリュームが存在するストレージプールの名前または UUID。
  • vol-name-or-key-or-path : ダウンロードするボリュームの名前、キー、またはパス。
  • --offset: データの読み取りを開始するストレージボリュームの位置。
  • --length length: ダウンロードするデータの容量の上限。

例13.2 ストレージボリュームからのデータのダウンロード

# virsh vol-download sde1 /tmp/data-sde1.tmp disk-pool
この例では、sde1disk-pool のボリュームになります。sde1 のデータは /tmp/data-sde1.tmp にダウンロードされます。

13.3.4.4. ストレージボリュームのサイズ変更

vol-resize コマンドを使用すると、指定のストレージボリュームの容量を変更できます。
# virsh vol-resize --pool pool-or-uuid vol-name-or-path pool-or-uuid capacity --allocate --delta --shrink
capacity はバイト単位です。コマンドには、ストレージボリュームがあるストレージプールの名前または UUID である --pool pool-or-uuid が必要です。また、サイズを変更するボリュームの名前、キー、またはパスである --pool pool-or-uuid も必要です。
新たな容量は、--allocate が指定されない限りスパースになります。通常、容量は新規のサイズになりますが、--delta がある場合、既存のサイズに追加されます。--shrink がない場合、ボリュームを縮小する試みは失敗します。
--shrink が指定されていない限り、capacity は負の値にならず、負の符号は不要であることに注意してください。capacity は、サフィックスがない場合、デフォルトがバイトになる単位付き整数です。また、このコマンドはアクティブなゲストによって使用されていないストレージボリュームの場合にのみ安全であることにも注意してください。ライブのサイズ変更については、「ゲスト仮想マシンのブロックデバイスのサイズ変更」 を参照してください。

例13.3 ストレージボリュームのサイズ変更

たとえば、作成した 50M のストレージボリュームのサイズを 100M に変更する場合は以下のコマンドを使用します。
# virsh vol-resize --pool disk-pool sde1 100M

13.3.5. ストレージボリュームの削除

virsh または 仮想マシンマネージャー を使用するとストレージボリュームを削除できます。

注記

削除するストレージボリュームを使用するゲスト仮想マシンへの影響を避けるため、ストレージボリュームが使用しているリソースをすべて解放することが推奨されます。

13.3.5.1. virsh を使用したストレージボリュームの削除

virsh vol-delete コマンドを使用してストレージボリュームを削除します。コマンドには、ストレージボリュームの名前またはパスと、ストレージボリュームが抽象化されるストレージプールを指定する必要があります。
以下の例は、guest_images_dir ストレージプールから volume_name ストレージボリュームを削除します。
# virsh vol-delete volume_name --pool guest_images_dir
  vol volume_name deleted

13.3.5.2. 仮想マシンマネージャーを使用したストレージボリュームの削除

手順13.12 仮想マシンマネージャーでのストレージボリュームの削除

  1. ストレージ設定を開きます。

    1. 仮想マシンマネージャー で、編集 メニューを開き、接続の詳細 を選択します。
    2. 接続の詳細 ウインドウの ストレージ タブをクリックします。
      「ストレージ」タブ

      図13.13 「ストレージ」タブ

      接続の詳細 ウインドウの左側のペインにストレージプールの一覧が表示されます。
  2. 削除するストレージボリュームを選択します。

    1. ストレージプールの一覧で、ストレージボリュームが抽象化されるストレージプールをクリックします。
      選択したストレージプールに設定されたストレージボリュームの一覧が、ウインドウの下部にある ボリューム ペインに表示されます。
    2. 削除するストレージボリュームを選択します。
  3. ストレージボリュームの削除

    1. ボリューム リストの上にある ボタンをクリックします。確認のダイアログが表示されます。
    2. はい をクリックします。選択したストレージボリュームが削除されます。

13.3.6. ストレージデバイスのゲストへの追加

virsh または 仮想マシンマネージャー を使用すると、ストレージデバイスをゲスト仮想マシンに追加できます。

13.3.6.1. virsh を使用したストレージデバイスのゲストへの追加

ストレージデバイスをゲスト仮想マシンに追加するには、attach-disk コマンドを使用します。追加するディスクに関する情報が含まれる引数は、XML ファイルまたはコマンドラインで指定できます。
以下は、ストレージの定義が含まれる XML ファイルの例になります。
<disk type='file' device='disk>'>
  <driver name='qemu' type='raw' cache='none'/>
  <source file='/var/lib/libvirt/images/FileName.img'/>
  <target dev='vdb' bus='virtio'/>
</disk> 
以下のコマンドは、NewStorage.xml という XML ファイルを使用してディスクを Guest1 に割り当てます。
# virsh attach-disk --config Guest1 ~/NewStorage.xml
以下のコマンドは、xml ファイルを使用せずに、ディスクを Guest1 に割り当てます。
# virsh attach-disk --config Guest1 --source /var/lib/libvirt/images/FileName.img --target vdb

13.3.6.2. 仮想マシンマネージャーを使用したストレージデバイスのゲストへの追加

ストレージボリュームをゲスト仮想マシンに追加したり、デフォルトのストレージデバイスをゲスト仮想マシンに作成および追加することができます。
13.3.6.2.1. ストレージボリュームのゲストへの追加
ストレージボリュームをゲスト仮想マシンに追加するには、以下を行います。
  1. 仮想マシンマネージャーの仮想マシンハードウェア詳細のウインドウを開く

    virt-manager を開くには、root で virt-manager コマンドを実行するか、または アプリケーションシステムツール仮想マシンマネージャー を開きます。
    仮想マシンマネージャーのウィンドウ

    図13.14 仮想マシンマネージャーのウィンドウ

    ストレージボリュームを追加するゲスト仮想マシンを選択します。
    開く をクリックして、仮想マシンのウインドウを開きます。
    をクリックすると、ハードウェア詳細のウインドウが表示されます。
    ハードウェア詳細のウインドウ

    図13.15 ハードウェア詳細のウインドウ

  2. 「新しいハードウェアを追加」ウインドウの表示

    ハードウェアを追加 をクリックします。「新しい仮想ハードウェアを追加」ウインドウが表示されます。
    ハードウェアタイプのペインで ストレージ が選択されていることを確認してください。
    新しい仮想ハードウェアを追加ウインドウ

    図13.16 新しい仮想ハードウェアを追加ウインドウ

  3. ストレージボリュームの一覧を表示

    カスタムストレージの選択または作成 オプションボタンを選択します。
    管理 ボタンをクリックします。ストレージボリュームの選択ダイアログが表示されます。
    「ストレージボリュームの選択」ウィンドウ

    図13.17 「ストレージボリュームの選択」ウィンドウ

  4. ストレージボリュームの選択

    「ストレージボリュームの選択」ウインドウの左側にあるリストからストレージプールを選択します。ボリューム リストに、選択したストレージプールのストレージボリュームのリストが表示されます。

    注記

    「ストレージボリュームの選択」ウインドウからストレージプールを作成できます。詳細は 「仮想マシンマネージャーでのストレージプールの作成」 を参照してください。
    ボリューム リストでストレージボリュームを選択します。

    注記

    「ストレージボリュームの選択」ウインドウからストレージボリュームを作成できます。詳細は 「仮想マシンマネージャーでのストレージボリュームの作成」 を参照してください。
    ボリュームの選択 をクリックします。「ストレージボリュームの選択」ウインドウが閉じられます。
  5. ストレージボリュームの設定

    デバイスの種類 リストでデバイスの種類を選択します。ディスクデバイス、CDROM デバイス、フロッピーデバイス、または LUN パススルーの選択が可能です。
    バスの種類 リストでバスの種類を選択します。選択が可能なバスの種類は、選択したデバイスの種類によって異なります。
    キャッシュモデル リストでキャッシュモデルを選択します。ハイパーバイザーのデフォルト、none、writethrough、writeback、directsync、または unsafe の選択が可能です。
    完了 をクリックします。「新しい仮想ハードウェアを追加」ウインドウが閉じられます。
13.3.6.2.2. デフォルトストレージのゲストへの追加
デフォルトのストレージプールは /var/lib/libvirt/images/ ディレクトリーのファイルベースイメージです。
デフォルトのストレージをゲスト仮想マシンに追加するには、以下を行います。
  1. 仮想マシンマネージャーの仮想マシンハードウェア詳細のウインドウを開く

    virt-manager を開くには、root で virt-manager コマンドを実行するか、または アプリケーションシステムツール仮想マシンマネージャー を開きます。
    仮想マシンマネージャーのウィンドウ

    図13.18 仮想マシンマネージャーのウィンドウ

    ストレージボリュームを追加するゲスト仮想マシンを選択します。
    開く をクリックして、仮想マシンのウインドウを開きます。
    をクリックすると、ハードウェア詳細のウインドウが表示されます。
    ハードウェア詳細のウインドウ

    図13.19 ハードウェア詳細のウインドウ

  2. 「新しいハードウェアを追加」ウインドウの表示

    ハードウェアを追加 をクリックします。「新しい仮想ハードウェアを追加」ウインドウが表示されます。
    ハードウェアタイプのペインで ストレージ が選択されていることを確認してください。
    新しい仮想ハードウェアを追加ウインドウ

    図13.20 新しい仮想ハードウェアを追加ウインドウ

  3. ゲスト用のディスクの作成

    仮想マシン用にディスクイメージを作成する オプションを選択してください。
    仮想マシン用にディスクイメージを作成する オプションボタンの下にあるテキストボックスに作成するディスクのサイズを入力します。
    完了 をクリックします。「新しい仮想ハードウェアを追加」ウインドウが閉じられます。

13.3.6.3. SCSI LUN ベースのストレージのゲストへの追加

ホスト SCSI LUN を完全にゲストに公開する方法は複数あります。SCSI LUN をゲストに公開すると、ゲスト上で直接 SCSI コマンドを LUN に実行できます。これは、ゲスト間で LUN を共有でき、ホスト間でファイバーチャネルストレージを共有できる便利な方法です。
SCSI LUN ベースのストレージに関する詳細は「SCSI デバイスを使用した vHBA ベースのストレージプール」を参照してください。

重要

オプションの sgio 属性は、特権のない SCSI Generical I/O (SG_IO) コマンドが device='lun' ディスクについてフィルターされるかどうかを制御します。sgio 属性は 'filtered' または 'unfiltered' として指定できますが、SG_IO ioctl コマンドを永続性保存の状態でゲスト上で渡せるようにするには 'unfiltered' に設定する必要があります。
sgio='unfiltered' の設定のほかにも、ゲスト間で LUN を共有するために <shareable> 要素を設定する必要があります。sgio 属性は、指定がない場合はデフォルトで 'filtered' に設定されます。
<disk> XML 属性 device='lun' は、以下のゲストディスク設定について有効です。
  • type='block'<source dev='/dev/disk/by-{path|id|uuid|label}'/> に対して指定します。
    <disk type='block' device='lun' sgio='unfiltered'>
    ​  <driver name='qemu' type='raw'/>
    ​  <source dev='/dev/disk/by-path/pci-0000\:04\:00.1-fc-0x203400a0b85ad1d7-lun-0'/>
    ​  <target dev='sda' bus='scsi'/>
      <shareable/>
    ​</disk>

    注記

    <source> デバイス名のコロンの前にはバックスラッシュが必要なことに注意してください。
  • type='network'<source protocol='iscsi'... /> に対して指定します。
    <disk type='network' device='lun' sgio='unfiltered'>
      <driver name='qemu' type='raw'/>
      <source protocol='iscsi' name='iqn.2013-07.com.example:iscsi-net-pool/1'>
        <host name='example.com' port='3260'/>
        <auth username='myuser'>
          <secret type='iscsi' usage='libvirtiscsi'/>
        </auth>
      </source>
      <target dev='sda' bus='scsi'/>
      <shareable/>
    </disk> 
  • type='volume' を、iSCSI または NPIV/vHBA ソースプールを SCSI ソースプールとして使用する場合に指定します。
    以下のサンプル XML は、ゲストで iSCSI ソースプール (iscsi-net-pool という名前) を SCSI ソースプールとして使用していることを示しています。
    <disk type='volume' device='lun' sgio='unfiltered'>
      <driver name='qemu' type='raw'/>
      <source pool='iscsi-net-pool' volume='unit:0:0:1' mode='host'/>
      <target dev='sda' bus='scsi'/>
      <shareable/>
    </disk> 

    注記

    <source> タグ内で mode= オプションは任意ですが、使用する場合には 'direct' ではなく 'host' に設定する必要があります。'host' に設定される場合、libvirt はローカルホスト上のデバイスへのパスを検索します。'direct' に設定される場合、libvirt はソースプールのソースホストデータを使用してデバイスへのパスを生成します。
    上記のサンプルの iSCSI プール (iscsi-net-pool) には、以下のような設定があります。
    # virsh pool-dumpxml iscsi-net-pool
    <pool type='iscsi'>
      <name>iscsi-net-pool</name>
      <capacity unit='bytes'>11274289152</capacity>
      <allocation unit='bytes'>11274289152</allocation>
      <available unit='bytes'>0</available>
      <source>
        <host name='192.168.122.1' port='3260'/>
        <device path='iqn.2013-12.com.example:iscsi-chap-netpool'/>
        <auth type='chap' username='redhat'>
          <secret usage='libvirtiscsi'/>
        </auth>
      </source>
      <target>
        <path>/dev/disk/by-path</path>
        <permissions>
          <mode>0755</mode>
        </permissions>
      </target>
    </pool> 
    iSCSI ソースプールで利用可能な LUN の詳細を確認するには、以下のコマンドを入力します。
    # virsh vol-list iscsi-net-pool
    Name                 Path
    ------------------------------------------------------------------------------
    unit:0:0:1           /dev/disk/by-path/ip-192.168.122.1:3260-iscsi-iqn.2013-12.com.example:iscsi-chap-netpool-lun-1
    unit:0:0:2           /dev/disk/by-path/ip-192.168.122.1:3260-iscsi-iqn.2013-12.com.example:iscsi-chap-netpool-lun-2
  • type='volume' を、NPIV/vHBA ソースプールを SCSI ソースプールとして使用する場合に指定します。
    以下のサンプル XML は、ゲストで NPIV/vHBA ソースプール (vhbapool_host3 という名前) を SCSI ソースプールとして使用していることを示しています。
    <disk type='volume' device='lun' sgio='unfiltered'>
      <driver name='qemu' type='raw'/>
      <source pool='vhbapool_host3' volume='unit:0:1:0'/>
      <target dev='sda' bus='scsi'/>
      <shareable/>
    </disk>  
    上記のサンプルの NPIV/vHBA プール (vhbapool_host3) には、以下のような設定があります。
    # virsh pool-dumpxml vhbapool_host3
    <pool type='scsi'>
      <name>vhbapool_host3</name>
      <capacity unit='bytes'>0</capacity>
      <allocation unit='bytes'>0</allocation>
      <available unit='bytes'>0</available>
      <source>
        <adapter type='fc_host' parent='scsi_host3' managed='yes' wwnn='5001a4a93526d0a1' wwpn='5001a4ace3ee045d'/>
      </source>
      <target>
        <path>/dev/disk/by-path</path>
        <permissions>
          <mode>0700</mode>
          <owner>0</owner>
          <group>0</group>
        </permissions>
      </target>
    </pool>  
    vHBA で利用可能な LUN の詳細を確認するには、以下のコマンドを入力します。
    # virsh vol-list vhbapool_host3
    Name                 Path
    ------------------------------------------------------------------------------
    unit:0:0:0           /dev/disk/by-path/pci-0000:10:00.0-fc-0x5006016044602198-lun-0
    unit:0:1:0           /dev/disk/by-path/pci-0000:10:00.0-fc-0x5006016844602198-lun-0
    SCSI デバイスで NPIV vHBA を使用する方法についての詳細は、「SCSI デバイスを使用した vHBA ベースのストレージプール」 を参照してください。
以下の手順は、SCSI LUN ベースのストレージデバイスをゲストに追加する例を示しています。上記の <disk device='lun'> ゲストのディスク設定のいずれもこの方法で割り当てることができます。ご使用の環境に応じて設定を置き換えてください。

手順13.13 SCSI LUN ベースのストレージのゲストへの割り当て

  1. 新しいファイルに <disk> 要素を書き込むことによってデバイスファイルを作成し、このファイルを XML 拡張子を付けて保存します (例: sda.xml)。
    # cat sda.xml
    <disk type='volume' device='lun' sgio='unfiltered'>
      <driver name='qemu' type='raw'/>
      <source pool='vhbapool_host3' volume='unit:0:1:0'/>
      <target dev='sda' bus='scsi'/>
      <shareable/>
    </disk>  
  2. sda.xml で作成したデバイスをゲスト仮想マシン (例: Guest1) に関連付けます。
    # virsh attach-device --config Guest1 ~/sda.xml

    注記

    virsh attach-device コマンドを --config オプションを指定して実行するには、デバイスをゲストに永続的に追加するためにゲストを再起動する必要があります。または、--persistent オプションを --config の代わりに使用することができます。これを、デバイスをゲストにホットプラグするために使用することもできます。
別の方法として、SCSI LUN ベースのストレージを virt-manager を使用してゲスト上で割り当てるか、または設定することができます。virt-manager を使用してこれを設定するには、ハードウェアを追加 ボタンをクリックして、必要なパラメーターと共に仮想ディスクを追加するか、またはこのウィンドウから既存の SCSI LUN デバイスの設定を変更します。Red Hat Enterprise Linux 7.2 以降では、SGIO の値も virt-manager で設定できます。
virt-manager を使用した SCSI LUN ストレージの設定

図13.21 virt-manager を使用した SCSI LUN ストレージの設定

ハードウェア故障後に公開されている LUN に再接続

ハードウェア (ホストのバスアダプター等) の故障により公開されているファイバーチャネル (FC) LUN への接続が失われた場合、ハードウェアの故障が修復された後でも、ゲストの公開されている LUN は故障したままのように見えることがあります。これを防ぐためには、dev_loss_tmo および fast_io_fail_tmo カーネルオプションを編集します。
  • dev_loss_tmo は、SCSI デバイスが故障してから SCSI レイヤーが故障と識別するまでの時間をコントロールします。タイムアウトを防ぐには、オプションを最大値の 2147483647 に設定することをお勧めします。
  • fast_io_fail_tmo は、SCSI デバイスが故障してから SCSI レイヤーが I/O にフェイルバックするまでの時間をコントロールします。dev_loss_tmo がカーネルによって無視されないようにするには、このオプションの値を dev_loss_tmo の値より小さい数値に設定します。
dev_loss_tmo および fast_io_fail の値を変更するには、以下に示すどちらかの操作を行います。
  • /etc/multipath.conf ファイルを編集し、defaults セクションの値を設定する。
    defaults {
    ...
    fast_io_fail_tmo     20
    dev_loss_tmo    infinity
    }
  • FC ホストまたはリモートポートのレベルで dev_loss_tmo および fast_io_fail を設定する。例を以下に示します。
    # echo 20 > /sys/devices/pci0000:00/0000:00:06.0/0000:13:00.0/host1/rport-1:0-0/fc_remote_ports/rport-1:0-0/fast_io_fail_tmo
    # echo 2147483647 > /sys/devices/pci0000:00/0000:00:06.0/0000:13:00.0/host1/rport-1:0-0/fc_remote_ports/rport-1:0-0/dev_loss_tmo
新しい dev_loss_tmo および fast_io_fail の値が有効であることを確認するには、以下のコマンドを使います。
# find /sys -name dev_loss_tmo -print -exec cat {} \;
パラメーターが正しく設定されていれば、出力は次のようになります (ただし、pci0000:00/0000:00:06.0/0000:13:00.0/host1/rport-1:0-0/fc_remote_ports/rport-1:0-0 には実際のデバイスが表示されます)。
# find /sys -name dev_loss_tmo -print -exec cat {} \;
...
/sys/devices/pci0000:00/0000:00:06.0/0000:13:00.0/host1/rport-1:0-0/fc_remote_ports/rport-1:0-0/dev_loss_tmo
2147483647
...

13.3.6.4. ゲスト仮想マシンのストレージコントローラーの管理

virtio ディスクとは異なり、SCSI デバイスでは、コントローラーがゲスト仮想マシンに存在する必要があります。このセクションでは、仮想 SCSI コントローラー (「ホストバスアダプター」または HBA とも知られる) を作成し、SCSI ストレージをゲスト仮想マシンに追加するための必要なステップを詳しく説明します。

手順13.14 仮想 SCSI コントローラーの作成

  1. ゲスト仮想マシン (Guest1) の設定を表示して、すでに存在している SCSI コントローラーを探します。
    virsh dumpxml Guest1 | grep controller.*scsi
    デバイスコントローラーが存在する場合は、このコマンドは以下のように 1 つ以上の行を出力します。
    <controller type='scsi' model='virtio-scsi' index='0'/>
  2. 直前のステップでデバイスコントローラーが表示されない場合、新しいファイルでその 1 つを記述し、以下のステップを実行してそれを仮想マシンに追加します。
    1. 新しいファイルに <controller> 要素を書き込むことによってデバイスコントローラーを作成し、このファイルを XML 拡張子を付けて保存します。たとえば、NewHBA.xml のようになります。
      <controller type='scsi' model='virtio-scsi'/>
    2. virtio-scsi-controller.xml で作成したばかりのデバイスコントローラーを使用中のゲスト仮想マシン (例: Guest1) に関連付けます。
      virsh attach-device --config Guest1 ~/virtio-scsi-controller.xml
      この例では、--config オプションの挙動はディスクに対する挙動と同じです。詳細は 「ストレージデバイスのゲストへの追加」 を参照してください。
  3. 新しい SCSI ディスクまたは CD-ROM を追加します。新しいディスクは、「ストレージデバイスのゲストへの追加」 のやり方を使用して追加できます。SCSI ディスクを作成するには、sd で始まる目的のデバイス名を指定します。

    注記

    各コントローラーでサポートされる virtio-scsi ディスクの上限は 1024 個ですが、これよりも少ない数のディスクによってホストで利用できる他のリソース (ファイル記述子など) を使い果たしてしまう可能性があります。
    詳細については、Red Hat Enterprise Linux 6 ホワイトペーパー The next-generation storage interface for the Red Hat Enterprise Linux Kernel Virtual Machine: virtio-scsi を参照してください。
    virsh attach-disk Guest1 /var/lib/libvirt/images/FileName.img sdb --cache none
    ゲスト仮想マシン内のドライバーのバージョンによっては、実行中のゲスト仮想マシンを実行しても、新しいディスクをすぐには検出できない場合があります。『Red Hat Enterprise Linux 7 ストレージ管理ガイド』のステップに従ってください。

13.3.7. ゲストからのストレージデバイスの削除

virsh または 仮想マシンマネージャー を使用すると、ストレージデバイスをゲスト仮想マシンから削除することができます。

13.3.7.1. virsh で仮想マシンからストレージを削除

以下の例は vdb ストレージボリュームを Guest1 仮想マシンから削除します。
# virsh detach-disk Guest1 vdb

13.3.7.2. 仮想マシンマネージャーで仮想マシンからストレージを削除

手順13.15 仮想マシンマネージャーで仮想マシンからストレージを削除

仮想マシンマネージャー を使用してゲスト仮想マシンからストレージを削除するには、以下を行います。
  1. 仮想マシンマネージャーの仮想マシンハードウェア詳細のウインドウを開く

    virt-manager を開くには、root で virt-manager コマンドを実行するか、または アプリケーションシステムツール仮想マシンマネージャー を開きます。
    ストレージデバイスを削除するゲスト仮想マシンを選択します。
    開く をクリックして、仮想マシンのウインドウを開きます。
    をクリックすると、ハードウェア詳細のウインドウが表示されます。
  2. ゲスト仮想マシンからストレージを削除

    ハードウェア詳細のペインの左側にあるハードウェアのリストでストレージデバイスを選択します。
    削除 をクリックします。確認ダイアログが表示されます。
    はい をクリックします。ストレージがゲスト仮想マシンから削除されます。

第14章 qemu-img の使用

qemu-img は、KVM によって使用される各種ファイルシステムのフォーマット、変更、および検証を行うために使用するコマンドラインツールです。qemu-img のオプションとその使い方を以下に示します。

警告

実行中の仮想マシンまたはその他のプロセスで使用中のイメージを修正するために qemu-img を使用しないでください。使用するとイメージが破損することがあります。また、別のプロセスが修正しているイメージをクエリーすると不整合な状態が発生する可能性があります。

14.1. ディスクイメージの検査

ファイル名が imgname のディスクイメージで整合性チェックを行います。
# qemu-img check [-f format] imgname

注記

一部の形式のみが整合性チェックに対応しています。対応する形式には、qcow2vdivhdx、および vmdk が含まれます。

14.2. 変更のイメージへのコミット

qemu-img commit コマンドを使用して、指定のイメージファイル (imgname) に記録された変更をファイルのベースイメージにコミットします。任意で、ファイルの形式 (fmt) を指定します。
 # qemu-img commit [-f fmt] [-t cache] imgname

14.3. イメージの比較

qemu-img compare コマンドで、指定された 2 つのイメージファイル (imgname1imgname2) の内容を比較します。任意で、ファイルの形式 (fmt) を指定します。イメージには異なる形式や設定を指定できます。
デフォルトでは、サイズの異なるイメージは、大きい方のイメージにもう一方のイメージが含まれ、その最後の領域の後に未割り当てまたはゼロに設定されたされたセクターのみが含まれる場合に同じであると見なされます。さらに、1 つのイメージに割り当てられたイメージがなく、もう一方にゼロバイトのみが含まれる場合も同じであると評価されます。-s オプションを指定すると、イメージのサイズが異なったり、1 つのイメージに割り当てられたセクターがもう一方のイメージに割り当てられていない場合は同一であると見なされません。
 # qemu-img compare [-f fmt] [-F fmt] [-p] [-s] [-q] imgname1 imgname2
qemu-img compare コマンドは、以下の終了コードのいずれかを出力して終了します。
  • 0 - イメージは同じです。
  • 1 - イメージは異なります。
  • 2 - イメージの 1 つを開くときにエラーが発生しました。
  • 3 - セクター割り当ての確認時にエラーが発生しました。
  • 4 - データの読み取り時にエラーが発生しました。

14.4. イメージのマッピング

qemu-img map コマンドを使用すると、指定されたイメージファイル (imgname) とそのバッキングファイルチェーンのメタデータをダンプできます。ダンプにより、imgname の各セクターの割り当て状態が、バッキングファイルチェーンでそれを割り当てる最上位のファイルとともに表示されます。任意で、ファイルの形式 (fmt) を指定します。
 # qemu-img map [-f fmt] [--output=fmt] imgname
human 形式と json 形式の 2 つの出力形式があります。

14.4.1. human 形式

デフォルト形式 (human) は、ファイルのゼロが設定されていない割り当て済みの部分のみをダンプします。データの読み取り可能な場所と、ファイルのオフセットから出力はファイルを識別します。各行には 4 つのフィールドが含まれます。以下は出力の例になります。
Offset          Length          Mapped to       File
0               0x20000         0x50000         /tmp/overlay.qcow2
0x100000        0x10000         0x95380000      /tmp/backing.qcow2
最初の行は、イメージのオフセット 0 で開始する 0x20000 (131072) バイトが、オフセット 0x50000 (327680) で開始する tmp/overlay.qcow2 (raw 形式で開かれた) で利用可能であることを意味します。human 形式が指定されている場合は、圧縮または暗号化されたデータ、または raw 形式で利用できないデータが原因でエラーが発生します。

注記

ファイル名には改行文字が含まれる場合があります。そのため、スクリプト内で human 形式の出力を解析するのは安全ではありません。

14.4.2. json 形式

json オプションが指定されている場合、出力は JSON 形式の辞書の配列を返します。出力には、human オプションで提供された情報のほかに、以下の情報が含まれます。
  • data - セクターにデータが含まれるかどうかを示すブール値のフィールド。
  • zero: データがゼロとして読み取られると認識されているかどうかを示すブール値のフィールド。
  • depth - filename の曝気イングファイルの深さ。

注記

json オプションが指定された場合、offset フィールドは任意です。
qemu-img map コマンドおよび追加オプションについての詳細は、関連の man ページを参照してください。

14.5. イメージの変更

イメージファイルのイメージ形式に固有のオプションを変更します。任意で、ファイルの形式 (fmt) を指定します。
# qemu-img amend [-p] [-f fmt] [-t cache] -o options filename

注記

この操作は qcow2 ファイル形式でのみサポートされます。

14.6. 既存イメージの別形式への変換

convert オプションは、認識されたイメージの形式を別のイメージ形式に変換するために使用されます。許可される形式の一覧は 「qemu-img でサポートされる形式」 を参照してください。
# qemu-img convert [-c] [-p] [-f fmt] [-t cache] [-O output_fmt] [-o options] [-S sparse_size] filename output_filename
-p パラメーターは、コマンドの進捗を表示し (オプションのため、すべてのコマンドに使用できる訳ではありません)、-S フラグは、ディスクイメージ内に含まれる スパースファイル の作成を可能にします。スパースファイルは実際、ゼロ (0) のみを含む (つまり何も含まない) 物理ブロックの場合を除き、標準ファイルのように機能します。オペレーティングシステムがこのファイルを発見すると、いずれのディスク領域も使用していないものの、実際に存在し、実際のディスク領域を占めるものとしてこのファイルを処理します。これは、ディスクの使用領域が実際よりも多く表示されるため、ゲスト仮想マシンのディスクを作成する際にはとりわけ役に立ちます。たとえば、10Gb のディスクイメージで -S を 50Gb に設定する場合、実際に使用されているのは 10Gb のみであるのにもかかわらず、10Gb のディスク領域のサイズが 60Gb のように表示されます。
filename 形式を使って、 output_filename ディスクイメージをoutput_format ディスクイメージに変換します。-c オプションを使うとディスクイメージをオプションで圧縮することができます。また、-o オプションを使って -o encryption のように設定すると暗号化することができます。-o パラメーターと共に使用できるオプションは複数あり、これらは選択する形式によって異なる点に注意してください。
qcow2 および qcow2 形式のみが暗号化および圧縮に対応しています。qcow2 暗号化はセキュアな 128 ビットキーで AES 形式を使用します。qcow2 圧縮は読み取り専用であるため、圧縮されたセクターが qcow2 形式から変換されると、非圧縮データとして新しい形式に書き込まれます。
qcowcow などのサイズが大きくなる可能性のある形式を使用する場合、イメージの変換はイメージのサイズを小さくできるため便利です。空のセクターは検出され、変換後のイメージから削除されます。

14.7. 新規イメージまたはデバイスの作成およびフォーマット

サイズが filename、 形式が size となる format という新しいディスクイメージを作成します。
# qemu-img create [-f format] [-o options] filename [size]
-o backing_file=filename でベースイメージを指定すると、イメージは、それ自体とベースイメージとの相違部分のみを記録します。commit コマンドを使用しない限りバッキングファイルは変更されません。この場合、サイズを指定する必要はありません。

14.8. イメージ情報の表示

info パラメーターはディスクイメージ filename に関する情報を表示します。info オプションの形式は次のとおりです。
# qemu-img info [-f format] filename
このコマンドはディスク上で予約されているサイズを検出する場合によく使用され、予約サイズは表示サイズとは異なる場合があります。スナップショットがディスクイメージに格納されている場合は、それらも表示されます。たとえば、このコマンドはブロックデバイス上の qcow2 イメージが使用している領域のサイズを表示します。これは、qemu-img を実行して確認できます。使用中のイメージが qemu-img info コマンドと qemu-img check コマンドの出力に一致するものであることを確認できます。
# qemu-img info /dev/vg-90.100-sluo/lv-90-100-sluo
image: /dev/vg-90.100-sluo/lv-90-100-sluo
file format: qcow2
virtual size: 20G (21474836480 bytes)
disk size: 0
cluster_size: 65536

14.9. イメージのバッキングファイルの再設定

qemu-img rebase はイメージのバッキングファイルを変更します。
# qemu-img rebase [-f fmt] [-t cache] [-p] [-u] -b backing_file [-F backing_fmt] filename
バッキングファイルは backing_file に変更され、filename の形式が機能をサポートする場合は、バッキングファイルの形式が backing_format に変更されます。

注記

バッキングファイルの変更 (リベース) に対応するのは qcow2 形式のみになります。
rebase を操作できる 2 つのモードは safeunsafe です。
デフォルトでは safe モードが使用され、実際のリベースの操作が実行されます。新しいバッキングファイルは古いバッキングファイルとは異なる可能性があり、qemu-img rebase コマンドはゲスト仮想マシンが認識できる filename のコンテンツが変更されないようにします。backing_filefilename の古いバッキングファイル間で異なるクラスターは、バッキングファイルに変更が加えられる前に filename にマージされます。
safe モードはイメージの変換と同様に、コストの高い操作になります。正常に完了するには古いバッキングファイルが必要になります。
qemu-img rebase-u オプションを渡すと unsafe モードが使用されます。このモードでは、filename のバッキングファイル名と形式のみが変更され、ファイルの内容に対するチェックは行われません。新しいバッキングファイルを正しく指定したことを必ず確認してください。誤って指定すると、ゲストが認識できるイメージのコンテンツが破損します。
このモードはバッキングファイルの名前変更や移動を行う際に便利です。これを実行する際に、古いバッキングファイルへのアクセスは不要になります。たとえばこのモードは、バッキングファイルがすでに移動または名前変更されているイメージの修正を行う場合に使用できます。

14.10. ディスクイメージのサイズ変更

sizeというサイズで作成されたとしてディスクイメージ filename を変更します。サイズを拡大および縮小できるのは raw 形式のイメージのみになります。qcow2 バージョン 2 または qcow2 バージョン 3 イメージは拡張することはできますが、縮小することはできません。
以下を実行して、ディスクイメージ filename のサイズを size バイトに設定します。
# qemu-img resize filename size
ディスクイメージの現在のサイズを基準としてサイズを変更することもできます。ディスクイメージの現在のサイズを基準としてサイズを相対的に増やす場合は +、減らす場合は - をバイト数の前に追加します。単位の接尾辞を付けると、キロバイト (K)、メガバイト (M)、ギガバイト (G)、またはテラバイト (T) などの単位でイメージサイズを設定することができます。
# qemu-img resize filename [+|-]size[K|M|G|T]

警告

このコマンドを使ってディスクイメージを小さくする前に、仮想マシン自体のファイルシステムとパーティション設定のツールを使用し、割り当てられているファイルシステムとパーティションのサイズをそれぞれ小さくしておく必要があります。そうしないと、データを損失します。
このコマンドを使ってディスクイメージを大きくしたら、仮想マシン自体のファイルシステムとパーティション設定のツールを使用し、そのデバイス上で新しい領域を実際に使用し始める必要があります。

14.11. スナップショットの一覧表示、作成、適用および削除

qemu-img snapshot コマンドで異なるパラメーターを使用すると、指定イメージ (filename) の既存のスナップショット (snapshot) をリスト、適用、作成、または削除できます。
# qemu-img snapshot [ -l | -a snapshot | -c snapshot | -d snapshot ] filename
許可される引数は以下のようになります。
  • -l は、指定されたディスクイメージに関連付けられたすべてのスナップショットを一覧表示します。
  • apply オプション -a は、ディスクイメージ (filename) を以前保存した snapshot の状態に戻します。
  • -c はイメージ (filename) のスナップショット (snapshot) を作成します。
  • -d は指定されたスナップショットを削除します。

14.12. qemu-img でサポートされる形式

形式が qemu-img コマンドのいずれかで指定される場合、以下の形式を使用できます。
  • raw - raw ディスクイメージ形式 (デフォルト) です。最も高速なファイルベースの形式です。ファイルシステムがホール (未割り当てのブロック) に対応している場合 (ext2 や ext3 など)、書き込みが行われたセクターのみに領域が予約されます。イメージが使用している実際のサイズを取得する場合は qemu-img info を使用し、Unix/Linux では ls -lsを使用します。raw イメージでは最良のパフォーマンスを得ることができますが、利用できる機能は非常に基本的なものに限られます。たとえば、スナップショットは利用できません。
  • qcow2 - QEMU イメージ形式です。最も多目的で機能が充実した形式です。AES 暗号化、zlib ベースの圧縮、仮想マシンの複数のスナップショットに対するサポート、イメージを小さくするなどのオプションを指定する場合に使用します。これらのオプションは、ホール (未割り当てのブロック) に対応していないファイルシステムで役に立ちます。機能が充実している分、パフォーマンスは低下します。
    ゲスト仮想マシンまたはホスト物理マシンでは、上記の形式のみを使用できますが、qemu-imgraw または qcow2 形式のいずれかに変換するために以下の形式を認識し、サポートします。イメージの形式は通常自動的に検出されます。これらの形式を raw または qcow2 に変換することに加え、それらを raw または qcow2 から変換前の形式に戻すこともできます。Red Hat Enterprise Linux 7 と共に提供される qcow2 バージョンは 1.1 であることに注意してください。以前のバージョンの Red Hat Enterprise Linux と共に提供される形式は 0.10 です。イメージファイルを以前のバージョンの qcow2 に戻すことができます。使用しているバージョンを確認するには、qemu-img info qcow2 [imagefilename.img] コマンドを実行します。qcow バージョンを変更する場合は 「target 要素の設定」 を参照してください。
  • bochs: Bochs ディスクイメージ形式。
  • cloop: Linux 圧縮ループ (Linux Compressed Loop) のイメージです。Knoppix CD-ROM などにある圧縮された CD-ROM イメージを直接再利用する場合にのみ役立ちます。
  • cow: ユーザーモード Lunux コピーオンライト (User Mode Linux Copy On Write) のイメージ形式です。cow は、旧バージョンとの互換性を維持するために含まれています。
  • dmg: Mac のディスクイメージ形式。
  • nbd: ネットワークブロックデバイス。
  • parallels: Parallels の仮想化ディスクイメージ形式。
  • qcow: 旧式の QEMU イメージ形式です。この形式は、旧式バージョンとの互換性を維持するために含まれています。
  • qed: 旧式の QEMU イメージ形式です。この形式は、旧式バージョンとの互換性を維持するために含まれています。
  • vdi: Oracle 仮想マシンの VirtualBox (Oracle VM VirtualBox) のハードディスクイメージ形式です。
  • vhdx: Microsoft Hyper-V 仮想ハードディスク X ディスクイメージ形式です。
  • vmdk: VMware 3 および 4 互換のイメージ形式です。
  • vvfat: 仮想 VFAT ディスクイメージ形式。

第15章 KVM の移行

本章では、KVM ハイパーバイザーを実行するあるホスト物理マシンの別のマシンへのゲスト仮想マシンの移行について説明します。仮想マシンはハードウェア上で直接実行されるのではなく仮想化環境で実行されるため、ゲストを移行することができます。

15.1. 移行の定義と利点

ゲスト仮想マシンのメモリーと仮想化されたデバイスの状態を移行先のホスト物理マシンに送信することで移行が行われます。移行するゲスト仮想マシンのイメージは、ネットワーク接続されている共有ストレージに格納することをお勧めします。また、仮想マシンを移行する際の共有ストレージには libvirt 管理のストレージプールを使用することをお勧めします。
移行は、ライブ (稼働した状態) およびライブ以外 (シャットダウンした状態) のゲストで行うことができます。
ライブマイグレーションでは、ゲスト仮想マシンを移行元のホストマシン上で稼働させたままそのメモリーページを移行先ホスト物理マシンに転送します。移行時に、KVM はすでに転送されたページに変更がないか移行元を監視し、最初のページがすべて転送されるとこれらの検出した変更の転送を開始します。また、KVM は移行時の転送速度を推定できるため、データ残量の転送時間が一定の設定時間になると (デフォルトでは 10 ミリ秒)、元のゲスト仮想マシンを停止してから残りのデータを転送し、移行先ホスト物理マシンでその同じゲスト仮想マシンを再開します。
一方、ライブ以外の移行 (オフラインの移行) の場合には、ゲスト仮想マシンを一時停止してからゲスト仮想マシンのメモリーを移行先ホスト物理マシンにコピーします。その後、ゲストは移行先ホスト物理マシンで再開し、移行元のホスト物理マシンでゲストが使用していたメモリーを解放します。この移行が完了するまでに要する時間はネットワークの帯域幅および待ち時間によって異なります。ネットワークが混雑している場合や帯域幅が狭い場合は、移行にかかる時間も長くなります。元のゲスト仮想マシンがページを変更する速度の方が KVM が移行先ホスト物理マシンに送信する速度よりも速い場合は、ライブマイグレーションでは永久に完了しなくなる可能性があるため、オフラインの移行を使用する必要があります。
移行は以下の点で役立ちます。
負荷分散
負荷分散: ホストマシンに負荷がかかりすぎた場合に使用率の低いホスト物理マシンにゲスト仮想マシンを移動したり、別のホストマシンの使用率が低くなっている場合にそちらにゲスト仮想マシンを移動することができます。
ハードウェアの非依存性
ホスト物理マシン上のハードウェアデバイスのアップグレード、追加または削除などを行う必要がある場合、ゲスト仮想マシン群を他のホスト物理マシンに安全に移動することができます。つまり、ゲスト仮想マシンはハードウェアを改善する際に生じ得るダウンタイムを経験することはありません。
省エネ
仮想マシンを他のホスト物理マシンに再配分することで、アンロードされたホストシステムの電源を電力使用量の少ない時間帯にオフにして節電とコスト削減が可能になります。
地理的な移行
待ち時間の短縮や他の特別な状況のために、仮想マシンを別の場所に移動することができます。

15.2. 移行の要件と制限事項

KVM 移行を使用する前に、システムが移行の要件を満たしていることを確認し、その制限事項について理解しておく必要があります。

移行の要件

  • 次のいずれかのプロトコルを使用してゲスト仮想マシンを共有ストレージにインストールする場合:
    • ファイバーチャネルベースの LUN
    • iSCSI
    • NFS
    • GFS2
    • SCSI RDMA プロトコル (SCSI RCP): Infiniband および 10GbE iWARP アダプターで使用されているブロックエクスポートプロトコル
  • libvirtd サービスが有効で実行されていることを確認してください。
    # systemctl enable libvirtd.service
    # systemctl restart libvirtd.service
  • 効果的に移行を実行できるかどうかは、/etc/libvirt/libvirtd.conf ファイルのパラメーターの設定によります。このファイルを設定するには、次の手順にしたがいます。

    手順15.1 libvirtd.conf の設定

    1. libvirtd.conf を開くには、root としてコマンドを実行する必要があります。
      # vim /etc/libvirt/libvirtd.conf
    2. 必要に応じてパラメーターを変更し、ファイルを保存します。
    3. libvirtd サービスを再起動します。
      # systemctl restart libvirtd
  • 移行のプラットフォームとバージョンを 表15.1「ライブマイグレーションの互換性」 と照らし合わせてチェックする必要があります。
  • 共有ストレージメディアをエクスポートする別のシステムを使用します。ストレージは、移行に使用する 2 つのホスト物理マシンのいずれにもないことを確認してください。
  • 共有ストレージは、移行元システムと移行先システムの同じ場所にマウントします。マウントするディレクトリーの名前も同一にする必要があります。異なるパスでイメージを維持することは可能ですが、推奨されていません。virt-manager を使って移行する場合、パス名は同一である必要があります。ただし、virsh を使って移行する場合は、移行の際に --xml オプションや pre-hooks を使うと異なるネットワーク設定やマウントディレクトリーを使用することができます。pre-hooks の詳細については、libvirt のアップストリームのドキュメントを参照してください。XML オプションの詳細は 23章ドメイン XML の操作 を参照してください。
  • bridge+tap のパブリックネットワーク内の既存のゲスト仮想マシンで移行を行う場合、移行元ホストマシンと移行先ホストマシンは同じネットワーク内になければなりません。ネットワークが異なると、ゲスト仮想マシンのネットワークが移行後に機能しなくなります。

移行の制限

  • ゲスト仮想マシンの移行には、KVM に基づく仮想化技術を使って Red Hat Enterprise Linux 上で使用する場合に以下の制限が適用されます。
    • ポイントツーポイントの移行 – 移行元のハイパーバイザーから移行先ハイパーバイザーを指定するために手動で実行する必要があります。
    • 検証またはロールバックは利用できません。
    • ターゲットは手動でのみ定義できます。
    • Red Hat Enterprise Linux 7 ではストレージのライブマイグレーションは実行できませんが、ゲスト仮想マシンの電源がオフの時にストレージを移行することができます。ストレージのライブマイグレーション機能は Red Hat Virtualization で利用できます。詳細は、サービス担当者にお問い合わせください。

注記

virtio デバイスが搭載されているゲストマシンを移行する場合は、いずれかのプラットフォームの virtio デバイスのベクター番号を 32 以下に設定します。詳細は、「デバイス」 を参照してください。

15.3. ライブマイグレーションと Red Hat Enterprise Linux バージョンの互換性

ライブマイグレーションは 表15.1「ライブマイグレーションの互換性」 のとおりにサポートされます。

表15.1 ライブマイグレーションの互換性

移行の方法リリースタイプライブマイグレーション対応の有無注記
前方メジャーリリース6.5+ → 7.x完全サポート問題がある場合はご報告ください。
後方メジャーリリース7.x → 6.yサポートなし
前方マイナーリリース7.x → 7.y (7.0 → 7.1)完全サポート問題がある場合はご報告ください。
後方マイナーリリース7.y → 7.x (7.1 → 7.0)完全サポート問題がある場合はご報告ください。

移行に関するトラブルシューティング

  • 移行プロトコルに関する問題: 後方移行の実行時に「unknown section error」メッセージが表示される場合、これは一時的なエラーの可能性があるため移行プロセスを繰り返すことで 問題を修復することができるはずです。解決されない場合には問題の報告をお願いします。
  • オーディオデバイスに関する問題: Red Hat Enterprise Linux 6.x から Red Hat Enterprise Linux 7.y への移行の際に、es1370 オーディオカードはサポートされなくなったことに注意してください。ac97 オーディオカードを代わりに使用してください。
  • ネットワークカードに関する問題: Red Hat Enterprise Linux 6.x から Red Hat Enterprise Linux 7.y への移行の際に、pcnet と ne2k_pci のネットワークカードはサポートされなくなったことに注意してください。virtio-net ネットワークデバイスを代わりに使用してください。
ネットワークストレージの設定

共有ストレージを設定してその共有ストレージにゲスト仮想マシンをインストールします。

または、「共有ストレージの例: 単純な移行に NFS を使用する」 の NFS の例を使用します。

15.4. 共有ストレージの例: 単純な移行に NFS を使用する

重要

この例では、NFS を使ってゲスト仮想マシンのイメージを他の KVM ホスト物理マシンと共有します。これは大規模なインストールには実際的な方法ではありませんが、ここでは移行の手法を説明する目的で紹介します。2 台または 3 台を超えるゲスト仮想マシンを移行し、実行する場合には、この例を適用しないでください。また、synch パラメーターが有効にされている必要があります。これは、NFS ストレージを適切にエクスポートするのに必要です。
大規模な導入には iSCSI ストレージを選択するのが良いでしょう。設定の詳細については、「iSCSI ベースのストレージプール」 を参照してください。
NFS を設定し、IP テーブルを開き、ファイアウォールを設定する方法についての詳細は、『Red Hat Linux 7 ストレージ管理ガイド』を参照してください。
NFS ファイルロック機能は KVM ではサポートされていないため使用しないでください。
  1. libvirt イメージディレクトリーをエクスポートします。

    移行を行う場合、移行対象となるシステムとは別のシステムにストレージを置かなければなりません。/etc/exports ファイルにデフォルトのイメージディレクトリーを追加することで、この別のシステム上にストレージをエクスポートします。
    /var/lib/libvirt/images *.example.com(rw,no_root_squash,sync)
    環境に応じて hostname パラメーターを変更します。
  2. NFS を起動します。

    1. NFS パッケージがまだインストールされていない場合はインストールを行います。
      # yum install nfs-utils
    2. NFS のポートが iptables で開かれていることを確認します (例: 2049)。さらに、NFS を /etc/hosts.allow ファイルに追加します。
    3. NFS サービスを起動します。
      # systemctl start nfs-server
  3. ソースおよび移行先に共有ストレージをマウントします。

    移行元および移行先システムに /var/lib/libvirt/images ディレクトリーをマウントします。
    # mount storage_host:/var/lib/libvirt/images /var/lib/libvirt/images

    警告

    移行元のホスト物理マシンに選択されるディレクトリーは、移行先ホスト物理マシン上のディレクトリーと全く同一である必要があります。これは、共有ストレージのすべてのタイプに適用されます。ディレクトリーが同一でない場合、virt-manager を使用する移行は失敗します。

15.5. virsh を使用した KVM のライブマイグレーション

ゲスト仮想マシンは virsh コマンドで別のホスト物理マシンに移行することができます。migrate コマンドは以下の形式のパラメーターを受け入れます。
# virsh migrate --live GuestName DestinationURL
ライブマイグレーションが不要な場合は、--live オプションは省略しても構いません。その他のオプションは 「virsh migrate コマンドの追加オプション」 に記載されています。
GuestName パラメーターは移行するゲスト仮想マシンの名前を表します。
DestinationURL パラメーターは移行先ホスト物理マシンの接続 URL です。移行先システムも Red Hat Enterprise Linux の同じバージョンを実行し、同じハイパーバイザーを使用して libvirt を実行している必要があります。

注記

通常の移行とピアツーピアの移行では、DestinationURL パラメーターは異なる意味になります。
  • 通常の移行の場合: DestinationURL は、移行元のゲスト仮想マシンから見た移行先ホスト物理マシンの URL になります。
  • ピアツーピア移行の場合: DestinationURL は、移行元のホスト物理マシンから見た移行先ホスト物理マシンの URL になります。
コマンドを入力すると、移行先システムの root パスワードの入力が求められます。

重要

移行を正常に実行するには、名前解決が両側 (移行元と移行先) で機能する必要があります。一方から他方を検索できる必要があります。一方から他方に ping すると、名前解決が機能していることを確認できます。
例: virsh を使用したライブマイグレーション

この例では host1.example.com から host2.example.com に移行しています。環境に適したホスト物理マシンの名前を使用してください。この例では guest1-rhel6-64 という名前の仮想マシンを移行しています。

この例では、 共有ストレージが正しく設定され、前提条件をすべて満たしていることを仮定しています (移行の要件 を参照)。
  1. ゲスト仮想マシンが実行中であることを確認します。

    移行元システム host1.example.comguest1-rhel6-64 が実行中であることを確認します。
    [root@host1 ~]# virsh list
    Id Name                 State
    ----------------------------------
     10 guest1-rhel6-64     running
  2. ゲスト仮想マシンを移行します。

    次のコマンドを実行して、ゲスト仮想マシンの移行先 host2.example.com へのライブマイグレーションを実行します。移行先 URL の末尾に /system を追加し、libvirt に完全アクセスが必要であることを伝えます。
    # virsh migrate --live guest1-rhel7-64 qemu+ssh://host2.example.com/system
    コマンドを入力すると、移行先システムの root パスワードの入力が求められます。
  3. 待機します。

    負荷やゲスト仮想マシンのサイズにより移行にかかる時間は異なります。virsh はエラーが発生した場合しか報告しません。ゲスト仮想マシンは、移行が完全に終了するまで移行元のホストマシンで継続的に実行されます。
  4. ゲスト仮想マシンが移行先ホストに到達していることを確認します。

    移行先システムの host2.example.comguest1-rhel7-64 が実行されていることを確認します。
    [root@host2 ~]# virsh list
    Id Name                 State
    ----------------------------------
     10 guest1-rhel7-64     running
これでライブマイグレーションが完了しました。

注記

libvirt では、TLS/SSL、UNIX ソケット、SSH、および暗号化されていない TCP などの各種のネットワーク方式に対応しています。他の方式を利用する方法についての詳細は、18章ゲストのリモート管理 を参照してください。

注記

稼働していないゲスト仮想マシンの移行は、以下のコマンドで実行できます。
# virsh migrate --offline --persistent 

15.5.1. virsh を使用した移行に関するヒント

複数の移行を別々のコマンドシェルで実行する同時ライブマイグレーションを実行することは可能です。ただし、それぞれの移行インスタンスは移行元と移行先で 1 つの MAX_CLIENT 値を使用するため、慎重に計算した上で実行する必要があります。デフォルトの設定値は 20 なので、10 インスタンスまでは設定を変更せずに実行できます。設定値を変更する必要がある場合は、手順15.1「libvirtd.conf の設定」の手順を参照してください。
  1. 手順15.1「libvirtd.conf の設定」 の手順に従って libvirtd.conf ファイルを開きます。
  2. Processing controls のセクションを特定します。
    #################################################################
    #
    # Processing controls
    #
    
    # The maximum number of concurrent client connections to allow
    # over all sockets combined.
    #max_clients = 5000
    
    # The maximum length of queue of connections waiting to be
    # accepted by the daemon. Note, that some protocols supporting
    # retransmission may obey this so that a later reattempt at
    # connection succeeds.
    #max_queued_clients = 1000
    
    # The minimum limit sets the number of workers to start up
    # initially. If the number of active clients exceeds this,
    # then more threads are spawned, upto max_workers limit.
    # Typically you'd want max_workers to equal maximum number
    # of clients allowed
    #min_workers = 5
    #max_workers = 20
    
    
    # The number of priority workers. If all workers from above
    # pool will stuck, some calls marked as high priority
    # (notably domainDestroy) can be executed in this pool.
    #prio_workers = 5
    
    # Total global limit on concurrent RPC calls. Should be
    # at least as large as max_workers. Beyond this, RPC requests
    # will be read into memory and queued. This directly impact
    # memory usage, currently each request requires 256 KB of
    # memory. So by default upto 5 MB of memory is used
    #
    # XXX this isn't actually enforced yet, only the per-client
    # limit is used so far
    #max_requests = 20
    
    # Limit on concurrent requests from a single client
    # connection. To avoid one client monopolizing the server
    # this should be a small fraction of the global max_requests
    # and max_workers parameter
    #max_client_requests = 5
    
    #################################################################
  3. max_clientsmax_workers パラメーターの設定値を変更します。この 2 つのパラメーターの値は同一にすることをお勧めします。max_clients は移行ごと 2 つのクライアントを使用し (移行元と移行先で 1 つずつ)、max_workers は実行フェーズでは移行元の 1 ワーカー、移行先では 0 ワーカーを使用し、終了フェーズでは移行先で 1 ワーカーを使用します。

    重要

    max_clientsmax_workers のパラメーター設定値は、libvirtd サービスに接続するすべてのゲスト仮想マシンによる影響を受けます。つまり、同じゲスト仮想マシンを使用し、かつ同時に移行を実行しているユーザーもすべて max_clientsmax_workers パラメーターに設定された値による制限を受けます。このため、同時ライブマイグレーションを行なう際は、まず最大値を注意深く検討する必要があります。

    重要

    max_clients パラメーターは libvirt に接続できるクライアント数を制御します。一度に多数のコンテナーが起動すると、この制限にすぐに達するか、この制限を超えてしまう可能性があります。max_clients パラメーターの値は増やすことでこの状態を回避することはできますが、これにより、インスタンスに対するサービス拒否 (DoS) 攻撃に対してシステムをより脆弱な状態にする可能性があります。この問題を軽減するため、Red Hat Enterprise Linux 7.0 では max_anonymous_clients 設定が新たに導入されています。これは、許可できる接続の内、認証されていない接続の制限を指定します。実際のワークロードに合わせて max_clientsmax_anonymous_clients の組み合わせを実装することができます。
  4. ファイルを保存してサービスを再起動します。

    注記

    数多くの SSH セッションが開始されたものの認証が行われていないために移行中に接続が落ちる場合があります。デフォルトでは、sshd で認証前の状態が許可されるのは 10 セッションのみです。この設定は sshd 設定ファイル内の MaxStartups パラメーターで制御されます (/etc/ssh/sshd_config 内)。場合によっては、このパラメーターを調整する必要があります。DoS 攻撃 (また一般的にはリソースの過剰使用) を防ぐ目的でこの制限が設けられているため、このパラメーターを調整するには注意が必要です。値を高く設定しすぎると、当初の目的を達成することができなくなります。このパラメーターを変更するには、/etc/ssh/sshd_config を編集して MaxStartups 行の先頭にある # を削除し、10 (デフォルト値) をより大きな値に変更します。その後は必ずファイルを保存して sshd サービスを再起動してください。詳細は、sshd_config の man ページを参照してください。

15.5.2. virsh migrate コマンドの追加オプション

--live 以外にも、virsh migrate コマンドは次のようなオプションを受け入れます。
  • --direct - 直接の移行に使用します。
  • --p2p - used for peer-to-peer migration
  • --tunneled - トンネル移行に使用します。
  • --offline - 移行先のドメインを開始したり、移行元ホスト上でこれを停止することなくドメイン定義を移行します。オフラインの移行は非アクティブなドメインで使用でき、--persistent オプションを指定して実行する必要があります。
  • --persistent - 移行先ホスト物理マシンでドメインを永続的な状態に維持します。
  • --undefinesource - 移行元ホスト物理マシンのドメインの定義を解除します。
  • --suspend - 移行先ホスト物理マシンでドメインを一時停止の状態に維持します。
  • --change-protection - 移行の実行中に、ドメインに対して互換性のない設定変更が行なわれないよう強制します。このフラグは、ハイパーバイザーでサポートされている場合に暗黙的に有効になります。ただし、ハイパーバイザーに変更保護のサポート機能がない場合には、これを明示的に使用して移行を拒否することができます。
  • --unsafe - 移行を強制的に実行し、安全のための手順はすべて無視します。
  • --verbose - 実行中の移行の進捗状況を表示します。
  • --compressed - ライブマイグレーションの実行時に繰り返し転送されるメモリーページの圧縮をアクティブにします。
  • --abort-on-error - ソフトエラー (例: I/O エラー) が移行時に発生する場合に、移行をキャンセルします。
  • --domain [name] - ドメイン名、ID または UUID を設定します。
  • --desturi [URI] - クライアント (通常の移行) または移行元 (p2p 移行) から表示される移行先ホストの接続 URI です。
  • --migrateuri [URI] - 通常は省略できる移行 URI です。
  • --graphicsuri [URI] - シームレスなグラフィックスの移行に使用されるグラフィックス URI です。
  • --listen-address [address] - 移行先のハイパーバイザーが着信接続でバインドする必要のあるリッスンアドレスを設定します。
  • --timeout [seconds] - ライブマイグレーションカウンターが N 秒を超えるとゲスト仮想マシンを強制的に一時停止します。これはライブマイグレーションの場合にのみ使用できます。タイムアウトが開始されると、一時停止しているゲスト仮想マシンで移行が続行されます。
  • --dname [newname]- 移行時にドメイン名を変更する場合に使用します。 このオプションも通常は省略できます。
  • --xml [filename] - 基礎となるストレージにアクセスする際に移行元と移行先間で異なる名前を構成するなど、ドメイン XML のホスト固有の部分に多数の変更を加える場合、該当するファイル名を使用して、移行先で使用する代替 XML ファイルを指定できます。このオプションは通常は省略されます。
  • --migrate-disks [disk_identifiers] - このオプションは、移行時にコピーされるディスクを選択するために使用できます。これにより、一部のディスクが移行先にすでに存在する場合や有用でなくなる場合など、一部のディスクをコピーすることが望ましくない状況で、より効率的なライブマイグレーションを実行できます。[disk_identifiers] は移行されるディスクのコンマ区切りの一覧に置き換える必要があります。これは、ドメイン XML ファイルの <target dev= /> 行にあるそれぞれの引数で特定されます。
さらに、以下のコマンドも便利です。
  • virsh migrate-setmaxdowntime [domain] [downtime] - 別のホストにライブマイグレーションされるドメインに許容可能な最大ダウンタイムを設定します。指定されるダウンタイムはミリ秒で表されます。指定されるドメインは、移行されるドメインと同じである必要があります。
  • virsh migrate-compcache [domain] --size - ライブマイグレーション中に繰り返し転送されるメモリーページを圧縮するために使用されるキャッシュの容量 (バイト単位) を設定し、取得します。--size が使用されていない場合、コマンドは圧縮キャッシュの現在のサイズを表示します。--size が使用されていて、バイト単位で指定されている場合には、ハイパーバイザーは、現在のサイズが表示された後に指定サイズに一致する圧縮に変更するよう指示されます。--size 引数は、移行プロセスや domjobinfo から取得される圧縮キャッシュミスの増加数に対応して、ドメインのライブマイグレーション実行時に使用されることになっています。
  • virsh migrate-setspeed [domain] [bandwidth] - 別のホストに移行される指定ドメインに移行帯域幅 (メビバイト/秒) を設定します。
  • virsh migrate-getspeed [domain] - 指定ドメインに利用できる最大の移行帯域幅 (メビバイト/秒) を取得します。
詳細は、移行の制限 または virsh の man ページを参照してください。

15.6. virt-manager を使用した移行

このセクションでは、virt-manager を使ってあるホスト物理マシンから別のホスト物理マシンに KVM ゲスト仮想マシンを移行する方法について説明します。
  1. 移行先のホスト物理マシンに接続します。

    virt-manager インターフェース において、ファイル メニューを選択し、次に 接続を追加 をクリックして移行先のホスト物理マシンに接続します。
  2. 接続を追加します。

    接続を追加 ウィンドウが表示されます。
    移行先ホスト物理マシンへの接続の追加

    図15.1 移行先ホスト物理マシンへの接続の追加

    以下のような詳細を入力します。
    • ハイパーバイザー: QEMU/KVM を選択します。
    • メソッド: 接続方法を選択します。
    • ユーザー名: リモートのホスト物理マシンのユーザー名を入力します。
    • ホスト名: リモートのホスト物理マシンのホスト名を入力します。

    注記

    接続オプションの詳細については、「リモート接続の追加」を参照してください。
    接続 をクリックします。この例では SSH 接続を使用しているため、次のステップで指定ユーザーのパスワードを入力する必要があります。
    パスワードの入力

    図15.2 パスワードの入力

  3. 共有ストレージを設定します。

    移行元および移行先の両ホストが、たとえば NFS を使って ストレージを共有していることを確認します。
  4. ゲスト仮想マシンを移行します。

    移行するゲストを右クリックして 移行 をクリックします。
    新しいホスト フィールドのドロップダウンリストを使い、ゲスト仮想マシンの移行先とするホスト物理マシンを選択し、移行 をクリックします。
    移行先ホスト物理マシンの選択と移行プロセスの開始

    図15.3 移行先ホスト物理マシンの選択と移行プロセスの開始

    進捗ウィンドウが表示されます。
    進捗ウィンドウ

    図15.4 進捗ウィンドウ

    移行が正常に終了すると、virt-manager には、移行先ホストで実行されている新たに移行したゲスト仮想マシンが表示されます。
    移行先ホスト物理マシンで実行される移行済みゲスト仮想マシン

    図15.5 移行先ホスト物理マシンで実行される移行済みゲスト仮想マシン

第16章 ゲスト仮想マシンデバイスの設定

Red Hat Enterprise Linux 7 は、ゲスト仮想マシンの以下の 3 つのクラスのデバイスに対応します。
  • エミュレートされたデバイス は、実際のハードウェアを模倣する純粋の仮想デバイスです。変換されていないゲストオペレーティングシステムは標準のインボックスドライバーを使ってこれらのデバイスと動作できるようになります。
  • Virtio デバイス (準仮想化 とも呼ばれる) は、仮想マシン内で最適に動作するように設計された仮想デバイスです。Virtio デバイスは、エミュレートされたデバイスと似ていますが、Linux 以外の仮想マシンにはこれらのデバイスが必要とするドライバーがデフォルトで含まれていません。仮想マシンマネージャー (virt-manager) や Red Hat Virtualization Hypervisor といった仮想化管理ソフトウェアは、対応する Linux 以外のゲストオペレーティングシステム用にこれらのドライバーを自動的にインストールします。Red Hat Enterprise Linux 7 は最高 216 の virtio デバイスに対応します。詳細については、5章KVM 準仮想化 (virtio) ドライバー を参照してください。
  • 割り当てデバイス は、仮想マシンに公開されている物理デバイスです。この方法は、パススルー とも呼ばれます。デバイス割り当てにより、仮想マシンによる PCI デバイスへの排他的アクセスが可能となり、PCI デバイスを使用した各種のタスクを実行できるようになります。また、PCI デバイスがゲストオペレーティングシステムに物理的に接続されているかのように表示させ、動作させることができます。Red Hat Enterprise Linux 7 は、1 仮想マシンあたり最高 32 の割り当てデバイスに対応します。
    デバイス割り当ては、グラフィックデバイスの選択 を含めて PCIe デバイス上でサポートされています。パラレル PCI デバイスは割り当てデバイスとしてのサポートが可能ですが、セキュリティーとシステム設定の競合により、極端な制限があります。
Red Hat Enterprise Linux 7 は、仮想マシンへの単一機能のスロットとして公開されるデバイスの PCI ホットプラグをサポートします。単一機能のホストデバイスとマルチ機能のホストデバイスの個別の機能は、このサポートを有効にするように設定できます。デバイスを仮想マシンへのマルチ機能の PCI スロットとして公開する設定は、ノンホットプラグアプリケーションの場合にお勧めします。
特定デバイスおよび関連する制限の詳細は、「デバイス」を参照してください。

注記

割り込み再マッピングのプラットフォームサポートは、割り当てデバイスを持つゲストをホストから完全に分離するために必要です。このサポートがない場合、ホストは悪意のあるゲストからの割り込み挿入攻撃に対して脆弱になる可能性があります。ゲストが信頼される環境では、管理者は allow_unsafe_interrupts モジュールに対して vfio_iommu_type1 オプションを使用する PCI デバイス割り当てを許可することを選択できます。これは、以下を含む .conf ファイル (例: local.conf) を /etc/modprobe.d に追加することで永続的に実行できます。
options vfio_iommu_type1 allow_unsafe_interrupts=1
または sysfs エントリーを動的に使用して同じことを実行します。
# echo 1 > /sys/module/vfio_iommu_type1/parameters/allow_unsafe_interrupts

16.1. PCI デバイス

PCI デバイス割り当ては、Intel VT-d または AMD IOMMU 対応のハードウェアプラットフォーム上でのみ利用可能です。PCI デバイス割り当てを機能させるには、Intel VT-d または AMD IOMMU の仕様がホストの BIOS で有効にされている必要があります。

手順16.1 Intel システムでの PCI デバイス割り当ての準備

  1. Intel VT-d 仕様を有効にします。

    Intel VT-d 仕様は、物理デバイスを仮想マシンに直接割り当てるためのハードウェアサポートを提供します。この仕様は、Red Hat Enterprise Linux で PCI デバイス割り当てを使用するために必要なものです。
    Intel VT-d 仕様は、BIOS で有効にされている必要があります。システムメーカーの中には、この仕様をデフォルトで無効にしているところもあります。この仕様に言及するために使用される用語はメーカーによって異なります。それぞれの該当する用語については、システムメーカーの資料を参照してください。
  2. カーネルで Intel VT-d をアクティブにします。

    カーネルで Intel VT-d をアクティブにするには、intel_iommu=oniommu=pt パラメーターを /etc/sysconfig/grub ファイルの GRUB_CMDLINX_LINUX 行の終わりの引用符の内側に追加します。
    以下は、Intel VT-d をアクティブにした grub ファイルの修正例です。
    GRUB_CMDLINE_LINUX="rd.lvm.lv=vg_VolGroup00/LogVol01
    vconsole.font=latarcyrheb-sun16 rd.lvm.lv=vg_VolGroup_1/root
    vconsole.keymap=us $([ -x /usr/sbin/rhcrashkernel-param ] && /usr/sbin/
    rhcrashkernel-param || :) rhgb quiet intel_iommu=on iommu=pt"
  3. 設定ファイルを再生成します。

    以下を実行して /etc/grub2.cfg を再生成します。
    grub2-mkconfig -o /etc/grub2.cfg
    UEFI ベースのホストの場合、ターゲットファイルは /etc/grub2-efi.cfg であることに注意してください。
  4. これで使用できるようになります。

    システムを再起動して、変更を有効にします。これでシステムで PCI デバイス割り当てを使用できるようになりました。

手順16.2 AMD システムでの PCI デバイス割り当ての準備

  1. AMD IOMMU 仕様を有効にします。

    AMD IOMMU 仕様は、Red Hat Enterprise Linux で PCI デバイス割り当てを使用するために必要なものです。この仕様は、BIOS で有効にされている必要があります。システムメーカーの中には、この仕様をデフォルトで無効にしているところもあります。
  2. IOMMU カーネルサポートを有効にします。

    amd_iommu=pt/etc/sysconfig/grub の GRUB_CMDLINX_LINUX 行の末尾の引用符の内側に追加し、AMD IOMMU 仕様が起動時に有効になるようにします。
  3. 設定ファイルを再生成します。

    以下を実行して /etc/grub2.cfg を再生成します。
    grub2-mkconfig -o /etc/grub2.cfg
    UEFI ベースのホストの場合、ターゲットファイルは /etc/grub2-efi.cfg であることに注意してください。
  4. これで使用できるようになります。

    システムを再起動して、変更を有効にします。これでシステムで PCI デバイス割り当てを使用できるようになりました。

注記

IOMMU についての詳細は、付録E IOMMU グループの使用 を参照してください。

16.1.1. virsh を使用した PCI デバイスの割り当て

以下のステップでは、KVM ハイパーバイザー上の仮想マシンに PCI デバイスを割り当てる方法を説明します。
以下の例では、PCI 識別子コードが pci_0000_01_00_0 の PCIe ネットワークコントローラーと guest1-rhel7-64 という名前の完全仮想化ゲストマシンを使用します。

手順16.3 virsh を使用した PCI デバイスのゲスト仮想マシンへの割り当て

  1. デバイスを特定します。

    最初に、仮想マシンへのデバイス割り当てに指定されているPCI デバイスを特定します。lspci コマンドで利用可能な PCI デバイスを一覧表示します。lspci の出力を grep を使って絞り込むことができます。
    この例では、以下の出力で強調表示されているイーサネットコントローラーを使用します。
    # lspci | grep Ethernet
    00:19.0 Ethernet controller: Intel Corporation 82567LM-2 Gigabit Network Connection
    01:00.0 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    01:00.1 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    このイーサネットコントローラーは、00:19.0 の短い識別子と共に表示されています。この PCI デバイスを仮想マシンに割り当てるには、virsh が使用する完全な識別子を見つける必要があります。
    これを実行するには、virsh nodedev-list コマンドを使用して、ホストマシンに接続されている特定の種類 (pci) のデバイスをすべて一覧表示します。次に出力を参照し、使用するデバイスの短い識別子にマップされている文字列を探します。
    この例では、短い識別子 00:19.0 を持つイーサネットコントローラーにマップされている文字列が強調表示されています。完全な識別子では、:. 文字がアンダースコアに置き換えられていることに注意してください。
    # virsh nodedev-list --cap pci
    pci_0000_00_00_0
    pci_0000_00_01_0
    pci_0000_00_03_0
    pci_0000_00_07_0
    pci_0000_00_10_0
    pci_0000_00_10_1
    pci_0000_00_14_0
    pci_0000_00_14_1
    pci_0000_00_14_2
    pci_0000_00_14_3
    pci_0000_00_19_0
    pci_0000_00_1a_0
    pci_0000_00_1a_1
    pci_0000_00_1a_2
    pci_0000_00_1a_7
    pci_0000_00_1b_0
    pci_0000_00_1c_0
    pci_0000_00_1c_1
    pci_0000_00_1c_4
    pci_0000_00_1d_0
    pci_0000_00_1d_1
    pci_0000_00_1d_2
    pci_0000_00_1d_7
    pci_0000_00_1e_0
    pci_0000_00_1f_0
    pci_0000_00_1f_2
    pci_0000_00_1f_3
    pci_0000_01_00_0
    pci_0000_01_00_1
    pci_0000_02_00_0
    pci_0000_02_00_1
    pci_0000_06_00_0
    pci_0000_07_02_0
    pci_0000_07_03_0
    使用するデバイスにマップされている PCI デバイス番号を書き留めてください。この番号は他のステップで必要になります。
  2. デバイス情報を確認します。

    ドメイン、バスおよび機能についての情報は、virsh nodedev-dumpxml コマンドの出力を参照してください。
    
    # virsh nodedev-dumpxml pci_0000_00_19_0
    <device>
      <name>pci_0000_00_19_0</name>
      <parent>computer</parent>
      <driver>
        <name>e1000e</name>
      </driver>
      <capability type='pci'>
        <domain>0</domain>
        <bus>0</bus>
        <slot>25</slot>
        <function>0</function>
        <product id='0x1502'>82579LM Gigabit Network Connection</product>
        <vendor id='0x8086'>Intel Corporation</vendor>
        <iommuGroup number='7'>
          <address domain='0x0000' bus='0x00' slot='0x19' function='0x0'/>
        </iommuGroup>
      </capability>
    </device>
    

    図16.1 内容のダンプ

    注記

    IOMMU グループは、IOMMU から見たデバイスの可視性と分離度に基づいて決定されます。それぞれの IOMMU グループには、1 つ以上のデバイスが含まれる可能性があります。複数のデバイスが表示される場合、すべてのエンドポイントが、ゲストに割り当てられるIOMMU グループ内のすべてのデバイスに対して要求される必要があります。これは、追加のエンドポイントをゲストに割り当てるか、または virsh nodedev-detach を使用してエンドポイントをホストドライバーから分離するかのいずれかの方法で実行できます。単一グループに含まれるデバイスは、複数のゲスト間で分割したり、ホストとゲストの間で分割したりすることができないことがあります。PCIe ルートポート、スイッチポート、およびブリッジなどエンドポイント以外のデバイスはホストドライバーから分離することはできません。これらはエンドポイントの割り当てを妨げることはありません。
    IOMMU グループ内のデバイスは、virsh nodedev-dumpxml 出力の iommuGroup セクションを使用して判別できます。グループの各メンバーは別個の「アドレス」フィールドで指定されます。この情報は、以下を使用して sysfs 内で見つけることもできます。
    $ ls /sys/bus/pci/devices/0000:01:00.0/iommu_group/devices/
    この出力の一例を示します。
    0000:01:00.0  0000:01:00.1
    0000.01.00.0 のみをゲストに割り当てるには、ゲストを起動する前に、使用されていないエンドポイントをホストから切り離す必要があります。
    $ virsh nodedev-detach pci_0000_01_00_1
  3. 必要な設定の詳細を決定します。

    設定ファイルに必要な値については、virsh nodedev-dumpxml pci_0000_00_19_0 コマンドの出力を参照してください。
    サンプルのデバイスには、bus = 0、slot = 25、function = 0 の値が設定されています。10 進法の設定では、これらの値を使用します。
    bus='0'
    slot='25'
    function='0'
  4. 設定の詳細を追加します。

    仮想マシン名を指定して virsh edit を実行し、<source> セクションにデバイスエントリーを追加して PCI デバイスをゲスト仮想マシンに割り当てます。
    # virsh edit guest1-rhel7-64
    <hostdev mode='subsystem' type='pci' managed='yes'>
      <source>
         <address domain='0' bus='0' slot='25' function='0'/>
      </source>
    </hostdev>
    

    図16.2 PCI デバイスの追加

    または、仮想マシン名とゲストの XML ファイルを指定して virsh attach-device を実行します。
    virsh attach-device guest1-rhel7-64 file.xml
  5. 仮想マシンを起動します。

    # virsh start guest1-rhel7-64
これで PCI デバイスは正しく仮想マシンに割り当てられ、ゲストオペレーティングシステムからアクセスできるようになります。

16.1.2. virt-manager を使用した PCI デバイスの割り当て

PCI デバイスは、グラフィカルな virt-manager ツールを使ってゲスト仮想マシンに追加することができます。以下の手順では、Gigabit イーサネットコントローラーをゲスト仮想マシンに追加します。

手順16.4 virt-manager を使用した PCI デバイスのゲスト仮想マシンへの割り当て

  1. ハードウェア設定を開きます。

    ゲスト仮想マシンを開き、ハードウェアを追加 ボタンをクリックして新規デバイスを仮想マシンに追加します。
    The virtual machine hardware window with the Information button selected on the top taskbar and Overview selected on the left menu pane.

    図16.3 仮想マシンのハードウェア情報ウィンドウ

  2. PCI デバイスを選択します。

    左側の PCI Host Deviceハードウェア リストから を選択します。
    未使用の PCI デバイスを選択します。別のゲストが使用中の PCI デバイスを選択するとエラーが発生するので注意してください。以下の例では、予備のオーディオコントローラーが使用されます。完了 をクリックしてセットアップを終了します。
    The Add new virtual hardware wizard with PCI Host Device selected on the left menu pane, showing a list of host devices for selection in the right menu pane.

    図16.4 新しい仮想ハードウェアを追加ウィザード

  3. 新規デバイスを追加します。

    セットアップが完了し、これでゲスト仮想マシンは PCI デバイスに直接アクセスできます。
    The virtual machine hardware window with the Information button selected on the top taskbar and Overview selected on the left menu pane, displaying the newly added PCI Device in the list of virtual machine devices in the left menu pane.

    図16.5 仮想マシンのハードウェア情報ウィンドウ

注記

デバイスの割り当てに失敗する場合、ホストに依然として接続されている他のエンドポイントが同じ IOMMU グループ内にある可能性があります。virt-manager を使用してグループ情報を取得する方法はありませんが、virsh コマンドを使用して IOMMU グループの範囲を分析することができ、必要な場合はデバイスを分離することができます。
IOMMU グループについての詳細および virsh を使用してエンドポイントデバイスを切り離す方法については、「virsh を使用した PCI デバイスの割り当て」注記 を参照してください。

16.1.3. virt-install を使用した PCI デバイスの割り当て

virt-install コマンドを使ってゲストをインストールする際に、PCI デバイスを割り当てることができます。この場合、--host-device パラメーターを使用します。

手順16.5 virt-install を使用したゲスト仮想マシンへのPCI デバイス割り当て

  1. デバイスを特定します。

    ゲスト仮想マシンへのデバイス割り当てに指定されているPCI デバイスを特定します。
    # lspci | grep Ethernet
    00:19.0 Ethernet controller: Intel Corporation 82567LM-2 Gigabit Network Connection
    01:00.0 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    01:00.1 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    virsh nodedev-list コマンドは、システムに接続されている全デバイスを一覧表示し、各 PCI デバイスを文字列で特定します。出力を PCI デバイスに限定するには、以下のコマンドを入力します。
    # virsh nodedev-list --cap pci
    pci_0000_00_00_0
    pci_0000_00_01_0
    pci_0000_00_03_0
    pci_0000_00_07_0
    pci_0000_00_10_0
    pci_0000_00_10_1
    pci_0000_00_14_0
    pci_0000_00_14_1
    pci_0000_00_14_2
    pci_0000_00_14_3
    pci_0000_00_19_0
    pci_0000_00_1a_0
    pci_0000_00_1a_1
    pci_0000_00_1a_2
    pci_0000_00_1a_7
    pci_0000_00_1b_0
    pci_0000_00_1c_0
    pci_0000_00_1c_1
    pci_0000_00_1c_4
    pci_0000_00_1d_0
    pci_0000_00_1d_1
    pci_0000_00_1d_2
    pci_0000_00_1d_7
    pci_0000_00_1e_0
    pci_0000_00_1f_0
    pci_0000_00_1f_2
    pci_0000_00_1f_3
    pci_0000_01_00_0
    pci_0000_01_00_1
    pci_0000_02_00_0
    pci_0000_02_00_1
    pci_0000_06_00_0
    pci_0000_07_02_0
    pci_0000_07_03_0
    PCI デバイス番号は他のステップで必要になるので、書き留めます。
    ドメイン、バスおよび各種機能についての情報は、virsh nodedev-dumpxml コマンドの出力を参照することができます。
    # virsh nodedev-dumpxml pci_0000_01_00_0
    
    <device>
      <name>pci_0000_01_00_0</name>
      <parent>pci_0000_00_01_0</parent>
      <driver>
        <name>igb</name>
      </driver>
      <capability type='pci'>
        <domain>0</domain>
        <bus>1</bus>
        <slot>0</slot>
        <function>0</function>
        <product id='0x10c9'>82576 Gigabit Network Connection</product>
        <vendor id='0x8086'>Intel Corporation</vendor>
        <iommuGroup number='7'>
          <address domain='0x0000' bus='0x00' slot='0x19' function='0x0'/>
        </iommuGroup>
      </capability>
    </device>
    

    図16.6 PCI デバイスファイルの内容

    注記

    IOMMU グループに複数のエンドポイントがあり、それらのすべてがゲストに割り当てられている訳ではない場合、ゲストを起動する前に以下のコマンドを実行して、他のエンドポイントをホストから手動で切り離す必要があります。
    $ virsh nodedev-detach pci_0000_00_19_1
    IOMMU グループの詳細は、「virsh を使用した PCI デバイスの割り当て」注記 を参照してください。
  2. デバイスを追加します。

    virsh nodedev コマンドの PCI 識別子の出力を --host-device パラメーターの値として使います。
    virt-install \
    --name=guest1-rhel7-64 \
    --disk path=/var/lib/libvirt/images/guest1-rhel7-64.img,size=8 \
    --vcpus=2 --ram=2048 \
    --location=http://example1.com/installation_tree/RHEL7.0-Server-x86_64/os \
    --nonetworks \
    --os-type=linux \
    --os-variant=rhel7
    --host-device=pci_0000_01_00_0
  3. インストールを完了します。

    これでゲストのインストールが完了しました。PCI デバイスはゲストに接続されています。

16.1.4. 割り当てた PCI デバイスの接続解除

ホストの PCI デバイスがゲストマシンに割り当てられると、ホストはこのデバイスを使用できなくなります。PCI デバイスが managed モードにある場合は (managed='yes'ドメイン XML ファイル パラメーターを使って設定)、必要に応じてゲストマシンに接続し、ゲストマシンから切り離し、再びホストマシンに接続することができます。PCI デバイスが managed モードにない場合は、virsh または virt-manager を使って PCI デバイスをゲストマシンから切り離し、再び接続することができます。

手順16.6 virsh を使用した PCI デバイスのゲストからの接続解除

  1. デバイスの接続を解除します。

    以下のコマンドを使ってゲストの XML ファイル内から PCI デバイスを削除することで、ゲストから PCI デバイスを切り離します。
    # virsh detach-device name_of_guest file.xml
  2. デバイスをホストに再接続します (オプション)。

    デバイスが managed モードの場合は、このステップを省略します。デバイスはホストに自動的に戻ります。
    デバイスが managed モードを使用していない場合は、以下のコマンドを使用して PCI デバイスをホストマシンに再接続します。
    # virsh nodedev-reattach device
    たとえば、pci_0000_01_00_0 デバイスをホストに再接続するには、以下のようにします。
    # virsh nodedev-reattach pci_0000_01_00_0
    これでこのデバイスはホストで使用できます。

手順16.7 virt-manager を使用した PCI デバイスのゲストからの接続解除

  1. 仮想ハードウェアの詳細画面を開きます。

    virt-manager で、デバイスを含む仮想マシンをダブルクリックします。仮想マシンの情報を表示 ボタンを選択し、仮想ハードウェアの一覧を表示します。
    The Show virtual hardware details button.

    図16.7 仮想ハードウェア詳細ボタン

  2. デバイスを選択し、削除します。

    左側パネルの仮想デバイスの一覧より、接続を解除する PCI デバイスを選択します。
    The PCI device details and the Remove button.

    図16.8 接続解除する PCI デバイスの選択

    削除 ボタンをクリックします。これでデバイスがホストで使用可能になります。

16.1.5. PCI ブリッジの作成

PCI (Peripheral Component Interconnect) ブリッジは、ネットワークカード、モデムおよび音声カードなどのデバイスに接続するために使用されます。物理デバイスと同様に、仮想デバイスも PCI ブリッジに接続することができます。かつてゲスト仮想マシンに追加できる PCI デバイスの数は 31 のみでした。現在では、31 番目の PCI デバイスが追加されると、PCI ブリッジが自動的に 31 番目のスロットに配置され、追加の PCI デバイスはその PCI ブリッジに移行します。それぞれの PCI ブリッジには、追加の 31 デバイスに対応する 31 のスロットがあり、それらすべてをブリッジにすることができます。この方法で、900 を超えるデバイスをゲスト仮想マシンで利用可能にすることができます。このアクションは、ゲスト仮想マシンが実行中の場合には実行できないことに注意してください。シャットダウンしているゲスト仮想マシンに PCI デバイスを追加する必要があります。

16.1.5.1. PCI ブリッジのホットプラグ/アンホットプラグサポート

PCI ブリッジのホットプラグ/アンホットプラグは、以下のデバイスタイプでサポートされています。
  • virtio-net-pci
  • virtio-scsi-pci
  • e1000
  • rtl8139
  • virtio-serial-pci
  • virtio-balloon-pci

16.1.6. PCI デバイス割り当ての制限

PCI デバイス割り当て (PCI デバイスの仮想マシンへのアタッチ) で PCIe デバイスのデバイス割り当てを有効にするには、ホストシステムが AMD IOMMU または Intel VT-d サポートを備えている必要があります。
Red Hat Enterprise Linux 7 では、ゲストデバイスドライバーによる PCI 設定領域へのアクセスは制限されています。この制限により、拡張された PCI 設定領域にあるデバイス機能に依存するドライバーが設定に失敗する場合があります。
Red Hat Enterprise Linux 7 仮想マシン 1 台あたりに割り当てられるデバイスの合計数は 32 という制限があります。これは、仮想マシンにある PCI ブリッジの数やそれらの機能がどのようにマルチファンクションスロットを構成するように組み合わされるかにかかわらず、32 の PCI 機能に変換されることを意味します。
割り込み再マッピングのプラットフォームサポートは、割り当てデバイスを持つゲストをホストから完全に分離するために必要です。このサポートがない場合、ホストは悪意のあるゲストからの割り込み挿入攻撃に対して脆弱になる可能性があります。ゲストが信頼される環境では、管理者は allow_unsafe_interrupts モジュールに対して vfio_iommu_type1 オプションを使用する PCI デバイス割り当て許可を選択できます。これは、以下を含む .conf ファイル (例: local.conf) を /etc/modprobe.d に追加することで永続的に実行できます。
options vfio_iommu_type1 allow_unsafe_interrupts=1
または sysfs エントリーを動的に使用して同じことを実行します。
# echo 1 > /sys/module/vfio_iommu_type1/parameters/allow_unsafe_interrupts

16.2. PCI デバイス割り当てと SR-IOV デバイス

PCI ネットワーク (<source> 要素でドメイン XML に指定される) は、直接のデバイス割り当て (パススルー と呼ばれることがある) を使用してゲストに直接接続されます。標準の単一ポート PCI イーサネットカードドライバーの設計上の制限により、この方法で割り当てられるのは、シングルルート I/O 仮想化 (SR-IOV) の 仮想機能 (VF) デバイスのみになります。標準の単一ポート PCI または PCIe イーサネットカードをゲストに割り当てるには、従来の <hostdev> デバイスの定義を使用します。

     <devices>
    <interface type='hostdev'>
      <driver name='vfio'/>
      <source>
        <address type='pci' domain='0x0000' bus='0x00' slot='0x07' function='0x0'/>
      </source>
      <mac address='52:54:00:6d:90:02'>
      <virtualport type='802.1Qbh'>
        <parameters profileid='finance'/>
      </virtualport>
    </interface>
  </devices>

図16.9 PCI デバイス割り当ての XML サンプル

PCI-SIG が開発したシングルルート I/O 仮想化 (SR-IOV) 仕様は、単一デバイスを複数の仮想マシンで共有できる PCI デバイス割り当てにおける標準です。SR-IOV は、仮想マシンのデバイスパフォーマンスを強化します。
SR-IOV のしくみ

図16.10 SR-IOV のしくみ

SR-IOV は、シングルルート機能 (例: シングルイーサネットポート) を複数の別個の物理デバイスのように見せることができます。SR-IOV 対応の物理デバイスは、PCI 設定領域で複数機能のように見えるように設定することができます。各デバイスには、Base Address Registers (BAR) を備えた独自の設定領域があります。
SR-IOV は、以下の 2 つの PCI 機能を使用します。
  • 物理機能 (PF) は、SR-IOV 機能を含む完全な PCIe デバイスです。物理機能は、通常の PCI デバイスとして検出され、管理され、設定されます。物理機能は、仮想機能を割り当てることで SR-IOV 機能を設定し、管理します。
  • 仮想機能 (VF) は、I/O のみを処理する単純な PCIe 機能です。それぞれの仮想機能は物理機能から派生します。デバイス 1 台に備わる仮想機能の数は、デバイスのハードウェアによって制限されます。物理デバイスであるシングルイーサネットポートは、仮想マシンと共有可能な多くの仮想機能にマッピングできます。
ハイパーバイザーは 1 つまたは複数の仮想機能を仮想マシンに割り当てることができます。仮想機能の設定領域は、その後ゲストに提示される設定領域に割り当てられます。
仮想機能は実際のハードウェアリソースを必要とするので、それぞれの仮想機能は一度に 1 つのゲストにしか割り当てることができません。仮想マシンには複数の仮想機能を含めることができます。仮想機能は、通常のネットワークカードがオペレーティングシステムに対して表示されるようにネットワークカードとして表示されます。
SR-IOV ドライバーはカーネル内に実装されています。コア実装は PCI サブシステム内に内包されていますが、物理機能 (PF) と仮想機能 (VF) デバイスの両方にもドライバーサポートが必要です。SR-IOV 対応デバイスは、物理機能から仮想機能を割り当てることができます。仮想機能は、キューやレジスターセットなどのリソースで物理 PCI デバイスにバックアップされている PCI デバイスのように表示されます。

16.2.1. SR-IOV の利点

SR-IOV デバイスは、1 つの物理ポートを複数の仮想マシンと共有できます。
SR-IOV VF が仮想マシンに割り当てられている場合、VF からのすべてのネットワークトラフィックを特定の VLAN に配置するよう設定することができます (仮想マシンに対して透過的に)。仮想マシンは、自分のトラフィックが VLAN とタグ付けされていることを検知できず、このタグ付けを変更したり削除したりすることはできません。
仮想機能は、ネイティブに近いパフォーマンスを発揮し、準仮想化ドライバーやエミュレートされたアクセスよりもすぐれたパフォーマンスを提供します。仮想機能ではデータがハードウェアによって管理され、制御されるため、同一の物理サーバー上における仮想マシン間でのデータ保護が行われます。
これらの機能により、データセンター内でのホスト上の仮想マシン密度は高くなります。
SR-IOV は、複数ゲストとデバイスの帯域幅を有効活用できます。

16.2.2. SR-IOV の使用

このセクションでは、SR-IOV 対応のマルチポイントネットワークカードの仮想機能をネットワークデバイスとして仮想マシンに割り当てる、PCI パススルーの使い方を説明します。
<hostdev> または virsh edit コマンドで virsh attach-device 内にデバイスエントリーを追加することにより、SR-IOV 仮想機能を仮想マシンに割り当てられます。しかしこの操作は、通常のネットワークデバイスと違って SR-IOV VF は永久的な固有の MAC アドレスを持たず、ホストが再起動するたびに新たな MAC アドレスが割り当てられるので問題になる可能性があります。このため、再起動後にゲストに同じ仮想機能が割り当てられても、ホストが再起動すると、ゲストは新規の MAC アドレスを持たせるために新たなネットワークアダプターを決定します。その結果、ゲストは毎回新たなハードウェアが接続されたと認識し、通常はゲストのネットワークの再設定を要求することになります。
libvirt には、<interface type='hostdev'> インタフェースデバイスが含まれます。このインタフェースデバイスを使って、libvirt はまず指定されたネットワーク特定のハードウェア/スイッチの初期化を行います (MAC アドレスや VLAN タグ、802.1Qbh virtualport パラメーターの設定など)。その後に、ゲストへの PCI デバイス割り当てを実行します。
<interface type='hostdev'> インタフェースデバイスの使用には、以下が必要です。
  • SR-IOV 対応ネットワークカード
  • Intel VT-d または AMD IOMMU 拡張をサポートするホストハードウェア
  • 割り当てられる仮想機能の PCI アドレス

重要

SR-IOV デバイスを仮想マシンに割り当てるには、ホストハードウェアが Intel VT-d または AMD IOMMU 仕様に対応している必要があります。
SR-IOV ネットワークデバイスを Intel または AMD システムに割り当てるには、以下の手順を実行します。

手順16.8 SR-IOV ネットワークデバイスをIntel または AMD システムに割り当てる

  1. Intel VT-d または AMD IOMMU 仕様を BIOS およびカーネル内で有効にします。

    Intel システムでは、Intel VT-d が有効にされていない場合、BIOS で有効にします。BIOS およびカーネルで Intel VT-d を有効にする方法については、手順16.1「Intel システムでの PCI デバイス割り当ての準備」を参照してください。
    Intel VT-d が有効にされ、機能している場合は、このステップを省略してください。
    AMD システムでは、AMD IOMMU 仕様が有効にされていない場合、BIOS で有効にします。BIOS で IOMMU を有効にする方法については、手順16.2「AMD システムでの PCI デバイス割り当ての準備」を参照してください。
  2. サポートを確認します。

    SR-IOV 機能に対応する PCI デバイスが検出されるかどうかを確認します。この例では、SR-IOV 対応の Intel 82576 ネットワークインタフェースカードが一覧表示されています。lspci コマンドを使ってデバイスが検出されたかどうかを確認します。
    # lspci
    03:00.0 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    03:00.1 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    出力が変更されて、他のデバイスがすべて削除されていることに注意してください。
  3. 仮想機能をアクティブにします。

    次のコマンドを実行します。
    # echo ${num_vfs} > /sys/class/net/enp14s0f0/device/sriov_numvfs
  4. 仮想機能を永続化します。

    再起動後も仮想機能を存続させるためには、任意のエディターを使って以下のような udev ルールを作成し、VF の数をネットワークインターフェースカードでサポートされる上限値までの間で指定します (この例では 2 つ)。以下の例では、enp14s0f0 を PF ネットワークデバイス名に置き換え、ENV{ID_NET_DRIVER} の値を使用中のドライバーと一致させています。
    # vim /etc/udev/rules.d/enp14s0f0.rules
    ACTION=="add", SUBSYSTEM=="net", ENV{ID_NET_DRIVER}=="ixgbe",
    ATTR{device/sriov_numvfs}="2"
    これにより、この機能がブート時間に有効になります。
  5. 新たな仮想機能を検査します。

    lspci コマンドを使用して、Intel 82576 ネットワークデバイスに割り当てられ、新たに追加された仮想機能を一覧表示します。(または、grep を使って Virtual Function、または仮想機能をサポートするデバイスを検索します。)
    # lspci | grep 82576
    0b:00.0 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    0b:00.1 Ethernet controller: Intel Corporation 82576 Gigabit Network Connection (rev 01)
    0b:10.0 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.1 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.2 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.3 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.4 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.5 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.6 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:10.7 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.0 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.1 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.2 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.3 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.4 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    0b:11.5 Ethernet controller: Intel Corporation 82576 Virtual Function (rev 01)
    PCI デバイスの ID は、-n コマンドの lspci パラメーターを使って確認します。物理機能は、0b:00.0 および 0b:00.1 に対応します。仮想機能にはすべて Virtual Function と記述されます。
  6. virsh を使用してデバイスの有無を確認します。

    デバイスを仮想マシンに追加する前に、libvirt サービスはそのデバイスを認識する必要があります。libvirt は、lspci 出力に類似する表示を使用します。 出力では、すべての句読点とコロン (:) およびピリオド (.lspci) は、アンダースコア (_) に変換されます。
    virsh nodedev-list コマンドと grep コマンドを使って、利用可能なホストデバイスの一覧から Intel 82576 ネットワークデバイスを選び出します。この例の 0b は、Intel 82576 ネットワークデバイスのフィルターです。これはお使いのシステムによっても異なり、結果として別のデバイスが加わる場合もあります。
    # virsh nodedev-list | grep 0b
    pci_0000_0b_00_0
    pci_0000_0b_00_1
    pci_0000_0b_10_0
    pci_0000_0b_10_1
    pci_0000_0b_10_2
    pci_0000_0b_10_3
    pci_0000_0b_10_4
    pci_0000_0b_10_5
    pci_0000_0b_10_6
    pci_0000_0b_11_7
    pci_0000_0b_11_1
    pci_0000_0b_11_2
    pci_0000_0b_11_3
    pci_0000_0b_11_4
    pci_0000_0b_11_5
    この一覧には、仮想機能と物理機能の PCI アドレスが表示されます。
  7. virsh を使用してデバイスの詳細情報を取得します。

    pci_0000_0b_00_0 は物理機能の 1 つであり、pci_0000_0b_10_0 はこの物理機能に対応する最初の仮想機能です。virsh nodedev-dumpxml コマンドを使って、両方のデバイスのデバイス情報を表示します。
    # virsh nodedev-dumpxml pci_0000_03_00_0
    <device>
      <name>pci_0000_03_00_0</name>
      <path>/sys/devices/pci0000:00/0000:00:01.0/0000:03:00.0</path>
      <parent>pci_0000_00_01_0</parent>
      <driver>
        <name>igb</name>
      </driver>
      <capability type='pci'>
        <domain>0</domain>
        <bus>3</bus>
        <slot>0</slot>
        <function>0</function>
        <product id='0x10c9'>82576 Gigabit Network Connection</product>
        <vendor id='0x8086'>Intel Corporation</vendor>
        <capability type='virt_functions'>
          <address domain='0x0000' bus='0x03' slot='0x10' function='0x0'/>
          <address domain='0x0000' bus='0x03' slot='0x10' function='0x2'/>
          <address domain='0x0000' bus='0x03' slot='0x10' function='0x4'/>
          <address domain='0x0000' bus='0x03' slot='0x10' function='0x6'/>
          <address domain='0x0000' bus='0x03' slot='0x11' function='0x0'/>
          <address domain='0x0000' bus='0x03' slot='0x11' function='0x2'/>
          <address domain='0x0000' bus='0x03' slot='0x11' function='0x4'/>
        </capability>
        <iommuGroup number='14'>
          <address domain='0x0000' bus='0x03' slot='0x00' function='0x0'/>
          <address domain='0x0000' bus='0x03' slot='0x00' function='0x1'/>
        </iommuGroup>
      </capability>
    </device>
    # virsh nodedev-dumpxml pci_0000_03_11_5
    <device>
      <name>pci_0000_03_11_5</name>
      <path>/sys/devices/pci0000:00/0000:00:01.0/0000:03:11.5</path>
      <parent>pci_0000_00_01_0</parent>
      <driver>
        <name>igbvf</name>
      </driver>
      <capability type='pci'>
        <domain>0</domain>
        <bus>3</bus>
        <slot>17</slot>
        <function>5</function>
        <product id='0x10ca'>82576 Virtual Function</product>
        <vendor id='0x8086'>Intel Corporation</vendor>
        <capability type='phys_function'>
          <address domain='0x0000' bus='0x03' slot='0x00' function='0x1'/>
        </capability>
        <iommuGroup number='35'>
          <address domain='0x0000' bus='0x03' slot='0x11' function='0x5'/>
        </iommuGroup>
      </capability>
    </device>
    この例では、仮想機能 pci_0000_03_10_2 をステップ 8 の仮想マシンに追加します。仮想機能の busslot、および function パラメーターは、デバイスを追加するのに必要になります。
    /tmp/new-interface.xml などの一時 XML ファイルにこれらのパラメーターをコピーします。
       <interface type='hostdev' managed='yes'>
         <source>
           <address type='pci' domain='0x0000' bus='0x03' slot='0x10' function='0x2'/>
         </source>
       </interface>

    注記

    仮想マシンが起動すると、物理アダプターが提供し、MAC アドレスが設定されたネットワークデバイスのタイプが認識されます。このMAC アドレスは、ホストおよびゲストが再起動しても変更されません。
    以下の <interface> の例では、オプションの <mac address><virtualport><vlan> 要素の構文を示しています。実際には、<vlan> または <virtualport> を、例のように両方同時に使用するのではなく、どちらか一方を使用します。
    ...
     <devices>
       ...
       <interface type='hostdev' managed='yes'>
         <source>
           <address type='pci' domain='0' bus='11' slot='16' function='0'/>
         </source>
         <mac address='52:54:00:6d:90:02'>
         <vlan>
            <tag id='42'/>
         </vlan>
         <virtualport type='802.1Qbh'>
           <parameters profileid='finance'/>
         </virtualport>
       </interface>
       ...
     </devices>
    MAC アドレスは、指定されない場合は自動生成されます。<virtualport> 要素は、802.11Qbh ハードウェアスウィッチに接続する場合のみ使用されます。<vlan> 要素は、ゲストのデバイスを 42 とタグ付けされた VLAN に透過的に配置します。
  8. 仮想機能を仮想マシンに追加します。

    直前のステップで作成された一時ファイルで以下のコマンドを使用して、仮想機能を仮想マシンに追加します。これで新規デバイスは即時に割り当てられ、これ以降のゲストの再起動に備えて保存されます。
    virsh attach-device MyGuest /tmp/new-interface.xml --live --config
    --livevirsh attach-device を指定することで、新規デバイスを実行中のゲストに割り当てます。--config オプションを使うと、これ以降のゲストの再起動後も新規デバイスが確実に利用可能となります。

    注記

    --live オプションはゲストが実行中の場合にのみ受け入れられます。virsh オプションが実行中ではないゲストで使用されると、--live はエラーを返します。
仮想マシンが新規ネットワークインタフェースカードを検出します。この新規カードが、SR-IOV デバイスの仮想機能です。

16.2.3. SR-IOV デバイスの場合の PCI 割り当ての設定

SR-IOV ネットワークカードは、複数の仮想機能 (VF) を提供します。これらの仮想機能は、それぞれ PCI デバイス割り当てを使用してゲスト仮想マシンに割り当てることができます。いったん割り当てられると、それぞれの仮想機能は完全な物理ネットワークデバイスのように機能します。これにより、多くのゲスト仮想マシンが、ホスト物理マシン上で単一スロットのみを使用していても、直接の PCI デバイス割り当てによるパフォーマンス上の利点を得られます。
これらの仮想機能 (VF) は、<hostdev> 要素を使用する従来の方法によりゲスト仮想マシンに割り当てられますが、SR-IOV VF ネットワークデバイスには永続的な固有の MAC アドレスがないため、ホスト物理マシンが再起動されるたびにゲスト仮想マシンのネットワーク設定を再設定する必要があるという問題が生じます。この問題に対処するには、VF をホスト物理マシンに割り当てる前に MAC アドレスを設定する必要があり、この設定はゲスト仮想マシンの起動時に毎回行う必要があります。他のオプションと同様にこの MAC アドレスを割り当てるには、以下の手順を参照してください。

手順16.9 SR-IOV で PCI デバイスを割り当てるための MAC アドレス、vLAN、および仮想ポートの設定

<hostdev> 要素は、MAC アドレス割り当て、vLAN タグ ID 割り当て、または仮想ポートの割り当てなどの機能固有の項目に使用することはできません。<mac><vlan>、および <virtualport> 要素は <hostdev> の有効な子ではないためです。それらは hostdev インターフェースタイプ <interface type='hostdev'> で使用できます。このデバイスタイプは、<interface><hostdev> のハイブリッドとして機能します。そのため、PCI デバイスをゲスト仮想マシンに割り当てる前に、libvirt はゲスト仮想マシンの XML 設定ファイルに示されるネットワーク固有のハードウェアまたはスイッチ (MAC アドレスの設定、vLAN タグの設定、および/または 802.1Qbh スイッチとの関連付け) を初期化します。vLAN タグ設定についての情報は、「vLAN タグの設定」を参照してください。
  1. 情報を収集します。

    <interface type='hostdev'> を使用するには、SR-IOV 対応ネットワークカード、また Intel VT-d または AMD IOMMU 拡張のいずれかをサポートするホスト物理マシンハードウェアが必要であり、割り当てる VF の PCI アドレスを把握しておく必要があります。
  2. ゲスト仮想マシンをシャットダウンします。

    virsh shutdown コマンドを使用して、ゲスト仮想マシンのシャットダウン (ここで使用される名前は guestVM) を実行します。
    # virsh shutdown guestVM
  3. XML ファイルを開いて編集します。

    編集する XML ファイルを開くには、virsh save-image-edit オプションを指定して 「ゲスト仮想マシン設定の編集」 コマンドを実行します (詳細は、--runningを参照してください)。この例の設定ファイルの名前は guestVM.xml です。
     # virsh save-image-edit guestVM.xml --running 
    ユーザーのデフォルトエディターで guestVM.xml を開きます。
  4. XML ファイルを編集します。

    以下のような guestVM.xml エントリーを組み込むように設定ファイル (<devices>) を更新します。
    
     <devices>
       ...
       <interface type='hostdev' managed='yes'>
         <source>
           <address type='pci' domain='0x0' bus='0x00' slot='0x07' function='0x0'/> <!--these values can be decimal as well-->
         </source>
         <mac address='52:54:00:6d:90:02'/>                                         <!--sets the mac address-->
         <virtualport type='802.1Qbh'>                                              <!--sets the virtual port for the 802.1Qbh switch-->
           <parameters profileid='finance'/>
         </virtualport>
         <vlan>                                                                     <!--sets the vlan tag-->
          <tag id='42'/>
         </vlan>
       </interface>
       ...
     </devices>

    図16.11 hostdev インターフェースタイプのドメイン XML のサンプル

    MAC アドレスを指定しない場合、他のタイプのインターフェースデバイスの場合と同様に、アドレスは自動的に生成されます。さらに、<virtualport> 要素は、802.11Qgh ハードウェアスイッチ (802.11Qbg (別名「VEPA」) に接続される場合にのみ使用されます。これらのスイッチは現在サポートされていません。
  5. ゲスト仮想マシンを再起動します。

    ステップ 2 でシャットダウンしたゲスト仮想マシンを再起動するために virsh start コマンドを実行します。詳細は、「仮想マシンの起動、再開および復元」を参照してください。
     # virsh start guestVM 
    ゲスト仮想マシンが起動すると、設定済みの MAC アドレスと共に、物理ホストマシンのアダプターによって指定されたネットワークデバイスが表示されます。この MAC アドレスは、ゲスト仮想マシンと物理ホストマシンの起動時に変更されることはありません。

16.2.4. SR-IOV 仮想機能のプールからの PCI デバイス割り当ての設定

特定の仮想機能 (VF) の PCI アドレスをゲストの設定にハードコーディングする上で、2 つの重要な制限があります。
  • 指定した VF は、ゲスト仮想マシンの起動時にはいつでも利用可能な状態でなければなりません。つまり、各 VF を管理者が単一のゲスト仮想マシンに対して永久的に割り当てなければならないことを意味しています (または各ゲスト仮想マシンの起動時に、すべてのゲスト仮想マシンで現在使用されていない VF の PCI アドレスを指定するよう設定ファイルを修正する必要があります)。
  • ゲスト仮想マシンが別のホスト物理マシンに移行する場合、そのホスト物理マシンには、PCI バス上の同じ場所に全く同じハードウェアがなければなりません (または、ここでも起動前にゲスト仮想マシンの設定を変更する必要があります)。
これらの問題は、いずれも SR-IOV デバイスのすべての VF を含むデバイスプールで libvirt ネットワークを作成することによって回避できます。いったんこれが実行されると、このネットワークを参照するようにゲスト仮想マシンを設定できます。ゲストが起動するたびに、単一の VF がプールからゲスト仮想マシンに割り当てられます。ゲスト仮想マシンが停止すると、VF は別のゲスト仮想マシンが使用できるようにプールに戻ります。

手順16.10 デバイスプールの作成

  1. ゲスト仮想マシンをシャットダウンします。

    virsh shutdown コマンドを使用して、ゲスト仮想マシンのシャットダウン (ここで使用される名前は guestVM) を実行します。
    # virsh shutdown guestVM
  2. 設定ファイルを作成します。

    任意のエディターを使用して、passthrough.xml ディレクトリーに XML ファイル (例:/tmp) を作成します。pf dev='eth3' は、お使いの SR-IOV デバイスの物理機能 (PF) の netdev 名に置き換えるようにしてください。
    以下は、物理機能 (PF) をホスト物理マシンの「eth3」に設定し、SR-IOV アダプターのすべての VF のプールを利用可能にするネットワーク定義のサンプルです。
          
    <network>
       <name>passthrough</name> <!-- This is the name of the file you created -->
       <forward mode='hostdev' managed='yes'>
         <pf dev='myNetDevName'/>  <!-- Use the netdev name of your SR-IOV devices PF here -->
       </forward>
    </network>
          

    図16.12 ネットワーク定義の サンプルドメイン XML

  3. 新しい XML ファイルをロードします。

    /tmp/passthrough.xml を直前のステップで作成した XML ファイルの名前と場所に置き換え、以下のコマンドを入力します。
    # virsh net-define /tmp/passthrough.xml
  4. ゲストを再起動します。

    passthrough.xml を直前のステップで作成した XML ファイルの名前に置き換え、以下を実行します。
     # virsh net-autostart passthrough # virsh net-start passthrough 
  5. ゲスト仮想マシンを再起動します。

    最初のステップでシャットダウンしたゲスト仮想マシンを再起動するために virsh start コマンドを実行します (例では、ゲスト仮想マシンのドメイン名として guestVM を使用しています)。詳細は、「仮想マシンの起動、再開および復元」を参照してください。
     # virsh start guestVM 
  6. デバイスのパススルーを開始します。

    単一デバイスのみが表示されていますが、libvirt はゲスト仮想マシンの初回起動時に、PF に関連付けられたすべての VF の一覧を自動的に派生させます。この起動には、以下のようなドメイン XML 内のインターフェース定義が使用されます。
             
    <interface type='network'>
       <source network='passthrough'>
    </interface>
          

    図16.13 インターフェースネットワーク定義のサンプルドメイン XML

  7. 検証します。

    ネットワークを使用する最初のゲストの起動後に virsh net-dumpxml passthrough コマンドを実行して検証することができます。以下のような出力が得られます。
          
    <network connections='1'>
       <name>passthrough</name>
       <uuid>a6b49429-d353-d7ad-3185-4451cc786437</uuid>
       <forward mode='hostdev' managed='yes'>
         <pf dev='eth3'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x10' function='0x1'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x10' function='0x3'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x10' function='0x5'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x10' function='0x7'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x11' function='0x1'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x11' function='0x3'/>
         <address type='pci' domain='0x0000' bus='0x02' slot='0x11' function='0x5'/>
       </forward>
    </network>
          

    図16.14 XML ダンプファイル passthrough の内容

16.2.5. SR-IOV の制限

SR-IOV は、以下のデバイスを使用する場合についてのみ十分なテストが行われています。
  • Intel® 82576NS Gigabit Ethernet Controller (igb ドライバー)
  • Intel® 82576EB Gigabit Ethernet Controller (igb ドライバー)
  • Intel® 82599ES 10 Gigabit Ethernet Controller (ixgbe ドライバー)
  • Intel® 82599EB 10 Gigabit Ethernet Controller (ixgbe ドライバー)
他の SR-IOV デバイスも機能する可能性がありますが、リリース時にはテストを実施していません。

16.3. USB デバイス

このセクションでは、USB デバイスの処理に必要なコマンドを扱います。

16.3.1. ゲスト仮想マシンへの USB デバイスの割り当て

web カメラ、カードリーダー、ディスクドライブ、キーボード、マウスなどのほとんどのデバイスは、USB ポートとケーブルを使ってコンピューターに接続されます。これらのデバイスをゲスト仮想マシンに渡す方法として 2 つの方法があります。
  • USB パススルーの使用 - これには、ゲスト仮想マシンをホストしているホスト物理マシンに、デバイスが物理的に接続されている必要があります。この場合、SPICE は必要ではありません。ホスト上の USB デバイスは、コマンドラインまたは virt-manager を使用してゲストに渡すことができます。virt manager の説明については、「USB デバイスのゲスト仮想マシンへの割り当て」を参照してください。virt-manager の説明は、デバイスのホットプラグ/アンプラグには該当しないことに注意してください。USB デバイスのホットプラグ/アンプラグが必要な場合は、手順20.4「ゲスト仮想マシンが使用する USB デバイスのホットプラグ」を参照してください。
  • USB リダイレクトの使用 - USB リダイレクトは、ホスト物理マシンがデータセンターで実行されている場合に最適に使用されます。ユーザーは、ローカルマシンまたはシンクライアントからゲスト仮想マシンに接続します。このローカルマシンには、1 つの SPICE クライアントがあります。ユーザーは、任意の USB デバイスをシンクライアントに割り当てることができ、SPICE クライアントはデータセンターのホスト物理マシンにこのデバイスをリダイレクトするので、これをシンクライアント上で実行されているゲスト仮想マシンで使用することができます。virt-manager を使用した USB リダイレクトについての説明は、「USB リダイレクト」を参照してください。

16.3.2. USB デバイスのリダイレクトへの制限の設定

フィルターを使って特定のデバイスをリダイレクトから除去するには、フィルタープロパティーを -device usb-redir に渡します。フィルタープロパティーはフィルタールールで構成される文字列を取ります。ルールの形式は次の通りです。
<class>:<vendor>:<product>:<version>:<allow>
特定フィールドのいずれの値も受け入れるようにする場合は、-1 の値を使用します。「|」を区切り文字として使用すると同じコマンドラインで複数のルールを使用することができます。デバイスがルールに渡したいずれの条件にも一致しない場合、そのデバイスのリダイレクトは許可されません。

例16.1 ゲスト仮想マシンでリダイレクトの制限を設ける場合の例

  1. ゲスト仮想マシンを用意します。
  2. 次のコードの抜粋をゲスト仮想マシンのドメイン XML ファイルに追加します。
        <redirdev bus='usb' type='spicevmc'>
          <alias name='redir0'/>
          <address type='usb' bus='0' port='3'/>
        </redirdev>
        <redirfilter>
          <usbdev class='0x08' vendor='0x1234' product='0xBEEF' version='2.0' allow='yes'/>
          <usbdev class='-1' vendor='-1' product='-1' version='-1' allow='no'/>
        </redirfilter>
  3. ゲスト仮想マシンを起動し、次のコマンドを実行して設定の変更を確認します。
    #ps -ef | grep $guest_name
    -device usb-redir,chardev=charredir0,id=redir0,/
    filter=0x08:0x1234:0xBEEF:0x0200:1|-1:-1:-1:-1:0,bus=usb.0,port=3
  4. USB デバイスをホスト物理マシンに差し込み、virt-manager を使ってゲスト仮想マシンに接続します。
  5. メニュー内の USB デバイスの選択 をクリックします。「Some USB devices are blocked by host policy (ホストのポリシーによりブロックされている USB デバイスがあります)」というメッセージが生成されます。確認の OK をクリックし、続行します。
    フィルターが適用されます。
  6. フィルターよるキャプチャーが正しく動作するよう USB デバイスの製造元と製品を確認し、ホスト物理マシンのドメイン XML に次の変更を加えて USBリダイレクトを許可します。
       <redirfilter>
          <usbdev class='0x08' vendor='0x0951' product='0x1625' version='2.0' allow='yes'/>
          <usbdev allow='no'/>
        </redirfilter>
  7. ゲスト仮想マシンを再起動し、virt-viewer を使ってゲスト仮想マシンに接続します。USB デバイスがトラフィックをゲスト仮想マシンにリダイレクトするようになります。

16.4. デバイスコントローラーの設定

ゲスト仮想マシンのアーキテクチャーにより、一部のデバイスバスは、仮想コントローラーに関連付けられた仮想デバイスのグループと共に複数回表示されることがあります。通常、libvirt は明示的な XML マークアップを必要とせずに、このようなコントローラーを自動的に推定できますが、仮想コントローラーの要素を明示的に設定した方がよい場合があります。

  ...
  <devices>
    <controller type='ide' index='0'/>
    <controller type='virtio-serial' index='0' ports='16' vectors='4'/>
    <controller type='virtio-serial' index='1'>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x0a' function='0x0'/>
    </controller>
    ...
  </devices>
  ...

図16.15 仮想コントローラーのドメイン XML サンプル

各コントローラーには必須属性 <controller type> があります。これは、以下のいずかである必要があります。
  • ide
  • fdc
  • scsi
  • sata
  • usb
  • ccid
  • virtio-serial
  • pci
<controller> 要素には、(<controller index> 要素の controller 属性で使用される) バスコントローラーが出現する順序を記述する 10 進整数の必須属性 <address> があります。<controller type ='virtio-serial'> の場合、コントローラー経由で接続できるデバイスの数を制御する 2 つの追加のオプション属性 (portsvectors という名前) があります。
<controller type ='scsi'> の場合、以下の値を取るオプション属性 model モデルがあります。
  • auto
  • buslogic
  • ibmvscsi
  • lsilogic
  • lsisas1068
  • lsisas1078
  • virtio-scsi
  • vmpvscsi
<controller type ='usb'> の場合、以下の値を取るオプション属性 model モデルがあります。
  • piix3-uhci
  • piix4-uhci
  • ehci
  • ich9-ehci1
  • ich9-uhci1
  • ich9-uhci2
  • ich9-uhci3
  • vt82c686b-uhci
  • pci-ohci
  • nec-xhci
USB バスをゲスト仮想マシンに対して明示的に無効にする必要がある場合は、<model='none'> を使用することができることに注意してください。
コントローラー自体が PCI または USB バス上のデバイスである場合、オプションのサブ要素 <address> は、「デバイスのアドレス設定」 に示される形式を使用して、コントローラーとマスターバスとの正確な関係を指定することができます。
オプションのサブ属性 <driver> は、ドライバー固有のオプションを指定することができます。現在、これはコントローラーのキューの数を指定する属性 queues のみをサポートします。パフォーマンスを最大化するには、仮想 CPU (vCPU) の数に一致する値を指定することが推奨されます。
USB コンパニオンコントローラーには、コンパニオンとマスターコントローラーとの正確な関係を指定するためのオプションのサブ要素 <master> があります。コンパニオンコントローラーは、そのマスターと同じバスにあり、コンパニオンの index 値は等しい値である必要があります。
使用できる XML の例を示します。
   
     ...
  <devices>
    <controller type='usb' index='0' model='ich9-ehci1'>
      <address type='pci' domain='0' bus='0' slot='4' function='7'/>
    </controller>
    <controller type='usb' index='0' model='ich9-uhci1'>
      <master startport='0'/>
      <address type='pci' domain='0' bus='0' slot='4' function='0' multifunction='on'/>
    </controller>
    ...
  </devices>
  ...
   

図16.16 USB コントローラーのドメイン XML サンプル

PCI コントローラーには、以下の値を持つことのできるオプションの model 属性があります。
  • pci-root
  • pcie-root
  • pci-bridge
  • dmi-to-pci-bridge
暗黙的な PCI バスを提供するマシンタイプの場合、index='0' が指定された pci-root コントローラーが自動的に追加され、PCI デバイスを使用するために必要になります。pci-root にはアドレスがありません。PCI ブリッジは、デバイスの数が多すぎて model='pci-root' で指定される 1 つのバスに入らない場合や、ゼロより大きい PCI バスの数が指定されている場合に自動的に追加されます。さらに、PCI ブリッジを手動で指定することができますが、それらのアドレスは、すでに指定された PCI コントローラーによって提供される PCI バスのみを参照するものである必要があります。PCI コントローラーの index にギャップがあると、設定が無効になる可能性があります。以下の XML サンプルを <devices> セクションに追加することができます。

  ...
  <devices>
    <controller type='pci' index='0' model='pci-root'/>
    <controller type='pci' index='1' model='pci-bridge'>
      <address type='pci' domain='0' bus='0' slot='5' function='0' multifunction='off'/>
    </controller>
  </devices>
  ...

図16.17 PCI ブリッジのドメイン XML サンプル

暗黙的な PCI Express (PCIe) バスを提供するマシンタイプ (たとえば、Q35 チップセットに基づくマシンタイプ) の場合、index='0' が指定された pcie-root コントローラーがドメインの設定に自動的に追加されます。さらに、pcie-root にはアドレスがありませんが、31 スロット (1-31 までの番号) を提供し、PCIe デバイスを割り当てるためにのみ使用できます。pcie-root コントローラーを持つシステムの標準 PCI デバイスを接続するために、model='dmi-to-pci-bridge' が設定された pci コントローラーが自動的に追加されます。dmi-to-pci-bridge コントローラーは PCIe スロット (pcie-root によって提供される) にプラグインされ、それ自体は 31 の標準 PCI スロット (ホットプラグ不可能) を提供します。ホットプラグ可能な PCI スロットをゲストシステム内で設定するために、pci-bridge コントローラーが自動的に作成され、自動作成される dmi-to-pci-bridge コントローラーのスロットの 1 つに接続され、libvirt で自動判別される PCI アドレスを持つすべてのゲストデバイスが、この pci-bridge デバイス上に置かれます。
   
     ...
  <devices>
    <controller type='pci' index='0' model='pcie-root'/>
    <controller type='pci' index='1' model='dmi-to-pci-bridge'>
      <address type='pci' domain='0' bus='0' slot='0xe' function='0'/>
    </controller>
    <controller type='pci' index='2' model='pci-bridge'>
      <address type='pci' domain='0' bus='1' slot='1' function='0'/>
    </controller>
  </devices>
  ...
   

図16.18 PCIe (PCI express) のドメイン XML サンプル

以下の XML 設定は USB 3.0 / xHCI エミュレーションに使用されます。
   
     ...
  <devices>
    <controller type='usb' index='3' model='nec-xhci'>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x0f' function='0x0'/>
    </controller>
  </devices>
    ...

図16.19 USB3/xHCI デバイスに使用されるドメイン XML の例

16.5. デバイスのアドレス設定

多くのデバイスには、ゲスト仮想マシンに提示されるデバイスが仮想バス上のどこに配置されるかを説明するオプションの <address> サブ要素があります。アドレス (またはアドレス内のオプション属性) が入力で省略されている場合、libvirt は適切なアドレスを生成しますが、レイアウトにより多くの制御が必要な場合は明示的なアドレスが必要になります。<address> 要素を含むドメイン XML デバイスのサンプルについては、図16.9「PCI デバイス割り当ての XML サンプル」 を参照してください。
すべてのアドレスには、デバイスが置かれるバスを記述する必須属性 type があります。指定されるデバイスに使用するアドレスを選択することは、デバイスおよびゲスト仮想マシンのアーキテクチャーによって部分的に制限されます。たとえば、<disk> デバイスは type='drive' を使用し、<console> デバイスは、i686 または x86_64 ゲスト仮想マシンのアーキテクチャーで type='pci' を使用します。さらに、各アドレスの type には、表で説明されるようにデバイスを配置するバス上の場所を制御する追加のオプション属性があります。

表16.1 サポートされているデバイスアドレスのタイプ

アドレスタイプ説明
type='pci'PCI アドレスには以下の追加属性が含まれます。
  • domain (2 バイト 16 進数整数。現在 qemu で使用されていません)
  • bus (0 から 0xff までの 16 進数値)
  • slot (0x0 から 0x1f までの 16 進数値)
  • function (0 から 7 までの値)
  • multifunction は、PCI コントロールレジスターに特定のスロット/機能のマルチファンクションビットをオンにするように制御します。この属性は、デフォルトで 'off' になりますが、マルチファンクションが使用されるスロットのファンクション 0 では 'on' に設定する必要があります。
type='drive'ドライブアドレスには、以下の追加属性が含まれます。
  • controller (2 桁のコントローラー番号)
  • bus (2 桁のバス番号)
  • target (2 桁のバス番号)
  • unit (バス上の 2 桁のユニット番号)
type='virtio-serial'それぞれの virtio-serial アドレスには以下の追加属性が含まれます。
  • controller (2 桁のコントローラー番号)
  • bus (2 桁のバス番号)
  • slot (バス内の 2 桁のスロット)
type='ccid'スマートカードに使用される CCID アドレスには、以下の追加属性が含まれます。
  • bus (2 桁のバス番号)
  • slot 属性 (バス内の 2 桁のスロット)
type='usb'USB アドレスには以下の追加属性が含まれます。
  • bus (0 から 0xfff までの 16 進数)
  • port (1.2 または 2.1.3.1 などの最高 4 つのオクテットからなるドット区切りの表記)
type='isa'ISA アドレスには以下の追加属性が含まれます。
  • iobase
  • irq

16.6. 乱数ジェネレーターデバイス

乱数ジェネレーターは、オペレーティングシステムのセキュリティーにおいて非常に重要です。仮想オペレーティングシステムのセキュリティーを保護するために、Red Hat Enterprise Linux 7 には要求時に新規エントロピーをゲストに提供できる virtio-rng という仮想ハードウェアの乱数ジェネレーターが含まれます。
ホスト物理マシン上で、ハードウェア RNG インターフェースは /dev/hwrng に chardev を作成します。次に、この chardev が開かれ、ホスト物理マシンからエントロピーを取得するために読み込まれます。rngd デーモンと対で使用されると、ホスト物理マシンのエントロピーは、乱数度の主なソースであるゲスト仮想マシンの /dev/random に送られます。
乱数ジェネレーターの使用は、キーボード、マウスおよびその他の入力がゲスト仮想マシンのエントロピーを十分に生成しない場合にとくに便利です。仮想乱数ジェネレーターデバイスは、ホスト物理マシンからゲスト仮想マシンのオペレーティングシステムへのエントロピーの通過を許可します。このデバイスは Windows および KVM ゲスト仮想マシンの両方で利用できます。この手順は、コマンドライン または virt-manager インターフェース を使用して実行できます。virtio-rng についての詳細は、Red Hat Enterprise Linux Virtual Machines: Access to Random Numbers Made Easy を参照してください。

手順16.11 仮想マシンマネージャーを使用した virtio-rng の実装

  1. ゲスト仮想マシンをシャットダウンします。
  2. ゲスト仮想マシンを選択してから、編集 メニューで 仮想マシンの詳細 を選択し、指定されたゲスト仮想マシンの詳細ウィンドウを開きます。
  3. ハードウェアを追加 ボタンをクリックします。
  4. 新しい仮想ハードウェアを追加 ウィンドウで、RNG を選択し、Random Number Generator ウィンドウを開きます。
    乱数ジェネレーターウィンドウ

    図16.20 乱数ジェネレーターウィンドウ

    目的のパラメーターを入力したら 完了 をクリックします。パラメーターについては、virtio-rng 要素 で説明されています。

手順16.12 コマンドラインツールを使用した virtio-rng の実装

  1. ゲスト仮想マシンをシャットダウンします。
  2. virsh edit domain-name コマンドを使用し、目的のゲスト仮想マシンの XML ファイルを開きます。
  3. 以下を含めるように <devices> 要素を編集します。
    
      ...
      <devices>
        <rng model='virtio'>
          <rate period='2000' bytes='1234'/>
          <backend model='random'>/dev/random</backend>
          <!-- OR -->
          <backend model='egd' type='udp'>
            <source mode='bind' service='1234'/>
            <source mode='connect' host='1.2.3.4' service='1234'/>
          </backend>
        </rng>
      </devices>
      ...

    図16.21 乱数ジェネレーターデバイス

    乱数ジェネレーターデバイスは以下の XML 属性/要素を許可します。

    virtio-rng 要素

    • <model>: 必須の model 属性は、提供される RNG デバイスのタイプを指定します。
    • <backend model>: <backend> 要素は、ゲストに使用されるエントロピーのソースを指定します。ソースモデルは model 属性を使用して設定されます。サポートされるソースモデルには、'random' および 'egd' が含まれます。
      • <backend model='random'> - この <backend> タイプは、ブロック以外のキャラクターデバイスを入力として予想します。これらのデバイス例には、/dev/random および /dev/urandom があります。ファイル名は <backend> 要素のコンテンツとして指定されます。ファイル名が指定されていないと、ハイパーバイザーのデフォルトが使用されます。
      • <backend model='egd'> - このバックエンドは EGD プロトコルを使用してソースに接続されます。ソースはキャラクターデバイスとして指定されます。詳細は、キャラクターデバイスのホスト物理マシンインターフェースを参照してください。

16.7. GPU デバイスの割り当て

GPU をゲストに割り当てるには、以下の方法の 1 つを使用します。
  • GPU PCI デバイスの割り当て: この方法を使用すると、ホストから GPU デバイスを削除し、1 つのゲストに割り当てることができます。
  • NVIDIA vGPU の割り当て: この方法では、物理 GPU から複数の 媒介デバイス (mediated device) を作成することができ、これらのデバイスを仮想 GPU として複数のゲストに割り当てすることができます。これは一部の NVIDIA GPU でのみサポートされ、1 つの媒介 デバイスを 1 つのゲストのみに割り当てできます。

16.7.1. GPU PCI デバイスの割り当て

Red Hat Enterprise Linux 7 では、VGA 以外のグラフィックデバイスとして以下に記載されている PCI ベースの GPU デバイスの割り当てをサポートします。
  • NVIDIA Quadro K シリーズ、M シリーズ、および P シリーズ (モデル 2000 シリーズ以降)
  • NVIDIA GRID K シリーズ
  • NVIDIA Tesla K シリーズおよび M シリーズ
現在、標準のエミュレートされた VGA インターフェースのほかに、2 つまでの GPU を仮想マシンに割り当てることができます。エミュレートされた VGA は起動前およびインストールに使用され、NVIDIA グラフィックスドライバーがロードされると、NVIDIA GPU に引き継がれます。
GPU をゲスト仮想マシンに割り当てるには、IOMMU (I/O メモリー管理ユニット) をホストマシン上で有効にし、lspci コマンドを使用して GPU デバイスを特定する必要があります。さらに、デバイスの割り当てをホストから解除してゲストに割り当て、ゲストで Xorg を設定する必要もあります。以下の手順を参照してください。

手順16.13 ホストマシンカーネルの IOMMU サポートを有効にします。

  1. カーネルコマンドラインを編集します。

    Intel VT-d システムの場合、intel_iommu=on および iommu=pt パラメーターをカーネルコマンドラインに追加して IOMMU をアクティブにします。AMD-Vi システムの場合、必要なオプションは amd_iommu=pt になります。このオプションを有効にするには、以下のように GRUB_CMDLINX_LINUX 行を編集するか、これを /etc/sysconfig/grub 設定ファイルに追加します。
    GRUB_CMDLINE_LINUX="rd.lvm.lv=vg_VolGroup00/LogVol01
    vconsole.font=latarcyrheb-sun16 rd.lvm.lv=vg_VolGroup_1/root
    vconsole.keymap=us $([ -x /usr/sbin/rhcrashkernel-param ]  &&
    /usr/sbin/rhcrashkernel-param || :) rhgb quiet intel_iommu=on iommu=pt"

    注記

    IOMMU についての詳細は、付録E IOMMU グループの使用 を参照してください。
  2. ブートローダー設定の再生成

    カーネルコマンドラインの変更を適用するには、grub2-mkconfig を使用してブートローダーの設定を再生成します。
    # grub2-mkconfig -o /etc/grub2.cfg
    UEFI ベースのホストの場合、ターゲットファイルは /etc/grub2-efi.cfg であることに注意してください。
  3. ホストを再起動します。

    変更を反映するには、ホストマシンを再起動します。
    # reboot

手順16.14 GPU デバイスを、ホスト物理マシンドライバーへのバインドから除外する

GPU 割り当ての場合、ホストドライバーはデバイスの動的なバインド解除をサポートしないことが多いため、デバイスをホストドライバーへのバインドから除外することをお勧めします。
  1. PCI バスアドレスを特定します。

    PCI バスアドレスとデバイスの ID を特定するには、以下の lspci コマンドを実行します。この例では、NVIDIA Quadro または GRID カードなどの VGA コントローラーが使用されます。
    # lspci -Dnn | grep VGA
    0000:02:00.0 VGA compatible controller [0300]: NVIDIA Corporation GK106GL [Quadro K4000] [10de:11fa] (rev a1)
    結果の検索は、このデバイスの PCI バスアドレスが 0000:02:00.0 であることを示し、デバイスの PCI ID が 10de:11fa であることを示しています。
  2. ネイティブのホストマシンドライバーが GPU デバイスを使用しないようにします。

    ネイティブのホストマシンドライバーが GPU デバイスを使用しないようにするには、pci-stub ドライバーで PCI ID を使用します。これを実行するには、/etc/sysconfig/grub 設定ファイルにある GRUB_CMDLINX_LINUX 行に、PCI ID を値として pci-stub.ids オプションを追加します。例を以下に示します。
    GRUB_CMDLINE_LINUX="rd.lvm.lv=vg_VolGroup00/LogVol01
    vconsole.font=latarcyrheb-sun16 rd.lvm.lv=vg_VolGroup_1/root
    vconsole.keymap=us $([ -x /usr/sbin/rhcrashkernel-param ]  &&
    /usr/sbin/rhcrashkernel-param || :) rhgb quiet intel_iommu=on iommu=pt pci-stub.ids=10de:11fa"
    pci-stub 用に追加の PCI ID を追加するには、単にそれらをコンマで区切ります。
  3. ブートローダー設定の再生成

    grub2-mkconfig を使用してブートローダー設定を再生成し、このオプションが含まれるようにします。
    # grub2-mkconfig -o /etc/grub2.cfg
    UEFI ベースのホストの場合、ターゲットファイルは /etc/grub2-efi.cfg であることに注意してください。
  4. ホストマシンを再起動します。

    変更を反映するために、ホストマシンを再起動します。
    # reboot

手順16.15 任意設定: GPU IOMMU 設定の編集

GPU デバイスを割り当てる前に、ゲスト上で GPU が適切に動作するよう IOMMU 設定の変更が必要になることがあります。
  1. GPU の XML 情報の表示

    GPU の設定を XML 形式で表示するには、最初に pci_ を追加し、区切り文字をアンダースコアに変換して、PCI バスアドレスを libvirt 対応の形式に変換する必要があります。たとえば、0000:02:00.0 バスアドレス (以前の手順 で取得) と特定される GPU PCI デバイスは pci_0000_02_00_0 になります。virsh nodedev-dumpxml でデバイスの libvirt アドレスを使用して、XML 設定を表示します。
    # virsh nodedev-dumpxml pci_0000_02_00_0
    
    <device>
     <name>pci_0000_02_00_0</name>
     <path>/sys/devices/pci0000:00/0000:00:03.0/0000:02:00.0</path>
     <parent>pci_0000_00_03_0</parent>
     <driver>
      <name>pci-stub</name>
     </driver>
     <capability type='pci'>
      <domain>0</domain>
      <bus>2</bus>
      <slot>0</slot>
      <function>0</function>
      <product id='0x11fa'>GK106GL [Quadro K4000]</product>
      <vendor id='0x10de'>NVIDIA Corporation</vendor>
         <!-- pay attention to the following lines -->
      <iommuGroup number='13'>
       <address domain='0x0000' bus='0x02' slot='0x00' function='0x0'/>
       <address domain='0x0000' bus='0x02' slot='0x00' function='0x1'/>
      </iommuGroup>
      <pci-express>
       <link validity='cap' port='0' speed='8' width='16'/>
       <link validity='sta' speed='2.5' width='16'/>
      </pci-express>
     </capability>
    </device>
    XML の <iommuGroup> 要素に注目してください。iommuGroup は、IOMMU 機能および PCI バストポロジーのために他のデバイスから分離されているとみなされるデバイスのセットを示します。iommuGroup 内のすべてのエンドポイントデバイス (PCIe root ポート、ブリッジ、またはスイッチポートではないデバイス) は、ゲストに割り当てるためにネイティブのホストドライバーのバインドを解除する必要があります。上記の例では、グループは GPU デバイス (0000:02:00.0) およびコンパニオンオーディオデバイス (0000:02:00.1) で構成されています。詳細は、付録E IOMMU グループの使用 を参照してください。
  2. IOMMU 設定の調整

    この例では、レガシーの中断サポートにおけるハードウェアの問題が原因で、NVIDIA オーディオ機能の割り当てはサポートされません。さらに、通常 GPU 自体がないと GPU オーディオ機能は役に立ちません。よって、GPU をゲストに割り当てるには、最初にオーディオ機能のネイティブホストドライバーへの割り当てを解除する必要があります。これは、以下の方法の 1 つを使用して行えます。

手順16.16 GPU の割り当て

以下の方法の 1 つを使用して、GPU をゲストに割り当てできます。
  1. 仮想マシンマネージャー インターフェースを使用します。詳細は 「virt-manager を使用した PCI デバイスの割り当て」 を参照してください。
  2. GPU の XML 設定フラグメントを作成し、virsh attach-device で割り当てます。
    1. 以下のような XML をデバイス用に作成します。
      
      <hostdev mode='subsystem' type='pci' managed='yes'>
       <driver name='vfio'/>
       <source>
        <address domain='0x0000' bus='0x02' slot='0x00' function='0x0'/>
       </source>
      </hostdev>
    2. これをファイルに保存し、virsh attach-device [domain] [file] --persistent を実行して XML がゲストの設定に含まれるようにします。ゲストマシン内の既存のエミュレートされたグラフィックスデバイスのほかに、割り当てられた GPU が追加されることに注意してください。割り当てられた GPU は、仮想マシン内のセカンダリーグラフィックスデバイスとして処理されます。プライマリーグラフィックスデバイスとしての割り当てはサポートされず、ゲストの XML 内のエミュレートされたグラフィックスデバイスは削除することができません。
  3. virsh edit コマンドを使用してゲストの XML 設定を編集し、適切な XML セグメントを手作業で追加します。

手順16.17 ゲスト上の Xorg 設定の編集

ゲスト上の GPU の PCI バスアドレスはホスト上のものとは異なります。ホストが GPU を適切に使用できるようにするには、割り当てられた GPU アドレスを使用するようゲストの Xorg 表示サーバーを設定します。
  1. ゲストで lspci コマンドを使用し、GPU の PCI バスアドレスを検出します。
    # lspci | grep VGA
    00:02.0 VGA compatible controller: Device 1234:111
    00:09.0 VGA compatible controller: NVIDIA Corporation GK106GL [Quadro K4000] (rev a1)
    この例では、バスアドレスは 00:09.0 になります。
  2. ゲストの /etc/X11/xorg.conf ファイルに BusID を追加し、検出したアドレスを次のように調整します。
    		Section "Device"
    		    Identifier     "Device0"
    		    Driver         "nvidia"
    		    VendorName     "NVIDIA Corporation"
    		    BusID          "PCI:0:9:0"
    		EndSection

    重要

    手順 1 で検出されたバスアドレスは 16 進数であるため、区切り文字の間にある値を 10 進数に変換する必要があります。たとえば、00:0a.0 は PCI:0:10:0 に変換する必要があります。

注記

ゲスト内で割り当てられた NVIDIA GPU を使用する場合、NVIDIA ドライバーのみがサポートされます。他のドライバーは機能せず、エラーを出す可能性があります。Red Hat Enterprise Linux7 ゲストの場合、nouveau ドライバーが、インストール時にカーネルコマンドラインでオプションの modprobe.blacklist=nouveau を使用することでブラックリスト化される可能性があることに注意してください。他のゲスト仮想マシンについての情報は、オペレーティングシステム固有のドキュメントを参照してください。
ゲストオペレーティングシステムに応じて、NVIDIA ドライバーがロードされた状態で、ゲストはエミュレートされたグラフィックスと割り当てられたグラフィックスの両方を同時にサポートするか、またはエミュレートされたグラフィックスを無効にすることができます。割り当てられたグラフィックスフレームバッファーは、virt-manager などのアプリケーションでは提供されないことに注意してください。割り当てられた GPU が物理ディスプレイに接続されていない場合、ゲストベースのリモートソリューションが GPU デスクトップにアクセスするために必要になる場合があります。すべての PCI デバイス割り当ての場合と同様、割り当てられた GPU を持つゲストの移行はサポートされておらず、それぞれの GPU は単一ゲストによって排他的に所有されます。ゲストオペレーティングシステムにより、GPU のホットプラグサポートを利用できる場合があります。

16.7.2. NVIDIA vGPU の割り当て

NVIDIA vGPU の機能は、物理 GPU デバイスを 媒介デバイス (mediated device) と呼ばれる複数の仮想デバイスに分割することができます。媒介デバイスは仮想 GPU として複数のゲストに割り当てすることができます。そのため、これらのゲストは 1 つの物理 GPU のパフォーマンスを共有します。

重要

この機能は、限定された NVIDIA GPU のセットでのみ使用できます。これらのデバイスの最新リストは、NVIDIA GPU ソフトウェアのドキュメント を参照してください。

NVIDIA vGPU の設定

vGPU を設定するには、最初に GPU デバイスの NVIDIA vGPU ドライバーを取得し、媒介デバイスを作成した後、目的のゲストマシンに割り当てる必要があります。
  1. NVIDIA vGPU ドライバーを取得し、システムにインストールします。手順は、NVIDIA のドキュメント を参照してください。
  2. NVIDIA ソフトウェアインストーラーが /etc/modprobe.d/nvidia-installer-disable-nouveau.conf ファイルを作成しなかった場合は、/etc/modprobe.d/ ディレクトリーに .conf ファイル (ファイル名は自由) を作成します。このファイルに以下の行を追加します。
    blacklist nouveau
    options nouveau modeset=0
  3. 現在のカーネルの初期 RAM ディスクを再生成し、再起動します。
    # dracut --force
    # reboot
    サポートされる以前のカーネルバージョンを媒介デバイスに使用する必要がある場合、インストールされたすべてのカーネルバージョンの初期 RAM ディスクを再生成します。
    # dracut --regenerate-all --force
    # reboot
  4. nvidia_vgpu_vfio モジュールがカーネルによってロードされ、nvidia-vgpu-mgr.service サービスが稼働中であることを確認します。
    # lsmod | grep nvidia_vgpu_vfio
    nvidia_vgpu_vfio 45011 0
    nvidia 14333621 10 nvidia_vgpu_vfio
    mdev 20414 2 vfio_mdev,nvidia_vgpu_vfio
    vfio 32695 3 vfio_mdev,nvidia_vgpu_vfio,vfio_iommu_type1
    # systemctl status nvidia-vgpu-mgr.service
    nvidia-vgpu-mgr.service - NVIDIA vGPU Manager Daemon
       Loaded: loaded (/usr/lib/systemd/system/nvidia-vgpu-mgr.service; enabled; vendor preset: disabled)
       Active: active (running) since Fri 2018-03-16 10:17:36 CET; 5h 8min ago
     Main PID: 1553 (nvidia-vgpu-mgr)
     [...]
  5. デバイス UUID を /sys/class/mdev_bus/pci_dev/mdev_supported_types/type-id/create に書き込みます。pci_dev はホスト GPU の PCI アドレスに置き換え、type-id はホスト GPU タイプの ID に置き換えます。
    以下の例は、NVIDIA Tesla P4 カード上に nvidia-63 vGPU タイプの媒介デバイスを作成する方法を表しています。
    # uuidgen
    30820a6f-b1a5-4503-91ca-0c10ba58692a
    # echo "30820a6f-b1a5-4503-91ca-0c10ba58692a" > /sys/class/mdev_bus/0000:01:00.0/mdev_supported_types/nvidia-63/create
    特定のデバイスの type-id 値については、仮想 GPU ソフトウェアのドキュメント の「section 1.3.1. Virtual GPU Types」を参照してください。GRID P4-2Q などの Q シリーズの NVIDIA vGPU のみが GPU タイプの媒介デバイスとして Linux ゲストでサポートされることに注意してください。
  6. 以下の行を、vGPU リソースを共有するゲストの XML 設定にある <devices/> セクションに追加します。前のステップで uuidgen コマンドによって生成された UUID 値を使用します。各 UUID は 1 度に 1 つのゲストのみに割り当てできます。
    
    <hostdev mode='subsystem' type='mdev' managed='no' model='vfio-pci'>
      <source>
        <address uuid='30820a6f-b1a5-4503-91ca-0c10ba58692a'/>
      </source>
    </hostdev>
    

    重要

    vGPU の媒介デバイスが割り当てられたゲストで適切に動作するようにするには、ゲストに NVIDIA vGPU ゲストのソフトウェアライセンスを設定する必要があります。詳細および手順は、NVIDIA 仮想 GPU ソフトウェアのドキュメント を参照してください。

NVIDIA vGPU デバイスの削除

媒介の vGPU デバイスを削除するには、デバイスがアクティブでない状態で以下のコマンドを使用します。uuid はデバイスの UUID に置き換えます (例: 30820a6f-b1a5-4503-91ca-0c10ba58692a)。
# echo 1 > /sys/bus/mdev/devices/uuid/remove
ゲストが現在使用している vGPU デバイスを削除しようとすると、以下のエラーが発生します。
echo: write error: Device or resource busy

NVIDIA vGPU 機能のクエリー

指定タイプの媒介デバイスをいくつ作成できるかなど、システムの媒介デバイスに関する追加情報を取得するには、virsh nodedev-list --cap mdev_types または virsh nodedev-dumpxml コマンドを使用します。たとえば、以下は Tesla P4 カードで利用可能な vGPU タイプを表示します。

$ virsh nodedev-list --cap mdev_types
pci_0000_01_00_0
$ virsh nodedev-dumpxml pci_0000_01_00_0
<...>
  <capability type='mdev_types'>
    <type id='nvidia-70'>
      <name>GRID P4-8A</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>1</availableInstances>
    </type>
    <type id='nvidia-69'>
      <name>GRID P4-4A</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>2</availableInstances>
    </type>
    <type id='nvidia-67'>
      <name>GRID P4-1A</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>8</availableInstances>
    </type>
    <type id='nvidia-65'>
      <name>GRID P4-4Q</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>2</availableInstances>
    </type>
    <type id='nvidia-63'>
      <name>GRID P4-1Q</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>8</availableInstances>
    </type>
    <type id='nvidia-71'>
      <name>GRID P4-1B</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>8</availableInstances>
    </type>
    <type id='nvidia-68'>
      <name>GRID P4-2A</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>4</availableInstances>
    </type>
    <type id='nvidia-66'>
      <name>GRID P4-8Q</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>1</availableInstances>
    </type>
    <type id='nvidia-64'>
      <name>GRID P4-2Q</name>
      <deviceAPI>vfio-pci</deviceAPI>
      <availableInstances>4</availableInstances>
    </type>
  </capability>
</...>

NVIDIA vGPU のリモートデスクトップストリーミングサービス

Red Hat Enterprise Linux 7 上の NVIDIA vGPU 機能とテスト済みのリモートデスクトップストリーミングサービスは次のとおりです。
  • HP-RGS
  • Mechdyne TGX: 現在 Windows Server 2016 ゲストで Mechdyne TGX を使用することはできません。
  • NICE DCV: このストリーミングサービスを使用する場合、動的解像度を使用すると真っ黒な画面が表示されることがあるため、Red Hat は固定解像度設定の使用を推奨します。

第17章 仮想ネットワークの構築

本章では、 libvirt を使った仮想ネットワークの作成、 起動、停止、削除、変更などを行なう際に理解しておく必要がある概念について説明します。
詳細は libvirt についての参照情報の章を参照してください。

17.1. 仮想ネットワークのスイッチ

Libvirt 仮想ネットワークでは 仮想ネットワークスイッチ という概念を利用します。仮想ネットワークのスイッチは、ソフトウェアで構成され、ホスト物理マシンサーバー上で動作します。このスイッチに仮想マシン群 (ゲスト) が接続し、各ゲストのネットワークトラフィックはこのスイッチを経由することになります。
ゲストを 2 つ持つ仮想ネットワークの例

図17.1 ゲストを 2 つ持つ仮想ネットワークの例

Linux ホスト物理マシンのサーバーは、 仮想ネットワークスイッチをネットワークインターフェースとして表します。libvirtd デーモン (libvirtd) を最初にインストールし、起動する際に、仮想ネットワークスイッチを表すデフォルトのネットワークインターフェースは virbr0 になります。
上記の virbr0 インターフェースは、他のインターフェースと同様 ip コマンドで表示させることができます。
 $ ip addr show virbr0
 3: virbr0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN
     link/ether 1b:c4:94:cf:fd:17 brd ff:ff:ff:ff:ff:ff
     inet 192.168.122.1/24 brd 192.168.122.255 scope global virbr0

17.2. ブリッジモード

ブリッジモード の使用時には、すべてのゲスト仮想マシンがホスト物理マシンとして同一サブネット内に表示されます。同一の物理ネットワーク上にある他の物理マシンはこれらの仮想マシンを認識し、仮想マシンにアクセス可能です。ブリッジングは、OSI ネットワークモデルの第 2 層で動作します。
ブリッジモードの仮想ネットワークスイッチ

図17.2 ブリッジモードの仮想ネットワークスイッチ

複数の物理インターフェースは ボンド で結合し、ハイパーバイザー上で使用することが可能です。このボンドはブリッジに追加され、ゲスト仮想マシンもブリッジに追加されます。ただし、ボンディングドライバーにはいくつかの操作モードがあり、このなかで仮想ゲストマシンが使用されているブリッジと機能するものは、2、3 しかありません。

警告

ブリッジモードを使う場合、ゲスト仮想マシンと使用すべきボンディングモードは、Mode 1、Mode 2、および Mode 4 のみです。Modes 0、3、5、または 6 を使用すると、接続が切断される可能性があります。また、アドレス解決プロトコル (ARP) による監視は機能しないので、ボンディングモードの監視にはメディア非依存インタフェース (MII) による監視を使用してください。
ボンディングモードに関する詳細情報は、関連するナレッジベースの記事 か『Red Hat Enterprise Linux 7 ネットワークガイド』を参照してください。
ブリッジネットワークモードを設定するのに使われる bridge_opts パラメーターの詳細の説明については、『Red Hat Virtualization 管理ガイド』を参照してください。

17.3. Network Address Translation

デフォルトでは、仮想ネットワークスイッチは NAT モードで動作します。Source-NAT (SNAT) や Destination-NAT (DNAT) ではなく IP マスカレードを使用します。IP マスカレードを使用すると、接続しているゲストが外部ネットワークとの通信にホスト物理マシンの IP アドレスを使用できるようになります。仮想ネットワークスイッチが NAT モードで動作している場合、デフォルトではホスト物理マシンの外部にあるコンピューターはホスト内部にあるゲストと通信できません。これを以下の図で示します。
ゲストを 2 つ持つ仮想ネットワークスイッチで NAT を使用している例

図17.3 ゲストを 2 つ持つ仮想ネットワークスイッチで NAT を使用している例

警告

仮想ネットワークスイッチは iptables のルールで設定された NAT を使用します。 スイッチが稼働したままの状態でこれらのルールを編集することは推奨できません。正しくないルールが原因でスイッチが通信を行えなくなる恐れがあります。
スイッチが実行されていない場合、以下を実行して、ポートのマスカレード範囲を作成するために、forward mode NAT のパブリック IP 範囲を設定することができます。
# iptables -j SNAT --to-source [start]-[end]

17.4. DNS と DHCP

IP 情報は DHCP 経由でゲストに割り当てることができます。この割り当てを行うためアドレスのプールを仮想ネットワークスイッチに割り当てることができます。libvirt は dnsmasq プログラムを使用してこれを行います。dnsmasq のインスタンスは、このインスタンスを必要とする仮想ネットワークスイッチに自動的に設定され、起動されます。
dnsmasq を実行している仮想ネットワークスイッチ

図17.4 dnsmasq を実行している仮想ネットワークスイッチ

17.5. ルーティングモード

ルーティングモード を使用する場合、仮想スイッチはホスト物理マシンにつながっている物理的な LAN に接続され、NAT を使わずにトラフィックの受け渡しを行います。仮想スイッチによりすべてのトラフィックが検査され、またネットワークパケット内に含まれる情報がルーティングを決定するために使用されます。このモードを使用すると、仮想マシンはすべてそれ自体のサブネット内に存在することになり、仮想スイッチ経由でルーティングが行われます。ただし、手作業で物理的なルーター設定を行わないと、物理的なネットワーク上に存在する他のホスト物理マシンからはこれらの仮想マシンは認識されないため、アクセスすることもできません。このため、このモードが常に理想的であるとは言えません。ルーティングモードは OSI ネットワークモデルの第 3 層で動作します。
ルーティングモードの仮想ネットワークスイッチ

図17.5 ルーティングモードの仮想ネットワークスイッチ

17.6. 隔離モード

隔離モード を使用する場合、仮想スイッチに接続されているゲスト同士の通信およびホスト物理マシンとの通信は可能ですが、トラフィックはホスト物理マシンの外側へは通過していきません。また、ホスト物理マシンの外側からのトラフィックを受け取ることもできません。このモードで dnsmasq を使用するには、DHCP などの基本的な機能が必要になります。ただし、このネットワークを物理的なネットワークと切り離しても、DNS 名の解決は行われます。したがって、DNS 名は解決できるのに ICMP エコー要求 (ping) のコマンドは失敗するといった状況になる可能性があります。
隔離モードの仮想ネットワークスイッチ

図17.6 隔離モードの仮想ネットワークスイッチ

17.7. デフォルト設定

libvirtd デーモン (libvirtd) の初回インストール時には、NAT モードの仮想ネットワークスイッチ初期設定が含まれます。この設定を使用すると、インストールしているゲストがホスト物理マシンを経由して外部ネットワークと通信できるようになります。以下の図は、この libvirtd のデフォルト設定を表しています。
libvirt のデフォルトネットワーク設定

図17.7 libvirt のデフォルトネットワーク設定

注記

仮想ネットワークを特定の物理インターフェースに制限することができます。これは、複数のインタフェース (eth0eth1eth2 など) を持つ物理システムの場合に役立ちます。また、ルーティングモードおよび NAT モードの場合にのみ役立ち、dev=<interface> オプションで指定できます。また、新しい仮想ネットワークを作成する際に virt-manager で指定することもできます。

17.8. 一般的な事例

本セクションでは、複数の異なるネットワークモードを紹介し、その使用例を説明します。

17.8.1. ブリッジモード

ブリッジモードは、OSI モデルの第 2 層で作動します。これのモードの使用時には、ゲスト仮想マシンすべてが同一サブネット上でホスト物理マシンとして表示されます。ブリッジモードの一般的な使用例には、以下のものがあります。
  • ホスト物理マシンとともに既存ネットワーク内でゲスト仮想マシンをデプロイし、エンドユーザーに対して仮想マシンと物理マシンの違いを明らかにする。
  • 既存の物理ネットワーク設定に変更を加えずにゲスト仮想マシンをデプロイする。
  • 既存の物理ネットワークに容易にアクセス可能である必要があるゲスト仮想マシンをデプロイする。ゲスト仮想マシンを、DHCP などの既存のブロードキャストドメイン内でサービスにアクセスする必要のある物理ネットワーク上に配置する。
  • ゲスト仮想マシンを VLAN が使用されている既存のネットワークに接続する。

17.8.2. ルーティングモード

DMZ

セキュリティー上の理由で制御されたサブネットワーク内に 1 つ以上のノードがあるネットワークについて考えてみましょう。こうした特殊なサブネットワークの導入は一般的に行われており、このサブネットワークは DMZ と呼ばれています。レイアウトの詳細は、以下の図を参照してください。

DMZ の設定例

図17.8 DMZ の設定例

DMZ 内のホスト物理マシンは、通常 WAN (外部) ホスト物理マシンおよび LAN (内部) ホスト物理マシンにサービスを提供します。管理や運営の方法は場所ごとにまたセキュリティーや信頼できるレベルよって異なる点を考慮すると、さまざまな場所から DMZ 内のホストにアクセスする必要のあるこのような環境では ルーティングモードが最適な設定となります。
仮想サーバーのホスティング

仮想サーバーホスティング会社を例に見てみましょう。この仮想サーバーホスティング会社は複数のホスト物理マシンを有し、ホスト物理マシンごとに物理的なネットワーク接続が 2 つあります。1 つのインターフェースは管理と経理用に使用され、もう 1 つのインターフェースは仮想マシンの接続に使用されます。各ゲストは独自のパブリック IP アドレスを持っていますが、ホスト物理マシンはプライベートの IP アドレスを使用します。これは、内部の管理者のみがゲストの管理を行うようにするためです。この状況を理解するために、以下の図を参照してください。

仮想サーバーホスティングの設定例

図17.9 仮想サーバーホスティングの設定例

17.8.3. NAT モード

NAT (Network Address Translation) モードはデフォルトのモードです。直接ネットワークの可視性を必要としないテストなどに使用することができます。

17.8.4. 隔離モード

隔離モードを使用すると、 通信を行うことができるのは仮想マシン同士のみに限ることができます。仮想マシンは物理的なネットワークでの通信は行えません。

17.9. 仮想ネットワークの管理

システムで仮想ネットワークを設定する
  1. 編集 メニューから 接続の詳細 を選択します。
  2. 接続の詳細 メニューが開きます。 仮想ネットワーク タブをクリックします。
    仮想ネットワークの設定

    図17.10 仮想ネットワークの設定

  3. 利用可能な仮想ネットワークはすべてメニューの左側に一覧表示されます。仮想ネットワークの設定を変更するには、このボックスで該当する仮想ネットワークを選択し、適切に編集します。

17.10. 仮想ネットワークの作成

仮想マシンマネージャー (virt-manager) を使用してシステム上に仮想ネットワークを作成する方法:
  1. 接続の詳細 メニューから 仮想ネットワーク タブを開きます。(+) マークのアイコンで表されている ネットワークの追加 ボタンをクリックします。詳細は 「仮想ネットワークの管理」 を参照してください。
    仮想ネットワークの設定

    図17.11 仮想ネットワークの設定

    新しい仮想ネットワークの作成 ウィンドウが開きます。進む をクリックして先に進みます。
    新規の仮想ネットワークの名前の入力

    図17.12 新規の仮想ネットワークの名前の入力

  2. 仮想マシンの名前を入力して 進む をクリックします。
    IPv4 アドレス空間の選択

    図17.13 IPv4 アドレス空間の選択

  3. IPv4 ネットワークアドレス空間の定義を可能にする チェックボックスにチェックを入れます。
    ネットワーク フィールドに仮想ネットワークの IPv4 アドレス空間を入力します。
    DHCPv4 を有効化 チェックボックスにチェックを付けます。
    IP アドレス範囲の 開始終了 を指定して仮想ネットワークの DHCP 範囲を定義します。
    IPv4 アドレス空間の選択

    図17.14 IPv4 アドレス空間の選択

    進む をクリックして先に進みます。
  4. IPv6 を有効にする場合、IPv6 ネットワークアドレス空間の定義を可能にする にチェックを付けます。
    IPv6 の有効化

    図17.15 IPv6 の有効化

    追加のフィールドが「新しい仮想ネットワークを作成」ウィンドウに表示されます。
    IPv6 の設定

    図17.16 IPv6 の設定

    ネットワーク フィールドに IPv6 アドレスを入力します。
  5. DHCPv6 を有効にする場合、DHCPv6 を有効化 チェックボックスにチェックを付けます。
    追加のフィールドが「新しい仮想ネットワークを作成」ウィンドウに表示されます。
    DHCPv6 の設定

    図17.17 DHCPv6 の設定

    (オプション) DHCPv6 範囲の開始と終了を編集します。
  6. 静的ルートの定義を有効にする場合、スタティックルートの定義を有効化 チェックボックスにチェックを付けます。
    追加のフィールドが「新しい仮想ネットワークを作成」ウィンドウに表示されます。
    静的ルートの定義

    図17.18 静的ルートの定義

    該当するフィールドに、ネットワークへのルートに使用するネットワークアドレスおよびゲートウェイを入力します。
    進む (Forward) をクリックします。
  7. 仮想ネットワークを物理ネットワークに接続する方法を選択します。
    物理ネットワークへの接続

    図17.19 物理ネットワークへの接続

    仮想ネットワークを分離する場合、隔離された仮想ネットワーク ラジオボタンが選択されていることを確認します。
    仮想ネットワークが物理ネットワークに接続できるようにするには、物理ネットワークのフォワード を選択してから、宛先いずれかの物理デバイス または特定の物理デバイスにするかどうかを選択します。さらに、モードNAT または ルーティング にするかどうかを選択します。
    仮想ネットワーク内で IPv6 ルーティングを有効にするには、IPv6 の内部ルーティング/内部ネットワークを有効にする チェックボックスにチェックを付けます。
    仮想ネットワークの DNS ドメイン名を入力します。
    Finish をクリックし、仮想ネットワークを作成します。
  8. これで新しい仮想ネットワークが 接続の詳細 ウィンドウの 仮想ネットワーク タブに表示されるようになります。

17.11. 仮想ネットワークのゲストへの接続

仮想ネットワークをゲストに接続する
  1. 仮想マシンマネージャーウィンドウ内で、 ネットワークを割り当てるゲストを強調表示します。
    表示する仮想マシンの選択

    図17.20 表示する仮想マシンの選択

  2. 仮想マシンマネージャーの 編集 メニューから 仮想マシンの詳細 を選択します。
  3. 仮想マシンの詳細ウィンドウにある ハードウェアを追加 ボタンをクリックします。
  4. 新しい仮想ハードウェアを追加 ウィンドウ内の左側のペインから ネットワーク を選択し、ネットワークソース メニューでネットワーク名 (この例では network1) を選択します。必要に応じて MAC アドレスを修正し、デバイスのモデル を選択します。完了 をクリックします。
    新規の仮想ハードウェアの追加ウィンドウからネットワークを選択する

    図17.21 新規の仮想ハードウェアの追加ウィンドウからネットワークを選択する

  5. これで新しいネットワークが仮想ネットワークインターフェースとして表示されるようになりました。ゲストの起動時に提供されるようになります。
    ゲストのハードウェア一覧に表示される新しいネットワーク

    図17.22 ゲストのハードウェア一覧に表示される新しいネットワーク

17.12. 仮想 NIC を直接物理インターフェースへ接続

デフォルトの NAT 接続の代わりに、macvtap ドライバーを使ってゲストの NIC を直接ホストマシンの特定の物理インターフェースに接続することができます。これを、デバイス割り当て (パススルーとも呼ばれる) と混同しないようにしてください。Macvtap 接続には以下のモードがあり、それぞれメリットとユースケースが異なります。

物理インターフェースの配信モード

VEPA
仮想イーサネットポートアグリゲーター (VEPA) モードでは、ゲストからのパケットはすべて外部スイッチに送信されます。これにより、ユーザーはゲストのトラフィックを強制的にスイッチ経由にすることができます。VEPA モードが正常に機能するためには、外部スイッチは ヘアピンモード にも対応している必要があります。これにより、送信元ゲストと同じホストマシン上にあるゲスト宛のパケットが、外部スイッチによりホストに戻されます。
VEPA モード

図17.23 VEPA モード

bridge
送信元ゲストと同じホストマシン上にあるゲスト宛のパケットは、直接宛先の macvtap デバイスに配信されます。直接配信が正常に機能するためには、送信元デバイスと宛先のデバイスの両方が bridge モードになければなりません。どちらかのデバイスが VEPA モードにある場合は、ヘアピン機能に対応した外部スイッチが必要です。
Bridge モード

図17.24 Bridge モード

private
すべてのパケットは外部スイッチに送信されます。それらのパケットが同じホストマシン上にある宛先のゲストに配信されるのは、それらが外部ルーターまたはゲートウェイ経由で送信され、それらがパケットをホストに戻す場合のみです。private モードは、同一ホスト上にある個々のゲストが互いに通信するのを防ぐために使うことができます。送信元または宛先デバイスのいずれかが private モードにある場合に、この手順が実行されます。
Private モード

図17.25 Private モード

passthrough
この機能では、物理インターフェースデバイスまたは SR-IOV 仮想機能 (VF) を、移行機能を損なうことなく直接ゲストに接続します。すべてのパケットは、直接目的のネットワークデバイスに送信されます。passthrough モードでは、ゲスト間でネットワークデバイスを共有することはできません。従って、1 つのゲストにパススルーできるネットワークデバイスは 1 つだけです。
Passthrough モード

図17.26 Passthrough モード

Macvtap の設定は、ドメインの XML ファイルを変更して、または virt-manager インターフェースを使用して行います。

17.12.1. ドメイン XML を使用した macvtap の設定

ゲストのドメイン XML ファイルを開き、以下のように <devices> 要素を変更します。
<devices>
	...
	<interface type='direct'>
		<source dev='eth0' mode='vepa'/>
	</interface>
</devices>
直接接続したゲスト仮想マシンのネットワークアクセスは、ホスト物理マシンの物理インターフェースが接続されているハードウェアスイッチで管理することができます。
スイッチが IEEE 802.1Qbg 標準に設定されている場合は、インターフェースに以下に示すように追加パラメーターを持たせることができます。virtualport 要素のパラメーターについては IEEE 802.1Qbg 標準の記載をご覧ください。その値についてはネットワーク固有となるため、ネットワーク管理者にお問い合わせください。802.1Qbg では、VSI (Virtual Station Interface) は仮想マシンの仮想インターフェースのことを指します。なお、IEEE 802.1Qbg では、VLAN ID にゼロ以外の値を設定する必要があります。

Virtual Station Interface のタイプ

managerid
VSI Manager ID で VSI タイプとインスタンス定義が含まれるデータベースを識別します。これは整数の値で、0 の値は予約されています。
typeid
VSI Type ID で ネットワークアクセスの特性を示す VSI タイプを識別します。 VSI タイプは一般的にはネットワーク管理者によって管理されます。 整数の値になります。
typeidversion
VSI Type Version では VSI Type の複数のバージョンを許可します。 整数の値になります。
instanceid
VSI Instance ID は、VSI インスタンス (つまり、仮想マシンの仮想インターフェース) の作成時に生成されます。これは、グローバルに固有な識別子です。
profileid
プロファイル ID には、 このインターフェースに適用されるポートプロファイル名が含まれます。 この名前は、 ポートプロファイルのデータベースによってポートプロファイルからネットワークパラメーターに解決され、 このネットワークパラメータがこのインターフェースに適用されます。
4 種類のそれぞれのタイプの設定は、ドメインの XML ファイルを変更して行います。このファイルを開いたら、以下のようにモードの設定を変更します。
<devices>
 ...
 <interface type='direct'>
  <source dev='eth0.2' mode='vepa'/>
   <virtualport type="802.1Qbg">
    <parameters managerid="11" typeid="1193047" typeidversion="2" instanceid="09b11c53-8b5c-4eeb-8f00-d84eaa0aaa4f"/>
   </virtualport>
  </interface>
</devices>
プロファイル ID を以下に示します。
<devices>
 ...
 <interface type='direct'>
  <source dev='eth0' mode='private'/>
   <virtualport type='802.1Qbh'>
    <parameters profileid='finance'/>
   </virtualport>
 </interface>
</devices>
...

17.12.2. virt-manager を使用した macvtap の設定

仮想ハードウェアの詳細ウィンドウ を開き ⇒ メニューで NIC を選択し ⇒ ネットワークソースホストデバイス name: macvtap を選択し ⇒ 目的の ソースモード を選択します。
続いて、仮想ポート サブメニューで、Virtual Station Interface のタイプを設定することができます。
virt-manager で macvtap を設定

図17.27 virt-manager で macvtap を設定

17.13. 仮想 NIC に接続しているネットワークブリッジまたはホスト物理マシンの動的な変更

このセクションでは、ゲスト仮想マシンを稼働したままで安全性を確保しながら、そのゲスト仮想マシンの vNIC をあるブリッジから別のブリッジに移動する方法について説明します。
  1. 次のような設定でゲスト仮想マシンを用意します。
    <interface type='bridge'>
          <mac address='52:54:00:4a:c9:5e'/>
          <source bridge='virbr0'/>
          <model type='virtio'/>
    </interface>
  2. インターフェースの更新用に XML ファイルを準備します。
    # cat br1.xml
    <interface type='bridge'>
          <mac address='52:54:00:4a:c9:5e'/>
          <source bridge='virbr1'/>
          <model type='virtio'/>
    </interface>
  3. ゲスト仮想マシンを起動し、ゲスト仮想マシンのネットワーク機能を確認してから、そのゲスト仮想マシンの vnetX が指定するブリッジに接続されていることを確認します。
    # brctl show
    bridge name     bridge id               STP enabled     interfaces
    virbr0          8000.5254007da9f2       yes                  virbr0-nic
    
    vnet0
    virbr1          8000.525400682996       yes                  virbr1-nic
  4. 次のコマンドを使って新しいインターフェースのパラメーターでゲスト仮想マシンのネットワークを更新します。
    # virsh update-device test1 br1.xml 
    
    Device updated successfully
    
  5. ゲスト仮想マシン上で service network restart を実行します。ゲスト仮想マシンが virbr1 の新しい IP アドレスを取得します。ゲスト仮想マシンの virbr0 が新しいブリッジ (virbr1) に接続されていることを確認します。
    # brctl show
    bridge name     bridge id               STP enabled     interfaces
    virbr0          8000.5254007da9f2       yes             virbr0-nic
    virbr1          8000.525400682996       yes             virbr1-nic     vnet0

17.14. ネットワークのフィルター機能の適用

このセクションでは libvirt のネットワークフィルター、フィルターの目的、その概要と XML 形式などについて紹介します。

17.14.1. はじめに

ネットワークフィルター機能の目的は、仮想化システムの管理者がネットワークトラフィックのフィルタールールを仮想マシンに設定し、実施することができるようにし、また仮想マシンによる送受信を許可するネットワークトラフィックのパラメーターーを管理できるようにすることです。ネットワークトラフィックのフィルタールールは、仮想マシンの起動時にホスト物理マシンで適用されます。フィルタールールは仮想マシン内から回避することができないため、仮想マシンのユーザーの観点からは強制的なルールとなります。
ゲスト仮想マシンから見ると、ネットワークフィルターのシステムにより、インターフェースごとに各仮想マシンのネットワークトラフィックフィルタールールを個別に設定できます。これらのルールは仮想マシンの起動時にホスト物理マシンで適用され、仮想マシンの実行中に変更することができます。ルールの変更を行なう場合は、ネットワークフィルターの XML 記述を編集します。
複数の仮想マシンが同じ汎用ネットワークフィルターを利用できます。このようなフィルターを変更すると、このフィルターを参照している実行中の全仮想マシンのネットワークトラフィックフィルタールールが更新されます。実行中ではないマシンは起動時に更新されます。
前述の通り、 ネットワークトラフィックフィルターのルールは、特定タイプのネットワーク設定用に設定された個別のネットワークインターフェースに適用できます。 対応しているネットワークのタイプは次の通りです。
  • ネットワーク
  • イーサネット -- ブリッジモードで使用してください
  • bridge

例17.1 ネットワークフィルターの例

トップレベルのフィルターの参照にはインターフェース XML が使用されます。次の例では、インターフェースの記述で clean-traffic フィルターを参照しています。
   <devices>
    <interface type='bridge'>
      <mac address='00:16:3e:5d:c7:9e'/>
      <filterref filter='clean-traffic'/>
    </interface>
  </devices>
ネットワークフィルターは XMLで記述します。 他のフィルターへの参照またはトラフィックフィルターのルールのいずれかを含ませるか、またはそれら両方の組み合わせを含ませることもできます。上記の参照フィルター clean-traffic は、他のフィルターへの参照のみを含み、実際のフィルタールールは含まれていません。他のフィルターへの参照を使用することができるため、フィルターのツリーを作成することが可能です。clean-traffic フィルターは # virsh nwfilter-dumpxml clean-traffic コマンドを使用して表示できます。
前述のように、1 つのネットワークフィルターを複数の仮想マシンに参照させることができます。一般的にはインターフェースにはトラフィックフィルタールールに関連付けられた個別のパラメーターがあるため、フィルターの XML に記述されているルールは変数を使って一般化することができます。この場合、 変数の名前をフィルターの XML で使用し、フィルターが参照される場所にその名前と値を入力します。

例17.2 記述の拡張

次の例では、インターフェースの記述にパラメーターの名前「IP」と「ドット表記の IP アドレス」の値を加えて拡張しています。
  <devices>
    <interface type='bridge'>
      <mac address='00:16:3e:5d:c7:9e'/>
      <filterref filter='clean-traffic'>
        <parameter name='IP' value='10.0.0.1'/>
      </filterref>
    </interface>
  </devices>
この例では、clean-traffic ネットワークトラフィックフィルターは IP アドレスパラメーター 10.0.0.1 で表され、ルールの指示によりこのインターフェースからのトラフィックはすべて必ず 10.0.0.1 をソースの IP アドレスとして使用するようになります。これがこのフィルターの目的です。

17.14.2. フィルターチェーン

フィルタールールはフィルターチェーンで編成されます。これらのチェーンは、各チェーン (ブランチ) 内に複数のパケットフィルタールールのエントリーを持つツリー構造を形成していると考えることができます。
パケットはルートチェーンでフィルター評価を開始し、次に他のチェーンでの評価を継続していき、ルートチェーンに戻ってくるか、または途中のチェーンでドロップされるか、または承認されます。
libvirt のネットワークフィルターシステムでは、ユーザーがトラフィックフィルター機能の有効化を選択した仮想マシンのネットワークインターフェースに個別のルートチェーンを自動生成します。ユーザーは、ルートチェーン内で直接インスタンス化されるフィルタールールを記述したり、プロトコル固有のフィルターチェーンを作成してプロトコル固有のルールを効率的に評価したりすることができます。
次のようなチェーンがあります。
  • root
  • mac
  • stp (スパニングツリープロトコル)
  • vlan
  • arp と rarp
  • ipv4
  • ipv6
チェーン名にプロトコル名をプレフィックスとして付けるだけで、 mac、 stp、 vlan、 arp、 rarp、 ipv4、 ipv6 などそれぞれのプロトコルを評価するチェーンを複数作成することができます。

例17.3 ARP トラフィックフィルター

以下の例では、チェーンに「arp-xyz」や「arp-test 」などのチェーン名を付け、そのチェーン内で ARP プロトコルのパケットが評価されるようにしています。
次のフィルター XML では arp チェーン内で ARP トラフィックをフィルタリングする例を示しています。
<filter name='no-arp-spoofing' chain='arp' priority='-500'>
  <uuid>f88f1932-debf-4aa1-9fbe-f10d3aa4bc95</uuid>
  <rule action='drop' direction='out' priority='300'>
    <mac match='no' srcmacaddr='$MAC'/>
  </rule>
  <rule action='drop' direction='out' priority='350'>
    <arp match='no' arpsrcmacaddr='$MAC'/>
  </rule>
  <rule action='drop' direction='out' priority='400'>
    <arp match='no' arpsrcipaddr='$IP'/>
  </rule>
  <rule action='drop' direction='in' priority='450'>
    <arp opcode='Reply'/>
    <arp match='no' arpdstmacaddr='$MAC'/>
  </rule>
  <rule action='drop' direction='in' priority='500'>
    <arp match='no' arpdstipaddr='$IP'/>
  </rule>
  <rule action='accept' direction='inout' priority='600'>
    <arp opcode='Request'/>
  </rule>
  <rule action='accept' direction='inout' priority='650'>
    <arp opcode='Reply'/>
  </rule>
  <rule action='drop' direction='inout' priority='1000'/>
</filter>
ARP 固有となるルールをルートのチェーンではなく「arp」チェーン内に置くことで、ARP プロトコル以外のパケットを ARP プロトコル固有のルールで評価する必要がなくなります。このためトラフィックフィルタリングの効率性が向上することになります。ただし、プロトコル用のフィルタールールは必ずそのプロトコル用のチェーンに置くよう注意してください。これにより、他のルールが評価されなくなります。たとえば、 IPv4 プロトコルのパケットは ARP チェーンを通らないため、ARP チェーン内の IPv4 ルールは評価されません。

17.14.3. フィルターチェーンの優先度

前述のように、フィルタールールを作成すると、すべてのチェーンはルートチェーンにつながれます。それらのチェーンがアクセスされる順序はそのチェーンの優先度によって変わります。次の表は、優先度を割り当てることができるチェーンとそのデフォルトの優先度を示しています。

表17.1 フィルターチェーンのデフォルト優先度値

チェーン (プレフィックス)デフォルトの優先度
stp-810
mac-800
vlan-750
ipv4-700
ipv6-600
arp-500
rarp-400

注記

優先度の値が小さいチェーンは、値が大きいチェーンよりも前にアクセスされます。
表17.1「フィルターチェーンのデフォルト優先度値」 に一覧表示されているチェーンには、フィルターノード内の優先度 (XML) 属性に [-1000 から 1000] の範囲の値を記述してカスタムの優先度を割り当てることもできます。たとえば、「フィルターチェーン」 のフィルターは arp チェーンについて -500 のデフォルト優先度を示しています。

17.14.4. フィルター内での変数の使用

ネットワークトラフィックフィルターのサブシステムで使用するよう MAC と IP の 2 種類の変数が予約されています。
ネットワークインターフェースの MAC アドレスには MAC が指定されます。この変数を参照するフィルタールールは自動的にインターフェースの MAC アドレスに置換されます。これは、ユーザー側で明示的に MAC パラメーターを指定する必要がないために便利です。前述の IP パラメーターと同様、MAC パラメーターを指定することはできますが、インターフェースが使用する MAC アドレスは libvirt で認識できるためお勧めしません。
パラメーター IP は、仮想マシン内のオペレーティングシステムが特定のインターフェースで使用する IP アドレスを表します。パラメーターが明示的な指定ではなく参照する形になっている場合、libvirt デーモンがインターフェースで使用されている IP アドレス (および IP パラメーターの値) を確定するように試行するため、この場合 IP パラメーターは特殊となります。現在の IP アドレス検出には限界があるため、この機能の使い方および使用した場合に予想される制限については 「制限」 をよくお読みください。「フィルターチェーン」 で示した XML ファイルには no-arp-spoofing のフィルターが含まれています。これは、MAC と IP 変数を参照する場合にネットワークフィルター XML を利用する例です。
参照される変数には常に $ 文字のプレフィックスが付きます。変数の値の形式は XML で指定されるフィルター属性によって予想されるタイプにする必要があります。上記の例では、IP パラメーターに正式な IP アドレスを標準形式で持たせる必要があります。不適切な形式を指定すると、フィルターの変数が値に置換されないため、仮想マシンが起動しなくなったり、ホットプラグインを使用している場合はインターフェースが接続されなくなります。XML 属性に予想されるタイプのいくつかを 例17.4「変数タイプの例」に示します。

例17.4 変数タイプの例

変数には複数の要素を含めることができるため (たとえば、変数 IP には特定のインターフェースで有効となる複数の IP アドレスを含めることができる)、IP 変数に複数の要素を指定する場合は以下のように記述します。
  <devices>
    <interface type='bridge'>
      <mac address='00:16:3e:5d:c7:9e'/>
      <filterref filter='clean-traffic'>
        <parameter name='IP' value='10.0.0.1'/>
        <parameter name='IP' value='10.0.0.2'/>
        <parameter name='IP' value='10.0.0.3'/>
      </filterref>
    </interface>
  </devices>
この XML ファイルは、1 つのインターフェースに複数の IP アドレスを有効にするフィルターを作成します。各 IP アドレスが別個のフィルタールールになります。したがって、上記の XML と以下のルールを使用すると、3 種類の異なるフィルタールールが作成されます (IP アドレスごと 1 ルール)。
  <rule action='accept' direction='in' priority='500'>
    <tcp srpipaddr='$IP'/>
  </rule>
複数の要素を含む変数の各要素にアクセスすることができるため、以下のようなフィルタールールは DSTPORTS 変数の 2 番目の要素にアクセスします。
  <rule action='accept' direction='in' priority='500'>
    <udp dstportstart='$DSTPORTS[1]'/>
  </rule>

例17.5 各種変数の使用

$VARIABLE[@<iterator id="x">] の表記を使用すると、異なる一覧からの許容範囲内にあるルールのあらゆる組み合わせを表すことができるフィルタールールの作成が可能です。次のルールは、仮想マシンが DSTPORTS で指定されている複数のポート上で SRCIPADDRESSES に指定されている複数のソース IP アドレスからのトラフィックを受信できるよう許可します。このルールは、要素へのアクセスに 2 種類の独立した反復子を使って、変数 DSTPORTSSRCIPADDRESSES のあらゆる組み合わせを生成します。
  <rule action='accept' direction='in' priority='500'>
    <ip srcipaddr='$SRCIPADDRESSES[@1]' dstportstart='$DSTPORTS[@2]'/>
  </rule>
以下のように SRCIPADDRESSESDSTPORTS に具体的な値を割り当てます。
  SRCIPADDRESSES = [ 10.0.0.1, 11.1.2.3 ]
  DSTPORTS = [ 80, 8080 ]
$SRCIPADDRESSES[@1]$DSTPORTS[@2] を使って変数に値を割り当てると、以下のようにアドレスとポートのあらゆる組み合わせが作成されることになります。
  • 10.0.0.1, 80
  • 10.0.0.1, 8080
  • 11.1.2.3, 80
  • 11.1.2.3, 8080
$SRCIPADDRESSES[@1]$DSTPORTS[@1] の表記など、1 つの反復子を使って前述の変数にアクセスすると、両方の一覧に並列にアクセスされるため、次のような組み合わせになります。
  • 10.0.0.1, 80
  • 11.1.2.3, 8080

注記

$VARIABLE$VARIABLE[@0] の簡略形になります。このセクションの冒頭で示したように、先の表記は常に反復子の役割となる iterator id="0" が付くと仮定しています。

17.14.5. 自動 IP アドレス検出と DHCP スヌーピング

このセクションでは、自動 IP アドレス検出と DHCP スヌーピングについての情報を提供します。

17.14.5.1. はじめに

仮想マシンのインターフェースで使用される IP アドレスの検出は、変数の IP が参照されるものの、値が割り当てられていない場合に自動的に作動します。使用する IP アドレスラーニングメソッドを指定する場合に変数 CTRL_IP_LEARNING を使用します。anydhcpnone が有効な値になります。
any の値では、libvirt に対し、パケットを使って仮想マシンで使用しているアドレスを確定するよう指示します。これは、変数 CTRL_IP_LEARNING が設定されていない場合のデフォルトになります。このメソッドの場合、検出する IP アドレスはインターフェースごとに 1 つのみとなります。ゲスト仮想マシンの IP アドレスが検出されると、その IP ネットワークトラフィックがそのアドレスにロックされ、IP アドレスのなりすましなどがそのフィルターの 1 つで防止されます。この場合、IP アドレスのなりすましと見られるような、仮想マシンのユーザーによるゲスト仮想マシン内からのインターフェースの IP アドレスの変更は行なえなくなります。ゲスト仮想マシンを別のホスト物理マシンに移行したり、一時停止状態から再開させた場合、ゲスト仮想マシンが送信する最初のパケットによって特定のインターフェースで使用できる IP アドレスが再度確定されます。
dhcp の値では、libvirt に DHCP サーバーで割り当てられる有効なリースを持つアドレスしか受け取らないよう指示します。このメソッドは 1 つのインターフェースでの複数 IP アドレスの検出および使用に対応しています。ゲスト仮想マシンが一時停止状態から再開すると、有効な IP アドレスのリースがそのフィルターに適用されます。その他の場合、ゲスト仮想マシンは新しい IP アドレスを取得するために DHCP を使用します。ゲスト仮想マシンを別の物理的なホスト物理マシンに移行する場合には、ゲスト仮想マシンで DHCP プロトコルを再実行する必要があります。
CTRL_IP_LEARNING を none に設定すると、libvirt では IP アドレスラーニングは行なわれず、明示的な値を割り当てない IP の参照はエラーになります。

17.14.5.2. DHCP スヌーピング

CTRL_IP_LEARNING=dhcp (DHCP スヌーピング) により、とくに IP アドレスの割り当てを信頼できる DHCP サーバーに限るフィルターと併用したい場合に、なりすまし防止に対する安全性が強化されます。これを有効にするには、DHCPSERVER 変数を有効な DHCP サーバーの IP アドレスに設定し、 この変数を使って着信 DHCP の応答を処理するフィルターを指定します。
DHCP スヌーピングが有効にされており、DHCP リースの有効期限が切れた場合、ゲスト仮想マシンは DHCP サーバーから新しい有効なリースを取得するまで、その IP アドレスを使用できなくなります。ゲスト仮想マシンを移行する場合、IP アドレスを使用するために新しい有効な DHCP リースを取得する必要があります (たとえば、仮想マシンをいったんダウンさせてから再起動する必要があります)。

注記

自動 DHCP 検出では、ゲスト仮想マシンがインフラストラクチャーの DHCP サーバーと通信する DHCP トラフィックをリッスンします。libvirt でのサービス拒否攻撃を回避するには、パケット評価の速度制限を行います。つまり、ゲスト仮想マシンがインターフェース上で 1 秒間に大量の DHCP パケットを送信している場合には、そのパケットすべてには評価を行わないようにして、フィルターが適用されないようにします。通常の DHCP クライアントの動作の場合、1 秒に送信する DHCP パケット数は多くないことが想定されます。また、DHCP パケットが送信されないようにするためにインフラストラクチャー内の全ゲスト仮想マシンに適切なフィルターを設定することが重要になります。したがって、ポート 67 からポート 68 へのゲスト仮想マシンによる UDP および TCP トラフィック送信を防止するか、または DHCPSERVER 変数を全ゲスト仮想マシンで使用して DHCP サーバーのメッセージが信頼できる DHCP サーバーからしか送信できないよう制限する必要があります。同時に、なりすまし防止の対策をサブネット内の全ゲスト仮想マシンで有効にしておく必要があります。

例17.6 DHCP スヌーピング用に IP をアクティブ化

以下の XML は、DHCP スヌーピングメソッドを使って IP アドレスラーニングをアクティブにした例を示しています。
    <interface type='bridge'>
      <source bridge='virbr0'/>
      <filterref filter='clean-traffic'>
        <parameter name='CTRL_IP_LEARNING' value='dhcp'/>
      </filterref>
    </interface>

17.14.6. 予約済み変数

表17.2「予約済み変数」 は、予約済みとみなされ、libvirt によって使用される変数を示しています。

表17.2 予約済み変数

変数名定義
MACインターフェースの MAC アドレス
IPインターフェースで使用中の IP アドレス一覧
IPV6現在のところ実装されていません。インターフェースで使用中の IPV6 アドレスの一覧
DHCPSERVER信頼できる DHCP サーバーの IP アドレス一覧
DHCPSERVERV6現在のところ実装されていません。信頼できる DHCP サーバーの IPv6 アドレスの一覧
CTRL_IP_LEARNINGIP アドレス検出モードの選択

17.14.7. 要素と属性の概要

ネットワークフィルターすべてに必要なルート要素は 2 つの属性を持つ <filter> になります。name 属性は特定フィルターの固有名を指定します。chain 属性はオプションですが、基礎となるホスト物理マシンのファイアウォールサブシステムによってより効率的な処理を実現するために特定のフィルターを編成することができます。現在、システムで対応しているチェーンは、rootipv4ipv6arp、および rarp のみです。

17.14.8. 他のフィルターへの参照

いずれのフィルターにも他のフィルターへの参照を持たせることができます。フィルターツリー内の各フィルターは複数回参照できますが、フィルター間の参照がループとならないようにする必要があります。

例17.7 clean traffic フィルターの例

以下は、他のいくつかのフィルターを参照している clean-traffic ネットワークフィルターの XML です。
<filter name='clean-traffic'>
  <uuid>6ef53069-ba34-94a0-d33d-17751b9b8cb1</uuid>
  <filterref filter='no-mac-spoofing'/>
  <filterref filter='no-ip-spoofing'/>
  <filterref filter='allow-incoming-ipv4'/>
  <filterref filter='no-arp-spoofing'/>
  <filterref filter='no-other-l2-traffic'/>
  <filterref filter='qemu-announce-self'/>
</filter>
別のフィルターを参照させる場合、XML ノードの <filterref> をフィルターノード内に指定する必要があります。このノードには参照先のフィルター名を値として持つ属性フィルターを持たせる必要があります。
新しいネットワークフィルターはいつの時点で定義しても構いません。また、libvirt がまだ認識できないネットワークフィルターへの参照を含めることもできます。ただし、仮想マシンの起動後、またはフィルターを参照するネットワークインターフェースのホットプラグ後には、フィルターツリー内の全ネットワークフィルターが利用可能な状態になければなりません。 利用できないフィルターがある場合には仮想マシンが起動しなくなるか、またはネットワークインターフェースの接続が不可能になります。

17.14.9. フィルタールール

以下の XML は、発信 IP パケット内の IP アドレス (変数 IP の値から取得される) が期待したアドレスではない場合に、トラフィックをドロップするルールを実施するネットワークトラフィックフィルターの簡単な例を示しています。これにより仮想マシンからの IP アドレスのなりすましを防ぎます。

例17.8 ネットワークトラフィックフィルターの例

<filter name='no-ip-spoofing' chain='ipv4'>
  <uuid>fce8ae33-e69e-83bf-262e-30786c1f8072</uuid>
  <rule action='drop' direction='out' priority='500'>
    <ip match='no' srcipaddr='$IP'/>
  </rule>
</filter>
トラフィックフィルターのルールはルールノードで開始します。このノードには以下の属性を最大 3 つまで含めることができます。
  • action を mandatory にすると、次の値を取ることができます。
    • drop (ルールに一致すると、さらに分析することなくパケットを破棄し、メッセージは出力されません)
    • reject (ルールに一致すると、さらに分析することなく ICMP 拒否メッセージを生成します)
    • accept (ルールに一致すると、さらに分析することなくパケットを受け取ります)
    • return (ルールに一致すると、このフィルターを通過しますがさらに分析するため呼び出しフィルターに制御を戻します)
    • continue (ルールに一致すると、さらに分析するため次のルールに移動します)
  • direction を mandatory にすると、次の値を取ることができます。
    • in - 着信トラフィック
    • out - 発信トラフィック
    • inout - 着信と発信のトラフィック
  • priority はオプションです。ルールの優先度は、ルールが他のルールに対して相対的にインスタンス化される順序を制御します。小さい値のルールは大きい値のルールより先にインスタンス化されます。有効な値は -1000 から 1000 の範囲です。この属性が指定されないと、デフォルトでは優先度 500が指定されます。ルートチェーン内のフィルタールールは、その優先度に基づいて、ルートチェーンに接続されるフィルターで分類されます。これにより、フィルターチェーンへのアクセスを持たせながらフィルタールール同士を交互配置することができるようになります。詳細は「フィルターチェーンの優先度」を参照してください。
  • statematch はオプションです。「0」または「false」に設定すると、 基礎となる接続状態のマッチングをオフにします。デフォルト設定は「1」または「 true」です。
詳細は、「高度なフィルター設定について」 を参照してください。
前述の 例17.7「clean traffic フィルターの例」 では、type ip のトラフィックはチェーン ipv4 に関連付けられ、ルールは priority=500 になることを示しています。type ip のトラフィックがチェーン ipv4 に関連付けられる別のフィルターが参照される場合は、そのフィルターのルールは先のルールの priority=500 に基づいて順序付けられます。
ルールにはトラフィックのフィルターを行なう単一ルールを含めることができます。上記の例では、タイプ ip のトラフィックがフィルターされます。

17.14.10. サポート対象プロトコル

以下のセクションでは、ネットワークフィルターのサブシステムで対応しているプロトコルの詳細について示します。このタイプのトラフィックルールはネスト化されたノードとしてルールノードで指定されます。ルールがフィルターするトラフィックのタイプにより、属性は異なります。上記の例では、単一の srcipaddr 属性を示しています。この属性は ip トラフィックフィルターノード内で有効になります。次のセクションでは有効な属性と期待されるデータタイプについて示します。 次のようなデータタイプが使用可能です。
  • UINT8 : 8 ビットの整数; 0-255 の範囲
  • UINT16: 16 ビットの整数; 0-65535 の範囲
  • MAC_ADDR: ドット付き 10 進数形式の MAC アドレス (00:11:22:33:44:55 など)
  • MAC_MASK: MAC アドレス形式による MAC アドレスマスク (FF:FF:FF:FC:00:00 など)
  • IP_ADDR: ドット付き 10 進数形式の IP アドレス (10.1.2.3 など)
  • IP_MASK: ドット付き 10 進数形式 (255.255.248.0) または CIDR マスク (0-32) による IP アドレスマスク
  • IPV6_ADDR: 数値形式の IPv6 アドレス (FFFF::1)
  • IPV6_MASK: 数値形式 (FFFF:FFFF:FC00::) または CIDR マスク (0-128) による IPv6 マスク
  • STRING: 文字列
  • BOOLEAN: 'true'、'yes'、'1'、または 'false'、 'no'、 '0'
  • IPSETFLAGS: 最大 6 つの 'src' または 'dst' 要素で記述される ipset のソースフラグと宛先フラグで、パケットヘッダーのソース部分または宛先部分いずれかの機能を選択します (src,src,dst など)。ここに入力する 'selectors' の数は参照される ipset のタイプによって異なります。
IP_MASK または IPV6_MASK のタイプを除き、すべての属性は no の値の match 属性を使って無効にすることができます。無効にした複数の属性を 1 つのまとめることもできます。次の XML の抜粋部分で抽象属性を使った一例を示します。
[...]
  <rule action='drop' direction='in'>
    <protocol match='no' attribute1='value1' attribute2='value2'/>
    <protocol attribute3='value3'/>
  </rule>
[...]
ルールの動作によりそのルールが評価されるとともに、特定のプロトコル属性の境界内でそのルールが論理的に調べられます。単一属性の値がルールで指定された値に一致しない場合、評価のプロセスではそのルール全体が省略されることになります。したがって、上記の例では、プロトコルプロパティの attribute1value1 に一致せず、プロトコルプロパティーの attribute2value2 に一致せず、かつプロトコルプロパティー attribute3value3 に一致する場合、 着信トラフィックのみがドロップされます。

17.14.10.1. MAC (イーサネット)

プロトコル ID: mac
このタイプのルールはルートチェーンに入ります。

表17.3 MAC プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAC_ADDR宛先の MAC アドレス
dstmacmaskMAC_MASK宛先の MAC アドレスに適用されるマスク
protocolidUINT16 (0x600-0xffff), STRINGレイヤー 3 プロトコル ID、有効な文字列 [arp, rarp, ipv4, ipv6]
commentSTRING最長 256 文字のテキスト文字列
フィルターは以下のように記述できます。
[...]
<mac match='no' srcmacaddr='$MAC'/>
[...]

17.14.10.2. VLAN (802.1Q)

プロトコル ID: vlan
このタイプのルールはルートチェーンまたは vlan チェーンのいずれかに入ります。

表17.4 VLAN プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAC_ADDR宛先の MAC アドレス
dstmacmaskMAC_MASK宛先の MAC アドレスに適用されるマスク
vlan-idUINT16 (0x0-0xfff, 0 - 4095)VLAN ID
encap-protocolUINT16 (0x03c-0xfff), Stringカプセル化されたレイヤー 3 プロトコル ID、有効な文字列 arp、ipv4、ipv6
commentSTRING最長 256 文字のテキスト文字列

17.14.10.3. STP (Spanning Tree Protocol)

プロトコル ID: stp
このタイプのルールはルートチェーンまたは stp チェーンのいずれかに入ります。

表17.5 STP プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
typeUINT8BPDU (Bridge Protocol Data Unit) タイプ
flagsUINT8BPDU flagdstmacmask
root-priorityUINT16ルート優先度範囲の始点
root-priority-hiUINT16 (0x0-0xfff, 0 - 4095)ルート優先度範囲の終点
root-addressMAC _ADDRESSルートの MAC アドレス
root-address-maskMAC _MASKルートの MAC アドレスマスク
roor-costUINT32ルートのパスコスト (範囲の始点)
root-cost-hiUINT32ルートのパスコスト (範囲の終点)
sender-priority-hiUINT16送信側優先度の範囲の終点
sender-addressMAC_ADDRESSBPDU 送信側 MAC アドレス
sender-address-maskMAC_MASKBPDU 送信側 MAC アドレスマスク
portUINT16ポート識別子 (範囲の始点)
port_hiUINT16ポート識別子 (範囲の終点)
msg-ageUINT16メッセージエイジタイマー (範囲の始点)
msg-age-hiUINT16メッセージエイジタイマー (範囲の終点)
max-age-hiUINT16最大エイジ時間の範囲の終点
hello-timeUINT16Hello タイムタイマー (範囲の始点)
hello-time-hiUINT16Hello タイムタイマー (範囲の終点)
forward-delayUINT16フォワード遅延 (範囲の始点)
forward-delay-hiUINT16フォワード遅延 (範囲の終点)
commentSTRING最長 256 文字のテキスト文字列

17.14.10.4. ARP/RARP

プロトコル ID: arp または rarp
このタイプのルールはルートチェーンまたは arp/rarp チェーンのいずれかに入ります。

表17.6 ARP と RARP のプロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAC_ADDR宛先の MAC アドレス
dstmacmaskMAC_MASK宛先の MAC アドレスに適用されるマスク
hwtypeUINT16ハードウェアのタイプ
protocoltypeUINT16プロトコルのタイプ
opcodeUINT16, STRINGOpcode の有効な文字列: Request、Reply、Request_Reverse、Reply_Reverse、DRARP_Request、DRARP_Reply、DRARP_Error、InARP_Request、ARP_NAK
arpsrcmacaddrMAC_ADDRARP/RARP パケット内のソース MAC アドレス
arpdstmacaddrMAC _ADDRARP/RARP パケット内の宛先 MAC アドレス
arpsrcipaddrIP_ADDRARP/RARP パケット内のソース IP アドレス
arpdstipaddrIP_ADDRARP/RARP パケット内の宛先 IP アドレス
gratuitousBOOLEAN余計な ARP パケットをチェックするかどうかを指定するブール値
commentSTRING最長 256 文字のテキスト文字列

17.14.10.5. IPv4

プロトコル ID: ip
このタイプのルールはルートチェーンまたは ipv4 チェーンのいずれかに入ります。

表17.7 IPv4 プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAC_ADDR宛先の MAC アドレス
dstmacmaskMAC_MASK宛先の MAC アドレスに適用されるマスク
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
protocolUINT8, STRINGレイヤー 4 プロトコルの識別子。protocol に有効な文字列: tcp、udp、udplite、esp、ah、icmp、igmp、sctp
srcportstartUINT16有効なソースポート範囲の開始点。プロトコルが必要。
srcportendUINT16有効なソースポート範囲の終了点。プロトコルが必要。
dstportstartUNIT16有効な宛先ポート範囲の開始点。プロトコルが必要。
dstportendUNIT16有効な宛先ポート範囲の終了点。プロトコルが必要。
commentSTRING最長 256 文字のテキスト文字列

17.14.10.6. IPv6

プロトコル ID: ipv6
このタイプのルールはルートチェーンまたは ipv6 チェーンのいずれかに入ります。

表17.8 IPv6 プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAC_ADDR宛先の MAC アドレス
dstmacmaskMAC_MASK宛先の MAC アドレスに適用されるマスク
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
protocolUINT8, STRINGレイヤー 4 プロトコル識別子。protocol に有効な文字列: tcp、udp、udplite、esp、ah、icmpv6、sctp
scrportstartUNIT16有効なソースポート範囲の開始点。プロトコルが必要。
srcportendUINT16有効なソースポート範囲の終了点。プロトコルが必要。
dstportstartUNIT16有効な宛先ポート範囲の開始点。プロトコルが必要。
dstportendUNIT16有効な宛先ポート範囲の終了点。プロトコルが必要。
commentSTRING最長 256 文字のテキスト文字列

17.14.10.7. TCP/UDP/SCTP

プロトコル ID: tcp、udp、sctp
このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.9 TCP/UDP/SCTP プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
scriptoIP_ADDRソース IP アドレス範囲の開始点
srcipfromIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
scrportstartUNIT16有効なソースポート範囲の開始点。プロトコルが必要。
srcportendUINT16有効なソースポート範囲の終了点。プロトコルが必要。
dstportstartUNIT16有効な宛先ポート範囲の開始点。プロトコルが必要。
dstportendUNIT16有効な宛先ポート範囲の終了点。プロトコルが必要。
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
flagsSTRINGTCP のみ: マスク/フラグの形式。マスクおよびフラグを SYN、ACK、URG、PSH、FIN、RST または NONE か ALL のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.10.8. ICMP

プロトコル ID: icmp
注意: このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.10 ICMP プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAD_ADDR宛先 MAC アドレス
dstmacmaskMAC_MASK宛先 MAC アドレスに適用されるマスク
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
srcipfromIP_ADDRソース IP アドレス範囲の開始点
scriptoIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
typeUNIT16ICMP タイプ
codeUNIT16ICMP コード
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.10.9. IGMP、ESP、AH、UDPLITE、'ALL'

プロトコル ID: igmp、esp、ah、udplite、all
このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.11 IGMP、ESP、AH、UDPLITE、'ALL'

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcmacmaskMAC_MASK送信側の MAC アドレスに適用されるマスク
dstmacaddrMAD_ADDR宛先 MAC アドレス
dstmacmaskMAC_MASK宛先 MAC アドレスに適用されるマスク
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
srcipfromIP_ADDRソース IP アドレス範囲の開始点
scriptoIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.10.10. IPV6 経由の TCP/UDP/SCTP

プロトコル ID: tcp-ipv6、udp-ipv6、sctp-ipv6
このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.12 IPv6 経由の TCP、UDP、SCTP プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
srcipfromIP_ADDRソース IP アドレス範囲の開始点
scriptoIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
srcportstartUINT16有効なソースポート範囲の開始点
srcportendUINT16有効なソースポート範囲の終了点
dstportstartUINT16有効な宛先ポート範囲の開始点
dstportendUINT16有効な宛先ポート範囲の終了点
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.10.11. ICMPv6

プロトコル ID: icmpv6
このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.13 ICMPv6 プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
srcipfromIP_ADDRソース IP アドレス範囲の開始点
scriptoIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
typeUINT16ICMPv6 タイプ
codeUINT16ICMPv6 コード
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.10.12. IPv6 経由の IGMP、ESP、AH、UDPLITE、'ALL'

プロトコル ID: igmp-ipv6、esp-ipv6、ah-ipv6、udplite-ipv6、all-ipv6
このタイプのトラフィックについてはチェーンパラメーターは無視されるため、省略するかまたはルートに設定します。

表17.14 IPv6 経由の IGMP、ESP、AH、UDPLITE、'ALL' プロトコルタイプ

属性名データタイプ定義
srcmacaddrMAC_ADDR送信側の MAC アドレス
srcipaddrIP_ADDRソース IP アドレス
srcipmaskIP_MASKソース IP アドレスに適用されるマスク
dstipaddrIP_ADDR宛先 IP アドレス
dstipmaskIP_MASK宛先 IP アドレスに適用されるマスク
srcipfromIP_ADDRソース IP アドレス範囲の開始点
scriptoIP_ADDRソース IP アドレス範囲の終了点
dstipfromIP_ADDR宛先 IP アドレス範囲の開始点
dstiptoIP_ADDR宛先 IP アドレス範囲の終了点
commentSTRING最長 256 文字のテキスト文字列
stateSTRINGNEW、ESTABLISHED、RELATED、INVALID または NONE のコンマで区切った一覧
ipsetSTRINGlibvirt の外側で管理されている IPSet の名前
ipsetflagsIPSETFLAGSIPSet のフラグ。ipset 属性が必要。

17.14.11. 高度なフィルター設定について

次のセクションでは高度なフィルター設定について解説します。

17.14.11.1. 接続の追跡

ネットワークフィルターのサブシステム (Linux 上) では、IP テーブルの接続追跡のサポートを使用します。ネットワークトラフィックの方向性を強制する (状態一致) ほか、ゲスト仮想マシンに対する同時接続数をカウントし、制限するのに役立ちます。たとえば、ゲスト仮想マシン側で TCP ポート 8080 をサーバーとして開くと、クライアントはポート 8080 でゲスト仮想マシンに接続することができます。接続の追跡と方向性の強制により、逆方向となるポート 8080 から (TCP クライアントから) ホスト物理マシンへの接続の開始は妨げられます。さらに重要な点は、追跡を行うことにより、リモート操作によりゲスト仮想マシンへの接続を確立するような攻撃を防ぐことができます。たとえば、ゲスト仮想マシン内のユーザーが攻撃者のサイトでポート 80 への接続を確立した場合でも、攻撃者は逆方向となる TCP ポート 80 からこのゲスト仮想マシンへの接続は開始できません。デフォルトでは、接続の追跡およびトラフィックの方向性の強制を有効にする接続状態一致はオンに設定されます。

例17.9 TCP ポートへの接続をオフにする XML 例

以下の XML の抜粋例では、TCP ポート 12345 への着信接続に対してこの機能をオフにしています。
   [...]
    <rule direction='in' action='accept' statematch='false'>
      <cp dstportstart='12345'/>
    </rule>
   [...]
これにより、TCP ポート 12345 への着信トラフィックが許可されますが、仮想マシン内の TCP ポート 12345 (クライアント) からの接続開始も有効になります。これは状況に適する場合もありますが、 適さない場合もあります。

17.14.11.2. 接続数の制限

ゲスト仮想マシンで確立できる接続数を制限する場合、特定タイプのトラフィックに対して接続数の制限を設けるルールを指定する必要があります。たとえば、仮想マシンに同時に ping を許可するのは 1 つの IP アドレスのみに制限したり、同時に許可されるアクティブな着信 SSH 接続を 1 つに制限する場合などにこの設定が必要になります。

例17.10 接続数に制限を設定した XML サンプル

次の XML の抜粋例を使って接続数を制限することができます。
  [...]
  <rule action='drop' direction='in' priority='400'>
    <tcp connlimit-above='1'/>
  </rule>
  <rule action='accept' direction='in' priority='500'>
    <tcp dstportstart='22'/>
  </rule>
  <rule action='drop' direction='out' priority='400'>
    <icmp connlimit-above='1'/>
  </rule>
  <rule action='accept' direction='out' priority='500'>
    <icmp/>
  </rule>
  <rule action='accept' direction='out' priority='500'>
    <udp dstportstart='53'/>
  </rule>
  <rule action='drop' direction='inout' priority='1000'>
    <all/>
  </rule>
  [...]

注記

制限ルールは、トラフィックを許可するルールの前に XML に記載する必要があります。例17.10「接続数に制限を設定した XML サンプル」 の XML ファイルでは、ポート 22 へ送信される DNS トラフィックがゲスト仮想マシンに到着するのを許可するルールが追加され、SSH デーモンによる DNS ルックアップの失敗に関連する理由で SSH セッションが確立されなくなることを防ぐようにされています。このルールを省くと、SSH クライアントが接続を試行する際に予期しないハングを招く可能性があります。トラフィックの追跡に関連するタイムアウトを扱う場合は十分な注意が必要です。ユーザーがゲスト仮想マシン内で終了させた可能性のある ICMP ping でホスト物理マシンの接続追跡システムに長期のタイムアウトが設定されていると、別の ICMP ping を通過させないことがあります。
最適なソリューションとしては、ホスト物理マシンの sysfs 内のタイムアウトをコマンド「# echo 3 > /proc/sys/net/netfilter/nf_conntrack_icmp_timeout」で調整する方法です。このコマンドにより、ICMP 接続の追跡タイムアウトが 3 秒に設定されます。1 つの ping が終了すると、別の ping が 3 秒後に開始されます。
何らかの理由でゲスト仮想マシンにより TCP 接続が正しく閉じられなかった場合、とくにホスト物理マシンでの TCP のタイムアウト値が長時間設定されている場合などは、接続が長い期間、開いたままになります。また、アイドル接続により接続追跡システム内でタイムアウトが生じ、パケットが交換されると接続が再度アクティブになる場合があります。
ただし、制限が低すぎると新たに開始された接続がアイドル接続を TCP バックオフに強制することがあります。したがって、接続の制限は高目に設定し、新しい TCP 接続での変動がアイドル接続に関連した異常なトラフィック動作の原因にならないようにします。

17.14.11.3. コマンドラインツール

virsh はネットワークフィルターのライフサイクルサポートで拡張されています。ネットワークフィルターサブシステムに関連するコマンドはすべて nwfilter のプレフィックスで開始されます。使用できるコマンドは次の通りです。
  • nwfilter-list : 全ネットワークフィルターの UUID と名前を一覧表示します。
  • nwfilter-define : 新しいネットワークフィルターを定義するか、または既存のフィルターを更新します (フィルター名の入力要)。
  • nwfilter-undefine : 指定したネットワークフィルターを削除します (フィルター名の入力要)。現在使用中のネットワークフィルターは削除しません。
  • nwfilter-dumpxml : 指定したネットワークフィルターを表示します (フィルター名の入力要)。
  • nwfilter-edit : 指定したネットワークフィルターを編集します (フィルター名の入力要)。

17.14.11.4. 既存のネットワークフィルター

以下は、libvirt で自動的にインストールされるサンプルのネットワークフィルターの一覧です。

表17.15 ICMPv6 プロトコルタイプ

プロトコル名説明
allow-arpゲスト仮想マシンに対するすべての着信および発信アドレス解決プロトコル (ARP) トラフィックを許可します。
no-arp-spoofingno-arp-mac-spoofingand no-arp-ip-spoofingこれらのフィルターは、ゲスト仮想マシンによる ARP トラフィックのなりすましを防ぎます。さらに、ARP 要求と返信メッセージだけを許可し、パケットに以下の項目が含まれるよう強制します。
  • no-arp-spoofing - ゲストの MAC および IP アドレス
  • no-arp-mac-spoofing - ゲストの MAC アドレス
  • no-arp-ip-spoofing - ゲストの IP アドレス
low-dhcpゲスト仮想マシンによる DHCP 経由の IP アドレスの要求を許可します (すべての DHCP サーバーから)。
low-dhcp-serverゲスト仮想マシンによる指定 DHCP サーバーからの IP アドレスの要求を許可します。DHCP サーバーのドット付き 10 進数 IP アドレスをこのフィルターへの参照内に指定する必要があります。変数名は DHCPSERVER にしてください。
low-ipv4仮想マシンに対するすべての着信および発信 IPv4 トラフィックを許可します。
low-incoming-ipv4仮想マシンへの着信 IPv4 トラフィックだけを許可します。このフィルターは、clean-traffic フィルターの一部です。
no-ip-spoofingゲスト仮想マシンが、パケット内部のアドレスとは異なるソース IP アドレスを持つ IP パケットを送信することを防ぎます。このフィルターは、clean-traffic フィルターの一部です。
no-ip-multicastゲスト仮想マシンが IP マルチキャストパケットを送信することを防ぎます。
no-mac-broadcast特定の MAC アドレスへの発信 IPv4 トラフィックを拒否します。このフィルターは、clean-traffic フィルターの一部です。
no-other-l2-trafficネットワークで使用される他のフィルターで指定したトラフィックを除き、すべての第 2 層ネットワークトラフィックを拒否します。このフィルターは、clean-traffic フィルターの一部です。
no-other-rarp-trafficqemu-announce-selfqemu-announce-self-rarpこれらのフィルターは、QEMU の自己アナウンス型逆アドレス解決プロトコル (RARP) パケットは許可しますが、他の RARP トラフィックはすべて拒否します。これらのフィルターも、すべて clean-traffic フィルターに含まれています。
clean-trafficMAC、IP および ARP のなりすましを防ぎます。このフィルターはビルディングブロックとして他の複数のフィルターを参照します。
これらのフィルターはビルディングブロックに過ぎないため、ネットワークトラフィックフィルターの機能を果たすためには他のフィルターと組み合わせて使用する必要があります。上記の一覧で最もよく使用されるフィルターは clean-traffic フィルターです。たとえば、このフィルター自体を no-ip-multicast フィルターと組み合わせ、パケットのなりすまし防止に加え、仮想マシンによる IP マルチキャストトラフィックの送信も防ぎます。

17.14.11.5. 独自のフィルターの記述

libvirt で提供されるのは数種類のサンプルネットワークフィルターのみとなるため、独自のフィルターの記述を検討するのもよいでしょう。独自のフィルターを記述する場合、ネットワークフィルターサブシステムについて、またこのシステムが内部でどのように機能するのかを知っておく必要があるかもしれません。また、意図するトラフィック以外のトラフィックは通過できず、意図するトラフィックのみが確実に通過できるようフィルターを行うプロトコルについて十分な知識と理解が必要になります。
ネットワークフィルターサブシステムは、現在 Linux のホスト物理マシン上でのみ利用できるため、QEMU および KVM タイプの仮想マシンでのみ機能します。Linux では、これは ebtables、iptables、ip6tables のサポートに基づいて構築され、これらの機能が使用されます。「サポート対象プロトコル」 の一覧を参照してください。以下のプロトコルは ebtables を使って実装できます。
  • mac
  • stp (スパニングツリープロトコル)
  • vlan (802.1Q)
  • arp、 rarp
  • ipv4
  • ipv6
IPv4 経由で実行されるプロトコルはすべて iptables を使ってサポートされます。IPv6 経由で実行されるプロトコルは ip6tables を使って実装されます。
Linux ホスト物理マシンを使用すると、libvirt のネットワークフィルターサブシステムで作成されたトラフィックフィルタールールはすべて ebtables で実装したフィルターサポートを最初に通過してから、iptables または ip6tables フィルターに移行します。フィルターツリーに mac、stp、vlan arp、rarp、ipv4、ipv6 などのいずれかのプロトコルのルールがある場合、まず etable のルールと一覧表示されている値が自動的に使用されます。
同じプロトコルの複数のチェーンを作成することができます。チェーン名には、以前にエミュレートされたプロトコルのいずれかのプレフィックスを含める必要があります。ARP トラフィックの処理用に追加のチェーンを作成するには、arp-test などの名前を持つチェーンを指定することができます。
たとえば、ip プロトコルフィルターを使用し、許可される UDP パケットのポート、ソースと宛先の IP アドレス、プロトコルの属性を指定して、ソースと宛先のポートごとに UDP トラフィック上でフィルターをかけることが可能です。これにより、ebtables を使った早期の UDP トラフィックのフィルターが可能になります。ただし、UDP パケットなどの IP または IPv6 パケットが ebtables 層を通過した後に、iptables または ip6tables ルールをインスタンス化する 1 つ以上のルールがフィルターツリーにある場合は、UDP パケットを通過させるルールをこれらのフィルター層にも指定する必要があります。これは、適切な udp または udp-ipv6 のトラフィックフィルターノードを含むルールで実行できます。

例17.11 カスタムフィルターの作成

以下の要件を満たすフィルターが必要であると仮定します。
  • 仮想マシンのインターフェースでの MAC、 IP、 ARP のなりすましを防ぐ
  • 仮想マシンのインターフェースの TCP ポート 22 と 80 のみを開く
  • 仮想マシンによるインターフェースからの ping トラフィック送信を許可する。ただしインターフェース上での仮想マシンに対する ping には応答させない
  • 仮想マシンによる DNS ルックアップを許可する (ポート 53 への UDP)
なりすまし防止の要件は既存の clean-traffic フィルターで満たすことができるため、カスタムフィルターからこのフィルターを参照させることで防止することができます。
TCP ポート 22 と 80 のトラフィックを許可するため、2 種類のルールを追加します。ゲスト仮想マシンによる ping トラフィックの送信を許可するために ICMP トラフィックにルールを 1 つ追加します。単純にするため、ゲスト仮想マシンからの一般的な ICMP トラフィックの開始を許可し、ICMP echo の要求および応答メッセージに対する ICMP トラフィックの指定を行ないません。他のすべてのトラフィックについては、ゲスト仮想マシンからの発信および着信すべてが遮断されます。これを実行するには、他のすべてのトラフィックをドロップするルールを追加します。ゲスト仮想マシン名は test、フィルターを関連付けるインターフェースは eth0 とし、作成するフィルターには test-eth0 という名前を付けるとします。
上記をネットワークフィルターの XML に反映させると以下のようになります。
<filter name='test-eth0'>
  <!- - This rule references the clean traffic filter to prevent MAC, IP and ARP spoofing. By not providing an IP address parameter, libvirt will detect the IP address the guest virtual machine is using. - ->
  <filterref filter='clean-traffic'/>

  <!- - This rule enables TCP ports 22 (ssh) and 80 (http) to be reachable - ->
  <rule action='accept' direction='in'>
    <tcp dstportstart='22'/>
  </rule>

  <rule action='accept' direction='in'>
    <tcp dstportstart='80'/>
  </rule>

  <!- - This rule enables general ICMP traffic to be initiated by the guest virtual machine including ping traffic - ->
  <rule action='accept' direction='out'>
    <icmp/>
  </rule>>

  <!- - This rule enables outgoing DNS lookups using UDP - ->
  <rule action='accept' direction='out'>
    <udp dstportstart='53'/>
  </rule>

  <!- - This rule drops all other traffic - ->
  <rule action='drop' direction='inout'>
    <all/>
  </rule>

</filter>

17.14.11.6. カスタムフィルターのサンプル

上記の XML 内のルールの 1 つにはゲスト仮想マシンのソースまたは宛先アドレスとなるいずれかの IP アドレスが含まれていますが、トラフィックのフィルターは正しく動作します。これは、ルールの評価はインターフェースごとに内部的に発生しますが、ルールがソースや宛先の IP アドレスではなく、パケットを送信したか、または受信するインターフェース (tap) に基づいて追加で評価されるためです。

例17.12 ネットワークインターフェースの詳細部分のサンプル XML

以下の XML の抜粋は、test ゲスト仮想マシンのドメイン XML 内にあるネットワークインターフェースの記述例を示しています。
   [...]
    <interface type='bridge'>
      <source bridge='mybridge'/>
      <filterref filter='test-eth0'/>
    </interface>
   [...]
ICMP トラフィックをさらに厳密に制御し、ICM echo の要求はゲスト仮想マシンからしか送信できないようにすると共に、ICMP echo の応答もゲスト仮想マシンでしか受信できないようにするには、上記の ICMP ルールを次の 2 つのルールに置き換えます。
  <!- - enable outgoing ICMP echo requests- ->
  <rule action='accept' direction='out'>
    <icmp type='8'/>
  </rule>
  <!- - enable incoming ICMP echo replies- ->
  <rule action='accept' direction='in'>
    <icmp type='0'/>
  </rule>

例17.13 カスタムフィルターのサンプル 2

この例では、前述の例と同じようなフィルターを構築していますが、ゲスト仮想マシン内にある ftp サーバーに関連して要件の一覧を拡張しています。このフィルターの要件は次の通りです。
  • ゲスト仮想マシンのインターフェースでの MAC、IP、ARP のなりすましを防ぐ
  • ゲスト仮想マシンのインターフェースの TCP ポート 22 と 80 のみを開く
  • ゲスト仮想マシンによるインターフェースからの ping トラフィック送信を許可するが、インターフェース上でのゲスト仮想マシンに対する ping には応答させない
  • ゲスト仮想マシンによる DNS ルックアップを許可する (ポート 53 への UDP)
  • ftp サーバーを有効にして (アクティブモード)、ゲスト仮想マシンの内側で実行できるようにする
ゲスト仮想マシン内で FTP サーバーを実行できるようにする追加要件は、FTP 制御トラフィックに対してポート 21 をアクセス可能にし、ゲスト仮想マシンによるゲスト仮想マシンの TCP ポート 20 から FTP クライアント (FTP アクティブモード) へ向けて発信する TCP 接続の確立を許可することになります。このフィルターは複数の方法で記述することができますが、以下の例では 2 種類のソリューションを示します。
1 つ目のソリューションでは、Linux ホスト物理マシンの接続追跡フレームワークとのつながりを提供する TCP プロトコルの状態属性を利用します。ゲスト仮想マシンが開始した FTP データ接続の場合 (FTP アクティブモード)、RELATED 状態を使ってゲスト仮想マシンによって開始された FTP データ接続が既存の FTP 制御接続の結果である (または関連性がある) ことを検出することができます。これにより、パケットがファイアウォールを通過できるようになります。ただし、RELATED 状態は、FTP データパスの TCP 発信接続の 1 番目のパケットにのみ有効になります。以後、状態は ESTABLISHED になり、この状態が着信と発信の両方向に一律に適用されます。これはすべてゲスト仮想マシンの TCP ポート 20から発信された FTP データトラフィックに関連します。これが次のソリューションにつながります。
<filter name='test-eth0'>
  <!- - This filter (eth0) references the clean traffic filter to prevent MAC, IP, and ARP spoofing. By not providing an IP address parameter, libvirt will detect the IP address the guest virtual machine is using. - ->
  <filterref filter='clean-traffic'/>

  <!- - This rule enables TCP port 21 (FTP-control) to be reachable - ->
  <rule action='accept' direction='in'>
    <tcp dstportstart='21'/>
  </rule>

  <!- - This rule enables TCP port 20 for guest virtual machine-initiated FTP data connection related to an existing FTP control connection - ->
  <rule action='accept' direction='out'>
    <tcp srcportstart='20' state='RELATED,ESTABLISHED'/>
  </rule>

  <!- - This rule accepts all packets from a client on the FTP data connection - ->
  <rule action='accept' direction='in'>
    <tcp dstportstart='20' state='ESTABLISHED'/>
  </rule>

  <!- - This rule enables TCP port 22 (SSH) to be reachable - ->
  <rule action='accept' direction='in'>
    <tcp dstportstart='22'/>
  </rule>

  <!- -This rule enables TCP port 80 (HTTP) to be reachable - ->
  <rule action='accept' direction='in'>
    <tcp dstportstart='80'/>
  </rule>

  <!- - This rule enables general ICMP traffic to be initiated by the guest virtual machine, including ping traffic - ->
  <rule action='accept' direction='out'>
    <icmp/>
  </rule>

  <!- - This rule enables outgoing DNS lookups using UDP - ->
  <rule action='accept' direction='out'>
    <udp dstportstart='53'/>
  </rule>

  <!- - This rule drops all other traffic - ->
  <rule action='drop' direction='inout'>
    <all/>
  </rule>

</filter>
RELATED 状態を使ってフィルターを試す前に、適切な接続追跡モジュールがホスト物理マシンのカーネルにロードされていることを確認する必要があります。カーネルのバージョンによっては、ゲスト仮想マシンで FTP 接続が確立される前に次の 2 つのコマンドのいずれかを実行する必要があります。
  • # modprobe nf_conntrack_ftp - where available OR
  • # modprobe ip_conntrack_ftp if above is not available
FTP 以外のプロトコルを RELATED 状態と併用する場合は、該当するモジュールをロードする必要があります。各プロトコルに使用できるモジュールは、ftp、tftp、irc、sip、sctp および amanda です。
2 つ目のソリューションでは、前述のソリューションより多くの接続状態フラグを利用します。このソリューションでは、トラフィックの一番最初のパケットが検出されると接続の NEW 状態が有効になる点を利用しています。続いて、最初のパケットのフローが許可されると、そのフローは接続とみなされ、ESTABLISHED 状態に移行します。したがって、ESTABLISHED 接続のパケットのゲスト仮想マシンへの着信、またゲスト仮想マシンからの発信を許可する汎用ルールを記述することができます。NEW 状態で識別できる一番最初のパケットについての特定ルールを記述し、データを受け取ることができるポートを指定して実行できます。明示的に許可されていないポートに向けたパケットはすべてドロップされるため、ESTABLISHED 状態にはなりません。そのポートから送信される後続パケットもすべてドロップされます。
<filter name='test-eth0'>
  <!- - This filter references the clean traffic filter to prevent MAC, IP and ARP spoofing. By not providing and IP address parameter, libvirt will detect the IP address the VM is using. - ->
  <filterref filter='clean-traffic'/>

  <!- - This rule allows the packets of all previously accepted connections to reach the guest virtual machine - ->
  <rule action='accept' direction='in'>
    <all state='ESTABLISHED'/>
  </rule>

  <!- - Th