仮想機械
仮想機械(かそうきかい、仮想マシン、バーチャルマシン、virtual machine、VM)とは、アプリの使用を最適化する方法であり、コンピュータの動作を再現するソフトウェアである。すなわち、エミュレートされた仮想のコンピュータそのものも仮想機械という。仮想機械によって、1つのコンピュータ上で複数のコンピュータやOSを動作させたり、別のアーキテクチャ用のソフトウェアを動作させることができ、アプリケーションが互いに干渉するのを防げる。
仮想機械によるアプローチは、企業や個人がレガシーアプリケーションに対処し、1台のコンピュータで処理できるさまざまな種類のアプリケーションを最大化することで、ハードウェアの使用を最適化するための一般的な方法である。
システム仮想機械はシステム全体を再現し、その上でOSを動かすことを可能にする。動作させるOSにいくらかの変更を加えることが必要な場合(準仮想化)もある。
システム仮想機械では、複数の仮想機械に計算資源やメモリ資源、ディスク資源を効率的に配分(スケジュール)したり、ハードウェア割り込みなどを伝達する必要がある。これらを制御するプログラムをハイパーバイザと呼ぶ。
システム仮想機械は、ユーザーやプログラムから「別のコンピュータ」に見えるもの(OS環境を実現するもの)を指すが、コンピュータの初期には仮想記憶やマルチタスク、マルチユーザー、タイムシェアリングなど、現在ではOSの機能となった技術を含める場合がある。仮想機械の技術はメインフレームで使われていたが、現在でコンピュータによるサービス提供の分野で一般的な技術となりつつある。
クラウドコンピューティングにおいてハードウェアに依存しない仮想実行環境の構築は基盤技術(IaaS)として利用される。
1958年 IBM 709(マイクロコードによる、商用初の別アーキテクチャのエミュレータ)
1961年 バロース B5000(商用初の仮想記憶装置)
コンピュータ・アーキテクチャの確立(マイクロコードによる上位互換の確立)
CP-67(商用初の仮想化OS)
1970年 IBM System/370(商用初の複数アドレス空間)
1973年 IBM System/370 モデル158/168(商用初の物理分割)
1985年 インテル i386で仮想86モード採用
1987年 IBM PR/SM(商用初のファームウェアによる論理分割 (LPAR))
1995年 Java公式発表(Java仮想マシンの登場)
1997年 サン・マイクロシステムズ ダイナミックシステムドメイン(DSD、UNIXサーバでは初の物理分割機能)
1999年 VMwareの登場(x86システムの本格的な商用仮想化OS)
2001年 IBM pSeries(UNIXサーバでは初の論理分割 (LPAR))
2008年3月 オラクル Oracle VMを発表(ベースはXen)
2008年6月 マイクロソフト Hyper-V(開発コード名 Viridian)を発表
ハードウェア(ビルディングブロック)の機能による物理分割
IBMのPPAR、サン・マイクロシステムズのDSD、ヒューレット・パッカードのnParsなど。ブレードサーバを含む場合もある。
ハードウェア(マイクロコード)の機能による論理分割
IBMのLPAR、サン・マイクロシステムズのLDOM、ヒューレット・パッカードのvParsなど
z/VM、VMware、Xen、VirtualBox、Hyper-Vなど。内部的にハードウェアの機能を活用している場合も多い。
AIX 6 ワークロードパーティション、Solaris10 Solarisコンテナなど。なおHyper-VはWindows Server 2008の一部として提供されるが、単体提供もされ、技術的・構造的には専用の仮想化OSである。
z/OSワークロードマネージャ、AIXワークロードマネージャ、Solarisリソースマネージャ、HP-UXワークロードマネージャなど
1940年代-1950年代のコンピュータは、機種ごとにアーキテクチャが異なるのがあたりまえであったが、既存の設計を参考にすることで新規設計のリスクを避けたり、よそのコンピュータの既存のプログラム・ライブラリを流用するためなどの目的で、既存機と命令セットに互換性を持たせたり論理設計を共通にした、一種の互換機と言えるマシンも存在した。たとえばEDSACはよく参考にされた。
1958年 IBM 709は、既存のIBM 704の命令セットをマイクロコードでエミュレーションし、上位互換性を提供した。
1964年 IBM System/360は、同様に既存のIBM 1401やIBM 1620の命令セットをマイクロコードでエミュレーションした。また、コンピュータ・アーキテクチャを定義し標準化し、以後の互換性を提供した(通常は仮想化と呼ばれないが、プログラムから見れば一種の仮想機械と言える。この効果として、メインフレームではアセンブリ言語でもバイナリでも、40年以上経過した現在まで互換が続いている)。
1973年 IBM System/370モデル158およびモデル168により、物理分割(PPAR)をサポート。単一のコンピュータとしても、複数のコンピュータとしても使用可能。ただし細かいリソースの割り当てはできず、変更にはコンピュータ全体の再起動が必要。
1987年 IBM 3090 の PR/SMにより、多数の論理区画(LPAR)を作成し、コンピュータ全体の停止を伴わず、より柔軟なリソースの割り当てが可能となった。
IBMのPR/SMに相当する機能には、日立製作所 PRMFなどがある。
1964年 IBM System/360では、商用初の仮想化OSである CP-40、CP-67により、ひとつのコンピュータで複数の仮想コンピュータを作成し、それぞれでゲストOS (MVSやCMSなど)を稼動させる事ができた。この仮想化OSは VM/CMS となり、現在も z/VM として、多数のゲストOS(Linuxなど)を同時稼動させる用途でも使われている。
IBMのz/VMに相当する製品には、富士通 AVM、日立製作所 VMS などがある。
OSの機能による各種リソースの仮想化には、仮想記憶やマルチタスク、マルチユーザー、タイムシェアリングなどがある。
主記憶装置の仮想化である仮想記憶は、商用では1961年のバロース B5000で登場し、1970年のIBM System/370で広く普及した。
マルチタスク(アプリケーションによるマルチプログラミングではなく、OSの機能によるマルチタスク)は商用では、OS/360のバリエーションのひとつであるMVTと、後継のMVSで登場し、広く普及した。入出力待ちなどにCPUが他の処理を行えるため、処理の応答時間短縮と全体のスループット向上がもたらされた。
なお、メインフレームにおけるこれらの「マルチタスク」は、単に複数のプログラムが同時に動かせるというだけではなく、複数の独立したアドレス空間(リージョン)を作成し、ハードウェアの機能も使用して完全に分離し、同時稼働するプログラム同士は直接見えない(バグや悪意あるプログラムでも相互に干渉できない)ものである。この点では、後の各種UNIXやWindowsなどの「マルチタスク」と比較すると、「仮想機械」に近いレベルのもので、可用性やセキュリティも向上した。同様の仕組みは2009年現在、MVSの後継のz/OSの他、IBM z/VSE、富士通 MSP/XSP、日立製作所 VOS3 などでも採用している。
タイムシェアリング(時分割多重)による並列処理(マルチユーザー)は、アプリケーションプログラムやユーザーに、複数のコンピュータを同時使用するイメージをもたらし、オンライン・リアルタイム処理の普及をもたらした。なお、マルチタスクとタイムシェアリングは別の技術であるが、現在では組み合わせて使用されている。(上記のMVSなどでは、マルチタスク環境の一部で、タイムシェアリング環境を稼働させ、それによりマルチユーザーを実現している。またマルチタスク自体も、初期には入出力待ちによる割り込みが基本であったが、現在ではタイムシェリングによる割り込みを併用している。)
1979年 IBM System/38は、TIMI(Technology Independent Machine Interface、技術に依存しないマシンインターフェイス)を採用した。TIMIは、メインフレームで採用されたマイクロコードによる互換性確保を更に進めたもので、主に水平型レベル・マイクロコードにより実現され、ハードウェア・アーキテクチャ(CPU命令セット等)とプログラムを分離している。プログラムの配布は中間コードであるバイトコードで行われ、インストール時にハードウェアの命令セットに展開される。このためソースプログラムを配布すること無く、実行時の性能を犠牲にすることもなく、別のアーキテクチャのハードウェアへの移行も容易である。実際、CPUアーキテクチャの移行(独自CISC→POWER)も容易に行えたとされる。
TIMIはSystem/38後継のAS/400、iSeries、System i、Power Systems i Edition に、現在でも使用されている。また現在はLPARなどと併用できる(後述のPowerVMを参照)。
各社の商用ミッドレンジコンピュータ(オフィスコンピュータ、ミニコンピュータ)では、TIMIと同等の機能を持ったシリーズは、過去も現在も存在しない。
商用UNIXベンダーによる仮想化技術には以下がある。現在の仮想化技術は各種のハードウェアとソフトウェアが密接に連携しており、またベンダーにより各技術の範囲が異なるため、ベンダー単位に記載する。
IBM PowerVM - 3エディションあり、全モデルに搭載。
LPAR (論理区画) - ファームウェアによる論理分割。複数OSを稼働。
マイクロパーティショニング - CPUを最小10分の1から100分の1単位でLPARに割り当てる。
WPAR - OS(AIX)の標準機能。アプリケーションから見て複数のOS環境(インスタンス)を提供。古いAIX V5.2も、WPARで稼動可能。
AIX WLM - ミドルウェアの機能でアプリケーションのワークロードを制御。
Sun N1構想(unified virtualization manager environment)
DSD (dynamic system domain) - 物理分割。動的なリソース移動も可能。上位機種のみ。
LDOM (logical domain) - ファームウェアによる論理分割。複数OSを稼働。上位機種のみに提供予定。
Solarisコンテナ - OS(Solaris 10)の標準機能。アプリケーションから見て複数のOS環境(インスタンス)を提供。
Solarisリソース・マネージャ - ミドルウェアの機能でアプリケーションのワークロードを制御
HP Virtual Server Environment for HP-UX
nPartitions(nPars) - ハードウェアによるパーティショニング技術
Virtual Partitions(vPars) - nParをさらに分割できる論理パーティション技術、1プロセッサ単位で構成
HP Integrity Virtual Machines (Integrity VM) - 各パーティションにプロセッサ・リソースを5% - 100%の範囲で動的に割り当てる、柔軟なsub-CPUパーティションニング技術 。
HP-UX Workload Manager -  パーティショニング、クラスタ、ユーティリティ・プライシングと連携し、サービスレベル維持に向けた リソース割り当てを自動化 。
Apple macOS
Hypervisor.framework -  macOS 10.10以降
Virtualization framework - macOS 11.0以降
UnixやLinux、Windows上で動作する仮想マシンには、VMwareやXen、Oracle VM(ベースはXen)、Hyper-Vなどがある。物理的資源を区分けして特定のワークロードがシステム全体を独占させない機構(仮想マシンモニタ)を持つ。
一台のコンピュータを複数のコンピュータとして使うことができる。オペレーティングシステムの変更なしに複数のゲストオペレーティングシステムを稼働できる。稼働させる複数のゲストオペレーティングシステムは、全く別の種類のオペレーティングシステムであることも可能である。
元々仮想マシンモニタはメインフレームにおいてその資源を各ワークロードの負荷に応じて動的に分割し、システム全体の利用効率を上げるために用いられた。計算機が高性能化した現在では、小規模なWebホスティングのような処理であっても、それらを仮想マシンモニタを用いて並列に実行することが行われている。
1985年 インテルの80386で採用された仮想86モードは、保護モード導入以前のx86のアーキテクチャに則ったタスクを保護モード上で実行する仮想機械を提供する。 OS/2 2.0 や Windows 3.0などのDOS互換環境(仮想DOSマシン)で使用された。
現在のCPUアーキテクチャ(SPARC, POWER, IA-64など)では、それぞれ仮想マシンソフトウェアとOSによる仮想化を支援する命令セットを持っている。
いくつかのアプリケーション・プログラムを動作させるための仮想機械。いくつかのプログラミング言語やその実装では理論上の機械によって実行されることを想定しているので、その機械をエミュレートする場合が多い。
ソフトウェアによる仮想CPUにバイトコードを実行させる形式が一般的である。バイトコードの実行方法にはインタプリタ方式、実行前に全バイトコードをネイティブに変換する事前コンパイル方式、実行時コンパイル方式がある。現在では、性能の観点から実行時コンパイル方式が主流である。
ハードウェアの制約がないのが特徴である。
型つきの演算をサポートしている仮想機械もある。
これらの仮想機械は理論的に設計されたものであるが、実行を最適化するために対応するハードウェアが製造される場合もある。
PascalのPコードマシンはウェスタン・デジタル MCP-1600チップセットが作られた
Javaでは、サン・マイクロシステムズのpicoJavaなどのJava processorがある。
ARMアーキテクチャにはJazelleと呼ばれるJavaバイトコードのための拡張がある。