[#20227] dyna_vars problem? — Tanaka Akira <akr@...17n.org>

しばらく前から、稀に Ruby が core を吐くという問題を追いかけているので

15 messages 2003/05/19
[#20234] Re: dyna_vars problem? — matz@... (Yukihiro Matsumoto) 2003/05/19

まつもと ゆきひろです

[#20236] Re: dyna_vars problem? — Tanaka Akira <akr@...17n.org> 2003/05/19

In article <1053363181.529491.30320.nullmailer@picachu.netlab.jp>,

[ruby-dev:20236] Re: dyna_vars problem?

From: Tanaka Akira <akr@...17n.org>
Date: 2003-05-19 17:33:33 UTC
List: ruby-dev #20236
In article <1053363181.529491.30320.nullmailer@picachu.netlab.jp>,
  matz@ruby-lang.org (Yukihiro Matsumoto) writes:

> 正しくないと思います。ここはTHREAD_SAVE_CONTEXTの直前ですか
> ら、currの状態は前回保存した過去の状態です。dyna_varsは途中
> でrb_gc_force_recycle()される可能性がありますから、回収され
> たゴミを指している可能性はあります。
> 
> dyna_varsに関する問題があるにしても、それはここではないので
> はないかと。

なるほど。でもゴミを使っちゃうことがあるんだよなぁ。

うぅむ、しょうがない。より生に近いスクリプトをつけます。
(スクリプト中に含まれる URI に意味はありません。)

たとえば、次のような問題が起きることがあります。
(起きないことも多々ありますし、他の問題が起きることもあります。)

% ./ruby -d tst
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.5...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.2...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.3...done
removing /tmp/open-uri4273.4...done
removing /tmp/open-uri4273.4...done
/home/src/r/0.d/lib/ruby/1.8/tempfile.rb:135: [BUG] Segmentation fault
ruby 1.8.0 (2003-05-20) [i686-linux]

zsh: abort (core dumped)  ./ruby -d tst
% gdb ./ruby core
GNU gdb 5.3-debian
Copyright 2002 Free Software Foundation, Inc.
GDB is free software, covered by the GNU General Public License, and you are
welcome to change it and/or distribute copies of it under certain conditions.
Type "show copying" to see the conditions.
There is absolutely no warranty for GDB.  Type "show warranty" for details.
This GDB was configured as "i386-linux"...
Core was generated by `./ruby -d tst'.
Program terminated with signal 6, Aborted.
Reading symbols from /lib/libdl.so.2...done.
Loaded symbols for /lib/libdl.so.2
Reading symbols from /lib/libcrypt.so.1...done.
Loaded symbols for /lib/libcrypt.so.1
Reading symbols from /lib/libm.so.6...done.
Loaded symbols for /lib/libm.so.6
Reading symbols from /lib/libc.so.6...done.
Loaded symbols for /lib/libc.so.6
Reading symbols from /lib/ld-linux.so.2...done.
Loaded symbols for /lib/ld-linux.so.2
Reading symbols from /home/src/r/0.d/lib/ruby/1.8/i686-linux/stringio.so...
done.
Loaded symbols for /home/src/r/0.d/lib/ruby/1.8/i686-linux/stringio.so
Reading symbols from /home/src/r/0.d/lib/ruby/1.8/i686-linux/socket.so...done.
Loaded symbols for /home/src/r/0.d/lib/ruby/1.8/i686-linux/socket.so
Reading symbols from /home/src/r/0.d/lib/ruby/1.8/i686-linux/fcntl.so...done.
Loaded symbols for /home/src/r/0.d/lib/ruby/1.8/i686-linux/fcntl.so
#0  0x40091a51 in kill () from /lib/libc.so.6
(gdb) where
#0  0x40091a51 in kill () from /lib/libc.so.6
#1  0x40091872 in raise () from /lib/libc.so.6
#2  0x40092986 in abort () from /lib/libc.so.6
#3  0x080c31b8 in rb_bug (fmt=0x80dd08a "Segmentation fault") at error.c:175
#4  0x080a713f in sigsegv (sig=11) at signal.c:412
#5  0x400919d8 in sigaction () from /lib/libc.so.6
#6  0x08093400 in rb_lastline_get () at parse.y:5971
#7  0x08062396 in rb_thread_restore_context (th=0x8161ce0, exit=1)
    at eval.c:8077
#8  0x08062258 in stack_extend (th=0x403c9770, exit=136136232) at eval.c:8027
#9  0x0806ae59 in rb_gc_mark (ptr=1077546292) at gc.c:621
#10 0x0806ae59 in rb_gc_mark (ptr=1077560952) at gc.c:621
#11 0x0806acf1 in mark_keyvalue (key=0, value=1077546292) at gc.c:573
#12 0x080a99a4 in st_foreach (table=0x82367b8, func=0x806acdc <mark_keyvalue>, 
    arg=0) at st.c:495
(gdb) 

% cat tst
#!/usr/bin/env ruby

require 'open-uri'
require 'resolv-replace'

module Enumerable
  def concurrent_map(max_threads=2)
    arr = self.to_a
    queue = (0...arr.length).to_a

    max_threads = arr.length if arr.length < max_threads

    threads = []
    max_threads.times {
      threads << Thread.new {
        while i = queue.shift
          arr[i] = yield arr[i]
        end
      }
    }

    threads.each {|t| t.join }
    arr
  end
end

def main
  status = [
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1036481443/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052273054/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053190979/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053223923/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1017240849/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052625006/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052651750/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051421813/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052931903/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053045530/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1037185937/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1019996589/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1042004759/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1047210828/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053053082/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1043623143/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051882835/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050805231/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053157149/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050926801/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053005739/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050938178/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1040435898/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050590661/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1046179115/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1006617496/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1045399051/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1033830935/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052627913/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/998569580/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050936741/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1049636615/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1033810047/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053349469/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1023727377/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052756106/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1034043673/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1027155489/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1021219939/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051840417/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051842450/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053344366/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1048030962/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052105314/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051099212/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1050468517/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1027964677/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1043629429/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053278662/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1039646808/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053337379/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1052542761/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1049286141/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1014783451/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053172660/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1045542179/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1049790146/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1008775775/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1041306043/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1003674814/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1049857221/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1042463586/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1051066162/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1032402846/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053259677/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1039071400/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1053185745/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/996171508/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1010400855/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1042611308/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1029120920/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1023940311/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1038042372/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1023556171/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1047222540/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1040651917/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1047748598/l50"},
    {"URI"=>"http://pc2.2ch.net/test/read.cgi/tech/1043246252/l50"}
  ]

 status.concurrent_map {|s|
    opts = {"User-Agent"=>"webpecker"}
    page = URI.parse(s['URI']).read(opts)
    /\A(?:\s                               (?# white space character)
            | [\x21-\x7e]                       (?# JIS X 0201 Latin)
            | [\xa1-\xdf]                     (?# JIS X 0201 Katakana)
            | [\x81-\x9f\xe0-\xef][\x40-\x7e\x80-\xfc]      (?# JIS X 0208)
            | [\xf0-\xfc][\x40-\x7e\x80-\xfc] (?# extended area)
            )*\z/nx =~ page
 }

end

main

なお、思考錯誤の末、core を吐く確率をあげるために次のようなパッチを当ててあります。

Index: eval.c
===================================================================
RCS file: /src/ruby/eval.c,v
retrieving revision 1.434
diff -u -r1.434 eval.c
--- eval.c      19 May 2003 15:44:42 -0000      1.434
+++ eval.c      19 May 2003 17:26:53 -0000
@@ -7942,6 +7942,7 @@
     th->stk_pos = (rb_gc_stack_start<pos)?rb_gc_stack_start
                                         :rb_gc_stack_start - len;
     if (len > th->stk_max) {
+        rb_gc();
        REALLOC_N(th->stk_ptr, VALUE, len);
        th->stk_max = len;
     }

なんとなく、thread, GC, finalizer が組合わさった三重苦のような気もしな
いでもないんですが。
-- 
[田中 哲][たなか あきら][Tanaka Akira]

In This Thread