新たな歴史の1ページ~Oracle Code One 2018現地レポート

【Oracle Code Oneレポート】Oracleが開発中の仮想マシン「GraalVM」で何ができるか

この記事を読むのに必要な時間:およそ 3 分

2018年10月22日から25日にかけての4日間,米サンフランシスコのMoscone CenterにおいてOracle主催の開発者向けイベント「Oracle Code One 2018」が開催されました。これは,これまでは「JavaOne Conference」として開催されていたイベントの後継となるものです。名称が変更された背景には,対象となる技術の裾野を広げてエンジニア同士のコラボレーションを促進しようという目的があります。多言語対応という時代の流れを取り入れた形と言えます。

Oracle自身,多言語対応の鍵となるさまざま技術を開発していますが,その1つに「GraalVM」があります。これはJava技術をベースとした多言語対応の汎用仮想マシンです。本稿では,このGraalVMについて,Oracle Code Oneで見た姿をレポートします。

GraalVMとは

GraalVMは,Java仮想マシン(以下,JVM)およびJITコンパイラ(Just-in-Timeコンパイラ)の技術を利用して作成された多言語対応の汎用仮想マシンです。Oracleが開発し,オープンソースで公開されています。

もともとJVMは,ScalaやKotlin,Groovyなど,Java以外の言語の実行にも対応しています。一般的には,これはコンパイラがJVM用のバイトコードを生成し,それをJVMが実行するという仕組みで実現されており,総称して「JVM言語」と呼ばれています。JRubyやJythonといった,既存言語のJVM用実装もJVM言語の一種と言えます。

これに対してGraalVMは,JavaやJVM言語だけでなく,JavaScriptやR言語,RubyやPython,そしてC/C++のようなLLVMベースの言語の実行にも対応します。同一の仮想マシンを用いて異なる複数の言語を実行できるだけでなく,複数の言語のコードが混在したプログラムを実行することもできます。

GraalVMの概念図

GraalVMの概念図

GraalVMには,⁠Graal」「Truffle」という2つの主要技術が含まれています。GraalはJVM用の新しいJITコンパイラで,Java 9以降のバージョンで利用できるようになりました。JavaのJITコンパイラは,コンパイラが生成したJavaバイトコードを読み込んで機械語を生成します。現在のJVMは,このJITコンパイラのエンジン部分のみを差し替えて実行できる仕組みを備えています。GraalVMは,このJITコンパイラ部分にGraalを採用することで高速化を実現しています。

Truffleは,自前のプログラミング言語を実装するためのフレームワークで,任意の言語インタプリタを比較的容易に実装することができます。Truffleはプログラムのソースコードを解析してAST(抽象構文木)を生成するためのAPIを提供しています。GraalはTruffleの生成するASTを解釈し,極めて高いパフォーマンスで実行することができるため,GraalVMはこの2つを組み合わせて高性能な多言語環境を実現しています。ただし,JVM言語に関してはもともとGraalで実行できるため,TruffleはJavaScriptやRubyなどJVM言語以外の言語のために使われています。

GraalVMの10の使い方

では,実際にGraalVMはどのような使い方ができるのでしょうか。OracleでGraalVMの開発を担当しているChris Seaton氏は,GraalVMについて以下に挙げる10の使い方を提案しています。

ハイパフォーマンスなJava実行環境として使う

GraalVMに搭載されているGraalは,モダンな実装を取り入れた,AOT(Ahead-Of-Time)としてもJITとしても動作するコンパイラです。既存のコンパイラよりも高速に動作するケースも多いため,コンパイラエンジンを既存のものからGraalに置き換えるだけで,アプリケーションの実行パフォーマンスが上がる可能性があります。

低フットプリント・高速スタートアップのJava実行ファイルを作る

GraalVMには,Javaプログラムをコンパイルしてネイティブの実行ファイルを生成するツールが付属しています。バイトコードではな実行ファイルなので,可搬性という利点は失われますが,通常のJavaバイトコードをJVMに読み込ませて実行するよりもフットプリントが小さく,起動が高速なネイティブプログラムを作ることができます。

