Project

General

Profile

Bug #1525

Deadlock in Ruby 1.9's VM caused by ConditionVariable.wait and fork?

Added by hongli (Hongli Lai) about 11 years ago. Updated about 9 years ago.

Status:
Closed
Priority:
Normal
Target version:
ruby -v:
ruby 1.9.1p129 (2009-05-12 revision 23412) [i386-darwin9.6.0]
Backport:
[ruby-core:23572]

Description

=begin
The following code seems to cause a VM-wide deadlock on 1.9:

require 'thread'

lock = Mutex.new
cond = ConditionVariable.new
t = Thread.new do
lock.synchronize do
cond.wait(lock)
end
end

pid = fork do
# Child
STDOUT.write "This is the child process.\n"
STDOUT.write "Child process exiting.\n"
end
STDOUT.write("Child PID = #{pid}\n")
Process.waitpid(pid)

The expected output is:

Child PID = xxxx
This is the child process.
Child process exiting.

After the exit message, Ruby should exit.

Instead, Ruby 1.9 gives:

Child PID = 15493
This is the child process.
(process hangs here)

Ruby 1.8 does not suffer from this problem.

Upon debugging Ruby, I've found that Ruby is stuck in blocking_region_end(), at the following line:

native_mutex_lock(&th->vm->global_vm_lock);

blocking_region_end() was called as part of rb_write_internal(), right after writing "This is the child process\n" to stdout. This problem only occurs if there's a background thread that's waiting on a ConditionVariable. If you remove the thread then the deadlock does not occur.
=end


Files

vm_deadlock_fix.diff (466 Bytes) vm_deadlock_fix.diff hongli (Hongli Lai), 11/17/2009 09:58 PM

Related issues

Related to Ruby master - Bug #2025: problem with pthread handling on non NPTL platformClosedmame (Yusuke Endoh)08/31/2009Actions

Also available in: Atom PDF