ささださんのるびまの連載を見るに、YARVは評価器だけ置き換えたっていう理解でOKね。
というわけで、るびまの連載が命令セットを解説してたりするのは無視して、RHG片手に学んだRuby内部の知識とJVMで学んだstack式VM一般の知識で読めるところまで読む。
どうでもいいけど、『創るJava』ってJVMを作ってみる本に見えません? 一瞬そう思ったのは私だけ? そういう内容なら買うのになぁ。JVM作れって言われたら仮想マシン仕様片手に作るだけだけど、私の知識じゃ絶対速度は出ないもんね。
話がそれた。
ソースコード(rev.481)を読んでみると
- main : main.c
- ruby_init : eval.c
- Init_yarv : yarvcore.c
- rb_call_inits : inits.c
- ruby_prog_init : ruby.c
- ruby_options : eval.c
- ruby_process_options : ruby.c
- ruby_run : eval.c
- ruby_exec : eval.c
- ruby_init : eval.c
でruby_execの中は
- ruby_exec_internal : eval.c
- yarvcore_eval_parsed : yarvcore.c
- th_compile_from_node : yarvcore.c
- yarvcore_eval_iseq : yarvcore.c
- yarvcore_eval_parsed : yarvcore.c
うーみゅ。流れはRHGの記述とそれほど違わない。Init_yarvはあとで読む。メインの構文木をコンパイルしているらしきth_compile_from_node以下を見る。
- th_compile_from_node : yarvcore.c
- yarv_new_iseqval : yarvcore.c
で、
VALUE
yarv_new_iseqval(VALUE node, VALUE name, VALUE file,
VALUE parent, VALUE type, VALUE opt)
{
VALUE argv[6];
argv[0] = node;
argv[1] = name;
argv[2] = file;
argv[3] = parent;
argv[4] = type;
argv[5] = opt;
return rb_class_new_instance(6, argv, cYarvISeq);
}
ISeq = Instruction Sequenceでおk? 型がVALUEだから最初は何かと思ったけど、rb_class_new_instanceで作ってるからには命令列はRubyオブジェクトとして表現されているらしい。
かつて拡張ライブラリだったという出自から察するに、cYarvISeqを構築したりするのはInit_yarvの中か……。と思ったらInit_yarvcoreのほうだった。Init_yarvcoreはrb_call_initsの中で呼ばれてる。組み込みライブラリっていう位置づけな訳ね。
void Init_yarvcore(void)
あるある。疑似Rubyコードでいうと、
module YarvCore # = mYarvCore
InsnNameArray = [ .... ]
def self.eval .... end
def self.parse .... end
def self.eval_iseq .... end
class InstructionSequence # = cYarvISeq
end
class VM # = cYarvVM
class Env # = cYarvEnv
end
class Thread # = cYarvVM
end
::Thread = Thread
class Proc # = rb_cProc = cYarvProc
end
Object::Proc = Proc
class Binding # = cYarvBinding
end
Object::Binding = Binding
end
end
おぉ。盛大に置き換えてる。
- rb_define_global_constとrb_const_setが混ざってるのは何故?
- rb_cThreadやrb_cBindingには代入しないのは何故?
(たぶん)続く
コメント