--Boundary-00dC+FPIX+H7bikJ
Content-Type: text/plain;
  charsettf-8"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline

On Wednesday 14 March 2007 17:29, MenTaLguY wrote:
> On Thu, 15 Mar 2007 01:19:04 +0900, Sylvain Joyeux <sylvain.joyeux / m4x.org> 
wrote:
> > Yup. Here is the right one.
>
> Hmm, why not just add a "prev" variable?
Because I'm too sleepy to think "good code" ?
Your version is better, while I think the 'ref' trick is clever but difficult 
to grasp at first read.

Here's the fix for ConditionVariable#wait. The problem occurs when the two 
thread that are trying to access the condition variable are also in 
concurrence for the mutex (see below)

I removed the test for mutex being NULL, and I think this one *cannot* be 
argued about since it makes #wait do nothing (no synchronization AT ALL)

Note that it is not possible to use #lock_mutex since it modifies 
rb_thread_critical

Testcase:

def test_conditionvariable_wait
  mutex  utex.new
  resource  onditionVariable.new
  result  ]
  mutex.synchronize do
      Thread.new do
          mutex.synchronize do
              result << 1
              resource.signal
          end
      end
      resource.wait(mutex)
  end

  assert_equal([0, 1, 2], result)
end


--Boundary-00dC+FPIX+H7bikJ
Content-Type: text/x-diff;
  charsettf-8";
  namehread-condvar_wait.diff"
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment;
	filenamehread-condvar_wait.diff"

--- /home/sjoyeux/system/ruby-1.8.6/ext/thread/thread.c	2007-03-03 11:08:06.000000000 +0100
+++ thread.c	2007-03-14 17:39:31.000000000 +0100
@@ -623,17 +645,12 @@ static void
 wait_condvar(ConditionVariable *condvar, Mutex *mutex)
 {
     rb_thread_critical  ;
-    if (!RTEST(mutex->owner)) {
-        rb_thread_critical  ;
-        return;
-    }
     if (mutex->owner ! b_thread_current()) {
         rb_thread_critical  ;
-        rb_raise(rb_eThreadError, "Not owner");
+        rb_raise(rb_eThreadError, "not owner of the synchronization mutex");
     }
-    mutex->owner  nil;
+    unlock_mutex_inner(mutex);
     wait_list(&condvar->waiting);
-
     lock_mutex(mutex);
 }
 

--Boundary-00dC+FPIX+H7bikJ--