ここんとこ、YARV の make test-all だか make yarv-test-all だかが止まらなくなってる。 かたまってるんじゃなくて、無限ループ。ps ax で見るとこんな感じ。
1119 ? R 1716:44 runner.rb test_exit_action(TestSignal)
しかも端末から実行するとちゃんと終わるのが解せない。 スレッド作りまくりなのが問題なのかと思って コメントアウトしてみたけど変化なし。 うーん?
つか、だいたい、test_exit_action は assert false なのに、 なんでここで止まるんだろう。
(14:23)
なーんかわかってきた。テストが終わらないんじゃなくて、 テストプログラムから fork したプロセスがずっと動いてるんだ。
class TestSignal < Test::Unit::TestCase def have_fork? begin Process.fork {} return true rescue NotImplementedError return false end end
このあたりに罠が潜んでるような気がする。
もしかして、fork したプロセスにも at_exit が登録されているから無限再帰になる? いやでも、ずっと動かしといてもプロセス ID は変化していないな。 ということは、無限に fork が呼ばれているわけではないはずだ。
うーん、だいたい YARV では test_exit_action は 無条件に assert(false) してるのに、なんで動くんだ。 assert の位置を変えてみよう。
tukumo:/var/www/autobuild-yarv/obj % make test-all aamine@tukumo ./miniruby /var/www/autobuild-yarv/src/runruby.rb --extout=.ext -- -C "/var/www/autobuild-yarv/src/test" runner.rb --runner=console "./ruby -C /var/www/autobuild-yarv/src/test runner.rb --runner=console" Loaded suite . Started ................................................................................ 中略 0000 (0x2aaaaf11f010): 00000004 0001 (0x2aaaaf11f018): 00000001 0002 (0x2aaaaf11f020): 2aaab17904d8 0003 (0x2aaaaf11f028): 0242b659 0004 (0x2aaaaf11f030): 2aaaab3ea550 0005 (0x2aaaaf11f038): 00000004 0006 (0x2aaaaf11f040): 00000001 0007 (0x2aaaaf11f048): 00000004 0008 (0x2aaaaf11f050): 00000001 <- lfp <- dfp -- control frame ---------- c:0005 p:---- s:0009 b:0009 l:000008 d:000008 CFUNC :(null) c:0004 p:---- s:0007 b:0007 l:000006 d:000006 CFUNC :now c:0003 p:0013 s:0004 b:0004 l:0x1958 d:000003 PROC /var/www/autobuild-ya:125 c:0002 p:---- s:0002 b:0002 l:000001 d:000001 FINISH c:0001 p:---- s:0000 b:-001 l:000000 d:000000 ------ --------------------------- DBG> : "/var/www/autobuild-yarv/src/lib/webrick/utils.rb:125:in `now'" DBG> : "/var/www/autobuild-yarv/src/lib/webrick/utils.rb:125:in `block in initialize'" [BUG] Segmentation fault ruby 1.9.0 (2006-11-06) [x86_64-linux]
おい!
(21:09)
とりあえずスタックトレース
#0 0x00002aaaab0c4dd0 in raise () from /lib/libc.so.6 #1 0x00002aaaab0c6280 in abort () from /lib/libc.so.6 #2 0x00000000004a7897 in rb_bug (fmt=0x4d4a89 "Segmentation fault") at /var/www/autobuild-yarv/src/error.c:172 #3 0x000000000046de99 in sigsegv (sig=16613) at /var/www/autobuild-yarv/src/signal.c:471 #4 <signal handler called> #5 mark_source_filename (f=0xe8106 <Address 0xe8106 out of bounds>) at /var/www/autobuild-yarv/src/gc.c:633 #6 0x000000000041b4b5 in gc_mark_children (ptr=55787088, lev=1) at /var/www/autobuild-yarv/src/gc.c:838 #7 0x000000000041ba5e in mark_entry (key=950534, value=950534, lev=1) at /var/www/autobuild-yarv/src/gc.c:732 #8 0x00000000004720c2 in st_foreach (table=0x228e340, func=0x41ba50 <mark_entry>, arg=2) at /var/www/autobuild-yarv/src/st.c:460 #9 0x000000000041b71f in gc_mark_children (ptr=46912545231680, lev=2) at /var/www/autobuild-yarv/src/gc.c:977 #10 0x000000000041b76d in gc_mark_children (ptr=46912533961640, lev=1) at /var/www/autobuild-yarv/src/gc.c:864 #11 0x0000000000488bcc in iseq_mark (ptr=0x13b92d0) at /var/www/autobuild-yarv/src/iseq.c:74 #12 0x000000000041b4f3 in gc_mark_children (ptr=1, lev=1) at /var/www/autobuild-yarv/src/gc.c:991 #13 0x0000000000488bf5 in iseq_mark (ptr=0x13a8d20) at /var/www/autobuild-yarv/src/iseq.c:71 #14 0x000000000041b4f3 in gc_mark_children (ptr=1, lev=1) at /var/www/autobuild-yarv/src/gc.c:991 #15 0x0000000000488bf5 in iseq_mark (ptr=0x12183a0) at /var/www/autobuild-yarv/src/iseq.c:71 #16 0x000000000041ba5e in mark_entry (key=950534, value=950534, lev=1) at /var/www/autobuild-yarv/src/gc.c:732 #17 0x00000000004720c2 in st_foreach (table=0x182b0b0, func=0x41ba50 <mark_entry>, arg=3) at /var/www/autobuild-yarv/src/st.c:460 #18 0x000000000041b71f in gc_mark_children (ptr=46912533953480, lev=3) at /var/www/autobuild-yarv/src/gc.c:977 #19 0x000000000041ba5e in mark_entry (key=950534, value=950534, lev=1) at /var/www/autobuild-yarv/src/gc.c:732 #20 0x00000000004720c2 in st_foreach (table=0x62eb00, func=0x41ba50 <mark_entry>, arg=2) at /var/www/autobuild-yarv/src/st.c:460 #21 0x000000000041b72b in gc_mark_children (ptr=46912506128840, lev=2) at /var/www/autobuild-yarv/src/gc.c:978 #22 0x000000000041b76d in gc_mark_children (ptr=46912552532720, lev=1) at /var/www/autobuild-yarv/src/gc.c:864 #23 0x0000000000488bcc in iseq_mark (ptr=0x226dec0) at /var/www/autobuild-yarv/src/iseq.c:74 #24 0x000000000041b4f3 in gc_mark_children (ptr=1, lev=1) at /var/www/autobuild-yarv/src/gc.c:991 #25 0x0000000000488bf5 in iseq_mark (ptr=0x1de72c0) at /var/www/autobuild-yarv/src/iseq.c:71 #26 0x000000000041ba5e in mark_entry (key=950534, value=950534, lev=1) at /var/www/autobuild-yarv/src/gc.c:732 #27 0x00000000004720c2 in st_foreach (table=0x637ee0, func=0x41ba50 <mark_entry>, arg=3) at /var/www/autobuild-yarv/src/st.c:460 #28 0x000000000041b71f in gc_mark_children (ptr=46912506071960, lev=3) at /var/www/autobuild-yarv/src/gc.c:977 以下略
struct RClass * 46912545231680 の m_tbl の中身 (NODE) のうちどれかの nd_file が壊れてるもよう。
m_tbl の中身は一個だけ (46912545227000) であった。
(gdb) p $4->bins[10]->record $19 = 46912545227000 (gdb) p (struct RNode*)$19 $20 = (struct RNode *) 0x2aaaad9800f8 (gdb) p *$20 $21 = {flags = 33087, nd_file = 0xa66e31 "(eval)", u1 = {node = 0x0, id = 0, value = 0, cfunc = 0, tbl = 0x0}, u2 = {node = 0x2aaaad980148, id = 46912545227080, argc = 46912545227080, value = 46912545227080}, u3 = { node = 0x0, id = 0, state = 0, entry = 0x0, cnt = 0, value = 0}}
壊れてない。 えーと、flags=33087 は NODE_FBODY で、u2.value = nd_body か。 NODE_FBODY の nd_body って何が入ってるんだっけ。NODE_METHOD?
(gdb) p $26->u2.value $28 = 46912545227080 (gdb) p (struct RNode*)$28 $29 = (struct RNode *) 0x2aaaad980148 (gdb) p *$29 $30 = {flags = 32831, nd_file = 0xa66e31 "(eval)", u1 = { node = 0x2aaaad981340, id = 46912545231680, value = 46912545231680, cfunc = 0x2aaaad981340, tbl = 0x2aaaad981340}, u2 = { node = 0x2aaaad980170, id = 46912545227120, argc = 46912545227120, value = 46912545227120}, u3 = {node = 0x0, id = 0, state = 0, entry = 0x0, cnt = 0, value = 0}}
flags=32831 は T_NODE の NODE_METHOD。
NODE_METHOD.nd_clss は struct RClass *。 NODE_METHOD.nd_body は NODE_BMETHOD。
なぬー。もうこの先は NODE ないじゃん。どこで落ちてんだよ。
(23:25)
Copyright (c) 2002-2007 青木峰郎 / Minero Aoki. All rights reserved.
なおしたつもり。
よくこれだけでわかるなあ……。さすがだ。