仮想化方式について

June 25, 2018

概要

ハードウェア仮想化方式には、PV 、HVM 、またハイブリッド型など色々存在する。
このエントリはこれらの (複雑な) 仮想化方式についてメリット/デメリット、また歴史的流れなどを踏まえた上で可能な限り簡単に説明することを目的とする。
まずは、純粋な PV/HVM について簡単にまとめ、その後ハイブリッド仮想化について優位性を踏まえた上で説明を加える。

参考

本エントリを作成するにあたり、以下の資料を参考とした。

PV/HVM について

Xen の仮想化タイプは大きく分けて PV 、HVM の二つがある。
まずは PV と HVM を簡単に説明し、それぞれの特徴を理解する。

PV

いっそのことゲスト OS に「君は VM ですよ!」ってことを知っててもらい、ハードウェアをソフトウェアでエミュレートするオーバーヘッドを軽減しようという仮想化方式。
ゲスト OS にとって、最大の違いはゲスト OS の Kernel がリング 1 で実行される、つまり特権命令が実行できない点にある (Xen Hypervisor がリング 0 で実行するため)。ゲスト OS の特権命令などの処理を Xen Hypervisor にジャンプする (hypercall) ように事前に kernel を書き換えておくことで、オーバーヘッドを軽減している。
ただし、ゲスト OS の書き換えが必要になるため、対応 OS が限定されたり、カーネルに対するセキュリティ修正プログラムの適用などが行えない場合がある。
その他の特徴としてはざっくり以下

  • ネットワーク/ブロックデバイス等には PV ドライバを用いる (NetFront/Back, BlockFront/Back)
  • PV ドライバは基本的に Dom0 と DomU で共有されたメモリセグメント内のリングバッファである
  • いきなり Protected Mode で起動する

HVM

ハードウェアを完全にエミュレート (by qemu) し、ゲスト OS を騙して、ハードウェアを占有していると思わせる。そのためゲスト OS のソースコードを書き換える必要がない。
その昔はバイナリバイナリトランスレーションという方法が用いられていた。これは何かというと、ゲスト OS はリング 0 で実行することを前提に設計されているため、当然のごとくリング 0 レベルの特権命令を発行するが、実際にはリング 1 で実行されているため、例外が発布される。その例外を Hypervisor が監視し特権命令をエミュレートしてゲスト OS に返す、という方法取るものである。しかし、ゲスト OS の命令発行を常時監視することや、命令のエミュレーションが大きなオーバーヘッドになっていた。そのため、特権命令のエミュレートの必要がなく、hypercall を使える PV が昔はパフォーマンス的にすぐれた仮想化方式として認識されていた。

しかし、Intel VT-x などの CPU による仮想化支援機構により、このオーバーヘッドが改善された。Intel VT-x では “VMX root” “VMX non-root” という、リング 0 ~ 3 とは異なる新たな動作モードを追加し、ゲスト OS を VMX non-root で、hypervisor は VMX root で実行するようにした (ゲスト OS はリング 0 と 3 を用いる。VMX root と VMX non-root の切り替えに関しては概念上、リング -1 を追加するものと考えて良い)。ゲスト OS が特権命令を発行した場合に、CPU は VMX root に切り替わり、hypervisor モードとなる。このように特権命令発行時のオペレーションがハードウェアで支援され、hypervisor はゲスト OS の特権命令の発行を監視してエミュレートする必要がなくなったことにより、オーバーヘッドが軽減された。

