[MacRuby] #176: timeout fails to raise a Timeout::Error

MacRuby ruby-noreply at macosforge.org
Sat Aug 21 08:04:28 PDT 2010


#176: timeout fails to raise a Timeout::Error
---------------------------------+------------------------------------------
 Reporter:  acangiano@…          |       Owner:  lsansonetti@…        
     Type:  defect               |      Status:  new                  
 Priority:  major                |   Milestone:                       
Component:  MacRuby              |    Keywords:                       
---------------------------------+------------------------------------------

Comment(by watson1978@…):

 The following patch seems to work well.
 {{{
 #!diff
 diff --git a/lib/timeout.rb b/lib/timeout.rb
 index 297b769..274f843 100644
 --- a/lib/timeout.rb
 +++ b/lib/timeout.rb
 @@ -40,11 +40,14 @@ module Timeout
    # Note that this is both a method of module Timeout, so you can
 'include Timeout'
    # into your classes so they have a #timeout method, as well as a module
 method,
    # so you can call it directly as Timeout.timeout().
 -  def timeout(sec, klass = nil)   #:yield: +sec+
 +  def timeout(sec, klass =  nil, &block)   #:yield: +sec+
      return yield(sec) if sec == nil or sec.zero?
      exception = klass || Class.new(ExitException)
      begin
 -      x = Thread.current
 +      val = nil
 +      x = Thread.start {
 +        val = block.call(sec)
 +      }
        y = Thread.start {
          begin
            sleep sec
 @@ -54,7 +57,8 @@ module Timeout
            x.raise exception, "execution expired" if x.alive?
          end
        }
 -      return yield(sec)
 +      x.join
 +      return val
      rescue exception => e
        rej = /\A#{Regexp.quote(__FILE__)}:#{__LINE__-4}\z/o
        (bt = e.backtrace).reject! {|m| rej =~ m}
 diff --git a/thread.c b/thread.c
 index 6659d06..8a3e715 100644
 --- a/thread.c
 +++ b/thread.c
 @@ -166,6 +166,9 @@ thread_join_m(VALUE self, SEL sel, int argc, VALUE
 *argv)
             ts.tv_sec = 0;
             ts.tv_nsec = 10000000;
             while (t->status != THREAD_DEAD) {
 +               if (t->status == THREAD_KILLED && t->exception != Qnil) {
 +                   break;
 +               }
                 nanosleep(&ts, NULL);
                 pthread_yield_np();
             }
 diff --git a/vm.cpp b/vm.cpp
 index d86cc1c..6f664b3 100644
 --- a/vm.cpp
 +++ b/vm.cpp
 @@ -4654,6 +4654,7 @@ rb_vm_thread_raise(rb_vm_thread_t *t, VALUE exc)
      // XXX we should lock here
      RoxorVM *vm = (RoxorVM *)t->vm;
      vm->push_current_exception(exc);
 +    GC_WB(&t->exception, exc);

      rb_vm_thread_cancel(t);
  }
 }}}

-- 
Ticket URL: <http://www.macruby.org/trac/ticket/176#comment:6>
MacRuby <http://macruby.org/>



More information about the macruby-tickets mailing list