From: Oliver Peng Date: 2008-03-04T05:54:10+09:00 Subject: Re: SystemStackError: stack level too deep Robert Klemme wrote: > 2008/3/3, Oliver Peng : >> Robert Klemme wrote: > >> as the sample code in book 'Programming ruby'. > There is no trace of Process.waitall in the signal handler sample code. > >> When a child process dies, a signal, SIGCHLD (or SIGCLD) is sent to its >> parent process. So when I run Process.wait, I always should get the >> response at once. And this code can work. The only problem is sometimes >> SystemStackError was raised. >> >> Can you please use sample code to show me where is the problem? > > The problem is in waitall. The sample code otherwise works ok. Try > this > > trap "CLD" do > puts "#{Process.wait} exited" > # alternative > p Process.wait2 > end > > 5.times do |i| > pid = fork do > puts "proc #{i}" > end and puts "#{pid} created" > end > > puts "all children created" > > sleep 10 > > Here's another approach > > require 'pp' > > 5.times do |i| > pid = fork do > puts "proc #{i}" > end and puts "#{pid} created" > end > > puts "all children created" > > pp Process.waitall > > > Kind regards > > robert Ok. I see. You mean that waitall shouldn't be used in trap 'CLD' because it would wait until all process exit. But I use wait at first and get the SystemStackError exception. Then I try to use waitall later. So I still don't know why the SystemStackError exception is raised. I also try to write test code and please have a look: ---------------------------------------------------- Server code: require 'socket' trap('CLD') do pid = Process.wait puts "pid #{pid} exited" end class TestServer def initialize @tcpServer = TCPServer.new('0.0.0.0', 7777) end def run while tcp = @tcpServer.accept fork do begin while str = tcp.gets() tcp.puts("hello") end ensure tcp.close_read tcp.close_write end end tcp.close end end end server = TestServer.new server.run ------------------------------------------------ Client code: require 'socket' threads = [] 100.times do threads << Thread.new() do while true socket = TCPSocket.new('localhost', 7777) socket.puts("hello") sleep 1 socket.gets socket.close sleep 10 end end end threads.each {|thr| thr.join} From the server output, I can see that CLD signal has been traped and server puts the process exit. But from top I can see that zombie process are getting more and more. Is there some problem in the code logic? Thanks. -- Posted via http://www.ruby-forum.com/.