さらに、Intel VT-x Gen2 では EPT (Extended Page Table) という機能が新たに追加されている。それまでは、ゲスト OS の仮想メモリアドレス <-> ゲスト OS の物理メモリアドレス (本当は物理ではないけど) の変換をした後に、“hypervisorが” ゲスト OS が想定する物理メモリアドレスを真の物理的なメモリアドレス (hypervisor が管理する物理アドレス) にマッピングしていた。EPT では、ゲスト OS の物理アドレス空間から、真の物理アドレス空間への変案がハードウェア的に支援され、メモリ変換処理にかかっていたオーバーヘッドが軽減された。
実際に性能比較を行なっている記事があったので、気になる方は[http://www.nkjmkzk.net/?p=1009 こちら]

ハイブリッド仮想化方式について

ハイブリッド仮想化ってなんだ?って話に移る前に、一度上記で説明した PV/HVM の利点についてそれぞれ簡単にまとめる。

  • PV: ハードウェアをエミュレートしないモード。ゲスト OS を書き換える必要があるが、特権命令を Hypercall にジャンプさせてオーバーヘッドを軽減させることができる。ネットワーク/ブロックデバイスなどを利用する際には PV ドライバを用いて、Dom0 を経由させる。
  • HVM: ハードウェアを完全にエミュレートするため、ゲスト OS を書き換える必要がない (ソースコードが公開されていない Windows OS などもゲストとして利用可能)。また Intel VT-x などの CPU による仮想化支援機構を利用可能。

ハイブリッド仮想化とは、両方の良いところを合わせた仮想化モード、つまり PV ドライバを使用しつつ、ゲスト OS の書き換えを必要とせず、また CPU の仮想化支援機構を利用できる、なんていう虫のいい仮想化方式のこと。いくつか歴史的にパターンがあるので順に説明する。

PV on HVM

PV on HVM モードとは、HVM モードにおいて、ネットワーク及びブロックデバイスにのみ PV ドライバを用いるという仮想化方式である。これにより、HVM の恩恵に預かりながら PV ドライバーを利用できる。PV on HVM モードについては EC2 のドキュメントにも記載がある。

(Linux AMI 仮想化タイプ)
https://docs.aws.amazon.com/ja_jp/AWSEC2/latest/UserGuide/virtualization_types.html

PV on HVM
従来、準仮想化のゲストはストレージやネットワークの操作については、HVM のゲストよりも高いパフォーマンスを実現していました。これは、準仮想化のゲストでは I/O 用の特別なドライバー (ネットワークとディスクのハードウェアをエミュレートする際のオーバーヘッドが回避されます) を活用することができたためです。これに対して、HVM のゲストでは、エミュレートされたハードウェアに対する命令を変換する必要がありました。現在では、このような PV ドライバーを HVM のゲストで利用できるようになりました。このため、準仮想化された環境で実行するための移植ができないオペレーティングシステム (Windows など) でも、これらのドライバーを使用することで、ストレージやネットワークの I/O でパフォーマンスの向上を確認することができます。このような PV on HVM ドライバーを使用すると、HVM のゲストで、準仮想化のゲストと同じまたはより優れたパフォーマンスを実現できます。

HVM ゲストで PV ドライバを用いる際は起動時に以下のような関連メッセージがコンソールに出力される。

[    0.000000] Xen Platform PCI: I/O protocol version 1  
[    0.000000] Netfront and the Xen platform PCI driver have been compiled for this kernel: unplug emulated NICs.  
[    0.000000] Blkfront and the Xen platform PCI driver have been compiled for this kernel: unplug emulated disks  
[    0.000000] Xen HVM callback vector for event delivery is enabled  
[    2.377167] vbd vbd-5632: 19 xenbus_dev_probe on device/vbd/5632  
[    2.378134] blkfront: xvda: flush diskcache: enabled  
[    6.266448] Initialising Xen virtual ethernet driver.  

PVHVM

PV on HVM モードでネットワーク及びブロックデバイスについては PV ドライバーが利用できるようになったものの、まだ他にいくつかの非効率な点があった。例えば割り込みコントローラー (APIC や IOAPIC) だ。HVM ではエミュレートされた割り込みコントローラーをゲストカーネルに提供しており、APIC を介する命令全てがソフトウェアによるデコードを必要とした。
Stefano Stabellini さんは OS が Xen 配下で HVM モードで起動しているかどうかを検知する Linux パッチを開発し、もし HVM モードで起動していれば、エミュレートされた割り込みコントローラーやタイマーではなく、Paravirtualized なものにスイッチするようにした。これが PVHVM モードと呼ばれる。これにより、ネットワーク、ディスク、割り込み及びタイマーが全て準仮想化 (PV ドライバ) された HVM ゲストを利用できるようになった。

ゲスト OS は依然として、エミュレートされたマザーボード、PCI バスなどを利用して boot する上に、Legacy Boot (BIOS から始まり、16 bit モードで起動する) である、という点は変わらないものの、PV ドライバによる恩恵及び CPU による仮想化支援が受けられる PVHVM モードは現状最強

PVH

これは PV モードで動作するゲスト OS が CPU の仮想化支援を受けられるようにしたもの。つまり、I/O や boot に関しては PV ドライバを使いつつ、Ring -1 や EPT などのハードウェアによる支援も受けられるというモードである。ハイブリッド仮想化の中では最も良いパフォーマンスを発揮すると言われている。

Spectrum of Virtualization Types

以上の仮想化タイプをわかりやすく二次元スペクトラムにしたのが以下の図。HVM with PV drivers が PV on HVM 、HVM with PVHVM drivers が PVHVM となる。

xen colors

SR-IOV

SR-IOV (Single Root I/O Virtualization) は PCI デバイス側で仮想化をサポートするための規格。デバイスへの I/O 要求に必要な処理が PCI デバイス側でハードウェア的にサポートされる様式であり、NIC に関して言えばベアメタルの 95 % のパフォーマンスが発揮できる (PV ドライバより優秀)。なお、ハードウェアによる仮想化支援が必要なため HVM でのみ利用可能。
SR-IOV は別にネットワークデバイスに限ったわけではなく、理論的にはどんな PCI-E デバイスでサポートされる (NVMe など)。


 © 2023, Dealing with Ambiguity