More Related Content
PDF
PDF
OpenJDK HotSpot C1Compiler Overview PDF
PDF
PDF
Javaはどのように動くのか~スライドでわかるJVMの仕組み PDF
Introduction to JShell: the Java REPL Tool #jjug_ccc #ccc_ab4 PDF
PPTX
What's hot
KEY
PDF
PPTX
Elixir入門「第6回:Elixirはtry…catchを書かない~障害対応のパラダイムシフト~」 PDF
PDF
第三回ありえる社内勉強会 「いわががのLombok」 PDF
PPTX
Jvm reading-synchronization PDF
Frege, What a Non-strict Language PDF
PPT
PPTX
そうだったのか! よくわかる process.nextTick() node.jsのイベントループを理解する PDF
PDF
InvokeDynamic at #shikadriven 2012 PDF
PDF
PDF
DoActionからJava VMバイトコードに変換する話 PDF
なぜリアクティブは重要か #ScalaMatsuri PDF
PDF
思ったほど怖くない! Haskell on JVM 超入門 #jjug_ccc #ccc_l8 PDF
Similar to Java 7 invokedynamic の概要
PDF
Kink: invokedynamic on a prototype-based language PDF
PPTX
jvmlang.daitokai 1.0.0 MinCamlJを作ってみた PDF
Adaptive optimization of JIT compiler PDF
Java SE 7 InvokeDynamic in JRuby PDF
静かに変わってきたクラスファイルを詳細に調べて楽しむ(JJUG CCC 2024 Fall講演資料) PDF
Javaセキュアコーディングセミナー東京第1回 講義 PDF
バイトコードって言葉をよく目にするけど一体何なんだろう?(JJUG CCC 2022 Spring 発表資料) PDF
Indy(Invokedynamic) and Bytecode DSL and Brainf*ck PDF
Var handles jjug_ccc_spring_2018 PDF
20171212 titech lecture_ishizaki_public PDF
PDF
PDF
Lambda: A Peek Under The Hood [Java Day Tokyo 2015 6-3] KEY
関ジャバ JavaOne Tokyo 2012報告会 PDF
gen-class とバイトコード(第3回 gen-class 勉強会資料) PDF
PDF
Programming24 第2回androidアプリ勉強会 PDF
PPTX
JEP280: Java 9 で文字列結合の処理が変わるぞ!準備はいいか!? #jjug_ccc More from Taku Miyakawa
PDF
Java SE 9の紹介: モジュール・システムを中心に PDF
PDF
Matrix Multiplication in Strassen Algorithm PDF
PDF
PDF
PDF
PDF
金勘定のためのBigDecimalそしてMoney and Currency API PDF
Quasar: Actor Model and Light Weight Threads on Java PDF
PDF
PDF
Summary of "Hacking", 0x351-0x354 PDF
Processing LTSV by Apache Pig PDF
Kink: プロトタイプベースの俺々 JVM 言語 PDF
PDF
PDF
Kink: developing a programming language on the JVM Java 7 invokedynamic の概要
- 1.
- 2.
1
発表者
• 名前: 宮川拓
• 職業: SI 屋で Hadooper
• オレオレ JVM 言語 Kink を開発中
– Its’ fun!
- 3.
2
invokedynamic とは?
• Java6 までの JVM
= Java のための仮想マシン
• Java 7 の JVM
= Java + Java 以外の言語のための仮想マシン
• invokedynamic は Java 以外の言語のために
追加された新しいメソッド呼び出し命令
- 4.
3
論点
• Java 6までの呼び出し命令
– JVM 命令は Java のために作られていた
• Java 以外の言語
– 既存の命令セットでは Java 以外の言語処理系が
効率的に実装できない
• invokedynamic
– 新しい命令で Java 以外の言語も効率的になる
- 5.
- 6.
5
Java 6 までの呼び出し命令
•4 種類
• Java のメソッド呼び出しはこれで全部 OK
invokestatic static メソッドを呼び出す
invokespecial コンストラクタ、 private メソッド等を呼び出す
invokevirtual クラスに属するメソッドを呼び出す (非 private)
invokeinterface インタフェースに属するメソッドを呼び出す
- 7.
6
invokestatic
• static メソッドの呼び出し→ invokestatic
StringUtils.rjust("VOXXX", 10, '.');
javac
ldc "VOXXX" // "VOXXX” をスタックに積む
bipush 10 // 10 をスタックに積む
bipush 46 // '.' = 46 をスタックに積む
invokestatic StringUtils#rjust(String,int,char):String
- 8.
- 9.
- 10.
- 11.
10
invokevirtual
• とある GUIツールキットのクラス階層
Widget
Rect getRect()
Button
void push()
CheckBox OKButton
void push() void push()
boolean isPushed()
- 12.
- 13.
- 14.
13
invokeinterface
• 再び GUIツールキットのクラス階層
intf Movable intf Resizable
void move(Point) void resize(Size)
class Icon class Frame
void move(Point) void resize(Size)
void move(Point)
- 15.
- 16.
- 17.
16
Java 6 までの呼び出し命令(rep)
• 4 つの呼び出し命令で Java のメソッド呼び出
しをカバー
• Java に特化した仕組み
– メソッドが再定義されることはない
– 単一継承
– 名前と型の組み合わせによるメソッドの特定
– レシーバのクラスによる単一ディスパッチ
- 18.
- 19.
18
古い革袋と新しい酒
Scheme
JS Python
Groovy Ruby
Scala
Java Java
JVM JVM
むかし 最近
- 20.
19
古い革袋と新しい酒
• JVM はJava のために作られたので、それ以外
の言語を動かすのには工夫が必要
• 例: Ruby ではメソッドが再定義できるので、既
存の呼び出し命令で直接呼び出せない
• 他にも
– method-missing
– 多重継承
– mix-in
- 21.
- 22.
21
本当はこうしたい!
array.join
バイトコード
生成
CAFE 0000 bang! def join
3939 5151 ...
...... ...
余計な処理がなく、JIT コンパイラに
よる最適化が掛けやすくなる
- 23.
- 24.
- 25.
- 26.
- 27.
- 28.
- 29.
28
MethodHandle
• MethodHandle は型付き関数ポインタ
•決まった型・数の引数をスタックから取り、結
果をスタックに置く処理を指し示す
プリミティブな MethodHandle の作成
Lookup#findVirtual • インスタンスメソッドを呼び出す
MH
Lookup#findConstructor • インスタンスを生成する MH
Lookup#findGetter • フィールドの値を返す MH
MethodHandles#constant • 定数値を返す MH
- 30.
29
MethodHandle
• MethodHandle は合成したり、引数の順序を
入れ替えたり、部分適用したりして新しい
MethodHandle を生成できる
複合的な MethodHandle の作成
MethodHandles • (if test then target else fallback) を行う
#guardWithTest MH
MethodHandles • 本処理の戻り値に後処理を加える MH
#filterReturnValue
MethodHandle • 先頭の引数の値を固定した MH
#bindTo
- 31.
30
CallSite
• ついで CallSite
初回実行時に invokedynamic
呼び出し
bootstrap <<create>>
CallSite
メソッド
任意の MH の Method bang! 対象の
処理 再登録 Handle 処理
- 32.
31
CallSite
• 1 つのinvokedynamic 命令に紐付いて「呼び
出し元」を表す
• MethodHandle の参照を保持する
CallSite の具象クラス
ConstantCallSite • MH が書き換えられない
• private final MethodHandle mh
MutableCallSite • MH が書き換えられる
• private MethodHandle mh
VolatileCallSite • MH が書き換えられる
• private volatile MethodHandle mh
- 33.
32
bootstrap メソッド
• 最後にbootstrap メソッド
初回実行時に invokedynamic
呼び出し
bootstrap <<create>>
CallSite
メソッド
任意の MH の Method bang! 対象の
処理 再登録 Handle 処理
- 34.
33
bootstrap メソッド
• 各invokedynamic 命令は bootstrap という
static メソッドへの参照を持っている
• invokedynamic 命令が最初に実行される時に
bootstrap メソッドが呼ばれて
– 命令に CallSite オブジェクトを紐付ける
– MethodHandle の初期値を CallSite に紐付ける
- 35.
34
bootstrap メソッド
• 例:戻り値の型が int の場合、強制的に値を
42 にする
static CallSite bsm(Lookup lu, String name, MethodType mt)
throws Exception {
MethodType vmt = mt.dropParameterTypes(0, 1);
MethodHandle vmh = lu.findVirtual(mt.parameterType(0), name, vmt);
if (vmt.returnType() == int.class)
return new ConstantCallSite(filterReturnValue(vmh,
dropArguments(constant(int.class, 42), 0, int.class)));
else
return new ConstantCallSite(vmh);
}
- 36.
35
bootstrap メソッド
• 例:「メソッド名」を文字列として戻す
– indy での「メソッド名」は bootstrap に渡す引数に
過ぎない
static CallSite bsm(Lookup lu, String name, MethodType mt) {
return new ConstantCallSite(dropArguments(
constant(String.class, name), 0, mt.parameterType(0)));
}
MethodType が引数なし
戻り値 String でないとエラー
- 37.
36
invokedynamic (rep)
• bootstrapメソッドにより、命令に紐付く処理を
言語処理系独自のやり方で選択できる
• CallSite に新しい MethodHandle を登録するこ
とにより、命令に紐付く処理を実行時に変更
できる
• これらの仕組みを JVM のレベルでサポートす
るため、賢く使うと効率的な言語処理系が実
装できる
- 38.
- 39.
38
参考
• Da VinciMachine Project (mlvm)
– http://openjdk.java.net/projects/mlvm/
• JSR 292 Cookbook
– http://cr.openjdk.java.net/~jrose/pres/200906-Cookbook.htm
• John Rose’ weblog at Oracle: dynamic invocation in the VM
– https://blogs.oracle.com/jrose/entry/dynamic_invocation_in_the_vm
• Optimizing invokedynamic
– http://dl.acm.org/citation.cfm?id=1852763
• HotSpot Internals for OpenJDK: CallingSequences
– https://wikis.oracle.com/display/HotSpotInternals/CallingSequences