42. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
最適化レベル
42
0 インタプリタ実行
1 C1 (プロファイリングなし)
2
C1 (ベーシックカウンタのみ
プロファイリング)
3 C1 (完全なプロファイリング)
4 C2
43. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
43
JITコンパイル
実行対象を
出力する
44. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
-XX:+PrintCompilation
44
32 5 3 java.lang.String::coder (15 bytes)
...
150 235 4 java.lang.String::coder (15 bytes)
151 5 3 java.lang.String::coder (15 bytes) made not entrant
経過時間
コンパイルID
最適化レベル 破棄した
コンパイルした
メソッドのバイト数
45. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
$ javap -c --module java.base java.lang.String
...
byte coder();
Code:
0: getstatic #9 // Field COMPACT_STRINGS:Z
3: ifeq 13
6: aload_0
7: getfield #4 // Field coder:B
10: goto 14
13: iconst_1
14: ireturn
メソッドのバイト数
45
0始まりで15バイト
46. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
46
メソッドの行数を
少なくする、
という意味は…
47. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイラが
生成コードを
見たい!
47
48. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
HSDIS
48
• HotSpot Disassembler
• JIT生成コードをアセンブリにする
• -XX:+UnlockDiagnosticVMOptions -XX:+PrintAssembly
もつける
49. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
49
JITコンパイラが
生成したコードを
アセンブラコードに
して見る
50. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
参考: HSDISの入手
50
1. OpenJDKのソースを取得する
2. hotspot/src/share/tools/hsdis ディレクトリへ
3. binutilsをここにダウンロードする
4. ビルドする
• make BINUTILS=binutils-X.XX ARCH=amd64
5. macOSの場合、hsdis-amd64.dylibをJDKに配
置する
• $JAVA_HOME/lib/server
• $JAVA_HOME/jre/lib (JDK 8まで)
https://www.sakatakoichi.com/entry/2016/06/01/180742
51. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
これで見るのは、
けっこう辛い…
51
52. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITWatch
52
• JITコンパイルログの解析ツール
• https://github.com/AdoptOpenJDK/jitwatch
53. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
53
JITWatch
54. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
では、
どのように
Javaバイトコードを
機械語にするのか?
54
55. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイルのプロセス
55
Java
バイトコード
IR (中間表現) 機械語
最適化を適用し、
IRを変更する
① ③
②
56. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
IR
56
• コードをデータ構造で表現する
• JVMでは、グラフで表現する
• プログラムの依存をグラフにする
• IRグラフ
57. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
例: x + y をグラフにする
58. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
例: getX() + getY() をグラフにする
59. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
例: メソッドの呼び出し順序を考慮
黄色が実行順序、緑色がデータフロー
60. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイルでの
最適化とは、
このグラフに対する
パターンマッチとなる
60
61. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
ものすごくラフな例
61
Aノード Bノード
Cノード
Dノード Dノード
Eノード
最適化パターンにマッチ!
62. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JVMのIRグラフを
見てみよう
(ただし、C2ではなく
GraalVM JITコンパイラ)
62
63. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
63
IdealGraph
Visualizer
64. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
IdealGraphVisualizer
64
• IRグラフ可視化ツール
• ただし、GraalVM JITコンパイラ用
• -Dgraal.Dump=:1 オプションをつけて実行する
• https://www.graalvm.org/docs/reference-manual/tools/#ideal-graph-visualizer
65. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
参考: C2とGraalVM JITコンパイラ
65
• C2
• OpenJDKのデフォルト
• C++で書かれている
• GraalVM JITコンパイラ
• GraalVMのデフォルト
• Javaで書かれている
• OpenJDKにも入っている (10以降)
• JEP 317: Experimental Java-Based JIT Compiler
66. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイラのアーキテクチャ
66
フロントエンド バックエンド
67. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
フロントエンド
67
• ハードウェアからは独立
• バイトコードからIRを生成する
• IRに最適化をほどこす
• IRは、HIRと呼ぶ
• High-Level IR: 高水準中間表現
68. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
バックエンド
68
• ハードウェアに依存
• レジスタを割り当てる
• LIRから機械語を生成する
• Low-Level IR: 低水準中間言語
69. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイラのアーキテクチャ
69
クラス
ロード
バイト
コード HIR
HIR LIR
LIR
機械語
コード
フロントエンド バックエンド
HIR生成
最適化 レジスタ割当
コード生成
70. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
org.graalvm.compiler.core.GraalCompiler
70
public static <T extends CompilationResult> T
compile(Request<T> r) {
...
emitFrontEnd(r.providers, r.backend, r.graph,
r.graphBuilderSuite, r.optimisticOpts,
r.profilingInfo, r.suites);
r.backend.emitBackEnd(r.graph, null,
r.installedCodeOwner, r.compilationResult,
r.factory, null, r.lirSuites);
...
}
71. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
最適化
71
• メソッドのインライン化
• ループアンロール
• デッドコード削除
• ロック粗粒化 / ロック省略
• エスケープ解析 (厳密には最適化ではない)
• など多数
72. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
デモ
72
JITWatchで
最適化を見る
73. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
ホットパスでのコンパイル
73
ノード ノード
ノード
ノード
プロファイル結果から、
左ルートを前提とした
コードを生成する
74. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
実行が右ルートに行く場合は?
74
ノード ノード
ノード
ノード
生成したコードにある
トラップに入る
75. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
脱最適化: Deoptimization
75
• JITコンパイラが立てた前提から
外れた実行となった場合
• if – else ifでまれな経路に入る
• クラスロードでインタフェースの実装クラス
が増える
• 機械語の実行から
インタプリタでの実行に戻る
76. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
JITコンパイルのライフサイクル
76
インタプリタ
コードキャッシュ
C1
C2
脱最適化
77. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
コードキャッシュ
77
• 機械語コードは、
CodeCache (C++オブジェクト)内に
配置する
• -XX:ReservedCodeCacheSize で指定
• デフォルトサイズは、240MB
78. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
Java HotSpot(TM) 64-Bit Server VM warning: CodeCache is
full. Compiler has been disabled.
Java HotSpot(TM) 64-Bit Server VM warning: Try increasing
the code cache size using -XX:ReservedCodeCacheSize=
CodeCache: size=2496Kb used=1980Kb max_used=1983Kb
free=515Kb
bounds [0x0000000103db8000, 0x0000000104028000,
0x0000000104028000]
total_blobs=1104 nmethods=623 adapters=288
compilation: disabled (not enough contiguous free space
left)
コードキャッシュあふれ
78
79. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
アプリケーションの
パフォーマンスが
低下する
79
80. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
今回扱っていない話題
80
• コンパイルキュー
• OSR: On Stack Replacement
• 最適化手法の詳細
• SSA: Static Single Assignment
• レジスタ割付のアルゴリズム
• Linear Scan Register Allocation
81. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
まとめ
81
• JITコンパイラ
• バイトコードを機械語に変換する
• HotSpot VMのJITコンパイラ
• C1とC2でTiered Compilation
• HSDISとJITWatch
• JIT生成コードを実際に見る
82. Copyright (C) 2019 Yahoo Japan Corporation. All Rights Reserved.
参考文献
82
• Java Magazine
• https://www.oracle.com/webfolder/technetwork/jp/javamagazine/Java-MA15-Architect-
newland.pdf
• https://www.oracle.com/webfolder/technetwork/jp/javamagazine/Java-JA14-Architect-
Evans.pdf
• Java Just-In-Timeコンパイラ
• https://www.slideshare.net/ishizaki/ppl-summer-school2004ishizaki-29661211