マルチ言語の実行環境として利用する

前述のように,GraalVMはJavaScriptやRuby,R,Pythonなどといった複数のプログラミング言語をサポートしています。単一の言語のプログラムを実行できるだけでなく,複数の言語を組み合わせて相互にAPIを呼び出すこともできるようになっています。これによって,各言語の得意分野を活かしたアプリケーション開発が可能になります。

ネイティブアプリケーションをJVM上で実行する

GraalVMでは,C言語で作られたプログラムも実行することもできます。原理的には,GraalVMはLLVMによって生成されたビットコードを実行することができるため,C言語以外にも,C++などのLLVMがサポートする他の言語にも対応できます。C言語で書かれた既存のプログラムもLLVMでコンパイルし直せば実行できるので,すでにあるさまざまな資産を容易にGraalVMに移行して再利用できるというメリットがあります。

さまざまな言語対応のデバッグ/プロファイルツールとして使う

GraalVMにはChrome拡張として作られたデバッガが付属しています。また,JVM用のプロファイラであるVisualVMも付属しています。これを使うことで,メモリの使用状況などといったJVM内の状態を調べることができます。これらのツールはGraalVM上で実行されるすべてのプログラムに対応しているため,JVM言語をはじめとして,JavaScriptやPythonといったGraalVMが対応するあらゆる言語の共通的な開発ツールとして利用できます。

JVM言語を多言語拡張する

GraalVMでは,JavaをはじめとするJVMベースの言語から,他の言語のコードを読み込んで実行するためのAPIが提供されています。これを使うことで,Javaプログラム内からJavaScriptを実行するなどといった,クロス言語な実装が可能になります。

ネイティブアプリケーションを多言語拡張する

GraalVMでは,ネイティブアプリケーションからGraalVM用のプログラムを呼び出すライブラリも用意されています。すなわち,この多言語ライブラリを通して,C言語のプログラムからGraalVMが対応するさまざまな言語を呼び出すことができるということです。この多言語ライブラリはデフォルトではJavaScript用にビルドされていますが,再ビルドすることで他の言語にも対応します。

Javaコードをネイティブライブラリとして使う

GraalVMでは,Javaのコードをスタンドアロンのネイティブライブラリにコンパイルすることもできます。通常,ネイティブアプリケーションでJavaのコードを実行するにはJVMを組み込む必要がありますが,GraalVMでネイティブライブラリに変換してしまえば,JVM無しでJavaで書かれた資産を利用することが可能です。

データベース内で任意の組込みプログラムを実行する

Oracleが提供するOracle Database 12cには,実験的にOracle Database Multilingual Engine(MLE)と呼ばれる機能が用意されています。これはデータベース内で任意のプログラムを実行できるようにする拡張機能です。MLEは,GraalVMを組込むことで,任意の言語のプログラムをサポートできるようになっています。この機能によって,たとえばJavaScriptをSQLクエリに組み込んで実行するといったようなことが可能になります。

Oracle DatabaseのほかにMySQLでも同様の拡張機能が利用できます。現段階ではJavaScriptのみサポートしていますが,将来的には他の言語にも対応する予定とのことです。

独自のプログラミング言語を作成する

Truffleを使えば,自前のプログラミング言語のためのインタプリタを比較的容易に作成することができます。Truffleで実装された言語はGraalVMの高性能なエンジンで実行することが可能です。TruffleのインタプリタはJavaで実装できるので,Javaプログラマにとっての親和性は極めて高いというメリットもあります。もちろん,ここまで説明してきたGraalVMの使い方は,Truffle製の独自言語にも通用します。

著者プロフィール

杉山貴章(すぎやまたかあき)

ONGS Inc.所属のプログラマ兼テクニカルライター。雑誌,書籍,Webメディアで多数の著作をもつ。

著書

コメント

コメントの記入