Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
SlideShare a Scribd company logo
mruby の JIT 解説
三浦英樹
mrubyのJITはtracing JITを採用しています。ざっくり言う
と、命令実行のたびに対応するVMと同等の機械語命令を
命令領域に書きこんでいいき、次にその命令を実行する場
合はその機械語命令を実行するというものです。
OP_LOADSELF R1
OP_LOADI R2, 1
OP_SEND R1, 1
PC
moveEAX, 1
move 8(ECX), EAX
命令を実行しつつ、同等の機械語命令を生成する
/* A sBx R(A) := sBx */
SET_INT_VALUE(regs[GETARG_A(i)], GETARG_sBx(i));
NEXT;
生成コードバッファ
mrubyのJITの概要
mrubyのJITはmrubyにJITコンパイラをいれたものです。
機械語生成にXbyakを使用させてもらっています
>>> Test test <<<
mrbtest - Embeddable Ruby Test
........................................................................................................................................................................
........................................................................................................................................................................
........................................................................................................................................................................
........................................................................................................................................................................
...................................................?...................................................................................................................
.........................................F...................
Skip: Module#prepend super in alias super does not currently work in aliased methods
Fail: multiple assignment (nosplat array rhs) (mrbgems: mruby-test)
- Assertion[1] Failed: Expected "Expected to be equal" to be nil
Expected: nil
Actual: 0
Total: 899
OK: 898
KO: 1
Crash: 0
mrubyのJITはmrubyの5~10倍速い(こと
がある)とかあるけど、一番の売りはこれ
RubyのJITコンパイラなのに脅威の互換性
なぜ脅威なのか?
Rubyは
・ メソッドの再定義が出来る
・ 整数がオーバフローするとBignum
(mrubyはFloat)に勝手に変換される
どちらもせっかく生成したコードが使えなくなる
解決法
自己書き換え
無効になった命令列の先頭にVMに戻る
コードを上書きする
メソッドの再定義
Rubyはメソッドの再定義が可能で、mrubyのmake testは
再定義を多用する
メソッドが再定義されると当然古い定義は無効になるが、
古い定義だけではなく古い定義をcallしている場所も無効
化する必要がある。Inline化している場合もあるし
そこで、古いメソッドの定義の機械語列にはVMに戻るだ
けではなく、呼び出し元のメソッド先頭にVMに戻るコード
をパッチを当てるパッチも当てる (ややこしい)
詳しくは、 
http://qiita.com/miura1729/items/1ab49d34acf3e9e447f8
を見てください
オーバーフロー時の処理
mrubyのJITでは直前の演算結果の型を記録しておいて
型のガードを省略している
ところが、オーバーフローするとFixnumだと思っていたら、
Floatが来るかもしれないからガードが省略できない
そこで、オーバーフローは起きないものとしてコンパイル
し、オーバーフローしたらコードを無効化して、コンパイル
しなおす。irep(mrubyの命令列の構造体)にはオーバフ
ローするかのフラグを増やしている。
問題点
パッチを当てて無効化したコードはなにもせず放置するの
で非常にメモリがもったいない
コードを細分化して管理してGCみたいなものが求められる

More Related Content

Mruby jitプレゼン