From: Yusuke ENDOH Date: 2007-12-12T12:00:45+09:00 Subject: [ruby-dev:32547] Re: SEGV by test/ruby/test_fiber.rb 遠藤です。 07/12/11 に SASADA Koichi さんは書きました: >  ささだです. > > Yusuke ENDOH wrote: > > r14156 を見ましたが、cfp->sp を書き換えないのは理由があるのでしょうか。 > >  スタックトップの先に,VALUE 以外の値が入っていないことを保証できな > いためです. うーん、ちょっと意味がわかりませんでした。すみません。 やっぱり気になるので、私の考えていることをもう少し説明します。 私の勘違いだったら無視してもらっても構いません。 例の場所で gc が起きるときのスタックの状況を図示してみます。 まず、vm_invoke_block も vm_setup_method も vm_callee_setup_arg を 呼ぶ前はargv がスタックトップに置かれていると思います。 sp v -+--+--+--+--+--+ ... | argv... | ? ? ? ? -+--+--+--+--+--+ # ささださんが「スタックトップの先に,VALUE 以外の値が入っていない # ことを保証できない」とおっしゃっているのは、? の部分に何が入って # いるかわからないということでしょうか。それは同意します。 vm_invoke_block は DEC_SP(argc) してから vm_yield_setup_args を呼び その中で vm_callee_setup_arg を呼ぶので、例の場所で gc が起きた場合は sp sp+mark_stack_len v v -+--+--+--+--+--+ ... | argv... | ? ? ? ? -+--+--+--+--+--+ という状況になります (簡単のため、iseq->arg_size と argc が等しいと しています) 。 一方 vm_setup_method は、sp をずらさず vm_callee_setup_arg を呼ぶので sp sp+mark_stack_len v v -+--+--+--+--+--+ ... | argv... | ? ? ? ? -+--+--+--+--+--+ という状況で gc が処理されます。田中さんがこの問題を指摘した時点では ? のところまで mark_maybe でなく mark していたため segv していました。 vm_invoke_block と vm_setup_method でこんな風に sp の扱いが異なるのは 意図的なんでしょうか。 私は sp の扱いを共通にすべきと考え、vm_setup_method でも sp をずらす (cfp->sp -= argc;) パッチを書きました。 -- Yusuke ENDOH