Java仮想マシン
Java仮想マシン(Java Virtual Machine, JVM)とは、Javaプログラムを実行するときに起動される仮想マシンである。
概要[編集]
Javaの設計思想の1つに、"WORA: Write once, run anywhere"、つまり作成したアプリケーションを書き直さずにそのままどのOSでも実行できるようにする、というものがあり、JVMはそれを実現するための仮想マシンである。
JVMは、特定のハードウェアアーキテクチャーを模倣したものではなく、Javaの実行コードに対してはスタックマシン[1]として振る舞い、VM内部では必要に応じてOSシステムコールを行う仕組みである。例えば、足し算プログラムを動かす場合、数値の計算自体はVMで完結するが、計算に使う数値の入力制御や結果の出力制御はVMが間接的にOSのシステムコールを呼び出している。
初期バージョンは、ほぼ単純にJavaバイトコードに対応するインタープリターであったため、動作は低速であった。後に最適化技術が導入され、中間コード方式としては比較的高速なパフォーマンスを得られるようになってきている。
動作[編集]
Java実行ファイル[2]を実行すると、JVMはOSのプロセスとして起動・常駐し、エントリーポイントとして指定されたクラスのmain
メソッドを呼び出す。何かしらの異常が発生していない限り、メインスレッドの処理がすべて終了するか、終了コマンド(System.exit
メソッド)が実行されるまでJVMプロセスは常駐し続ける。
前述の通り、JVMは特殊なスタックマシンである。一般的なレジスターマシンとの大まかな差異は以下の通り。
- レジスターの代わりに、スタックに格納された値を使って演算する。例えば、加算命令(add)はスタックから値を2つ取り出して加算し、結果をスタックに積む[3]。
- 機械語の命令としては抽象的なものがある(invoke、new、throwなど)
- 外部装置との直接操作はできない。それらの処理をラップしたメソッド経由で行う。
JVMには実行時に最適化を行う機能があり、最適化のために一部のJavaコードを書き換えたりネイティブコードに置き換えたりする。
ソフトウェアとしての構成[編集]
実行形式としての[4]JVMは、Java実行ファイル[2]に含まれる。
OpenJDK[5]では、JVMを含むJava本体のネイティブコード部分は、主にC++言語で書かれている。コードベースは共通だが、アーキテクチャーごとに異なるコードが含まれるので、ビルドはアーキテクチャーごとに行う必要がある。このようにして、JVMを含むJavaはアーキテクチャーの差異を吸収している。ただし、JVMはJVM仕様を満たしていれば良いので、OpenJDKと同様の構成であることは必須要件ではない。
JVM言語[編集]
Java言語以外のプログラミング言語で書かれたプログラムをコンパイルして中間コード(クラスファイル)を作り、JVMで動作させる言語は、JVM言語と呼ばれることがある。
JVM言語はコンパイラーと追加したクラスライブラリーを提供すれば、実行環境はJVMを使ってプログラムを実行することができる。
JVMは仮想マシンとして仕様が比較的シンプルで性能が良いため、多くの言語でこの方式が採用されている。