* lib/thread.rb (ConditionVariable): use hash instead of array for
@waiters. * test/thread/test_queue.rb (test_sized_queue_and_wakeup): remove a test because @waiters no longer have a chance to duplicated. Now it's a hash. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@38109 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
f9aef18497
commit
1f1db611b9
@ -1,3 +1,11 @@
|
|||||||
|
Sat Dec 1 14:23:33 2012 KOSAKI Motohiro <kosaki.motohiro@gmail.com>
|
||||||
|
|
||||||
|
* lib/thread.rb (ConditionVariable): use hash instead of array for
|
||||||
|
@waiters.
|
||||||
|
* test/thread/test_queue.rb (test_sized_queue_and_wakeup): remove
|
||||||
|
a test because @waiters no longer have a chance to duplicated. Now it's
|
||||||
|
a hash.
|
||||||
|
|
||||||
Sat Dec 1 17:16:54 2012 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
Sat Dec 1 17:16:54 2012 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
* misc/ruby-electric.el (ruby-electric-curlies): use kill-region
|
* misc/ruby-electric.el (ruby-electric-curlies): use kill-region
|
||||||
|
@ -52,7 +52,7 @@ class ConditionVariable
|
|||||||
# Creates a new ConditionVariable
|
# Creates a new ConditionVariable
|
||||||
#
|
#
|
||||||
def initialize
|
def initialize
|
||||||
@waiters = []
|
@waiters = {}
|
||||||
@waiters_mutex = Mutex.new
|
@waiters_mutex = Mutex.new
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -67,7 +67,7 @@ class ConditionVariable
|
|||||||
begin
|
begin
|
||||||
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
||||||
@waiters_mutex.synchronize do
|
@waiters_mutex.synchronize do
|
||||||
@waiters.push(Thread.current)
|
@waiters[Thread.current] = true
|
||||||
end
|
end
|
||||||
mutex.sleep timeout
|
mutex.sleep timeout
|
||||||
end
|
end
|
||||||
@ -86,10 +86,10 @@ class ConditionVariable
|
|||||||
def signal
|
def signal
|
||||||
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
||||||
begin
|
begin
|
||||||
t = @waiters_mutex.synchronize {@waiters.shift}
|
t, _ = @waiters_mutex.synchronize { @waiters.shift }
|
||||||
t.run if t
|
t.run if t
|
||||||
rescue ThreadError
|
rescue ThreadError
|
||||||
retry # t was alread dead?
|
retry # t was already dead?
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
self
|
self
|
||||||
@ -100,12 +100,12 @@ class ConditionVariable
|
|||||||
#
|
#
|
||||||
def broadcast
|
def broadcast
|
||||||
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
Thread.async_interrupt_timing(StandardError => :on_blocking) do
|
||||||
waiters0 = nil
|
threads = nil
|
||||||
@waiters_mutex.synchronize do
|
@waiters_mutex.synchronize do
|
||||||
waiters0 = @waiters.dup
|
threads = @waiters.keys
|
||||||
@waiters.clear
|
@waiters.clear
|
||||||
end
|
end
|
||||||
for t in waiters0
|
for t in threads
|
||||||
begin
|
begin
|
||||||
t.run
|
t.run
|
||||||
rescue ThreadError
|
rescue ThreadError
|
||||||
|
@ -56,24 +56,6 @@ class TestQueue < Test::Unit::TestCase
|
|||||||
assert_equal(1, q.max)
|
assert_equal(1, q.max)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_sized_queue_and_wakeup
|
|
||||||
sq = SizedQueue.new(1)
|
|
||||||
sq.push(0)
|
|
||||||
|
|
||||||
t1 = Thread.start { sq.push(1) ; sleep }
|
|
||||||
|
|
||||||
sleep 0.1 until t1.stop?
|
|
||||||
t1.wakeup
|
|
||||||
sleep 0.1 until t1.stop?
|
|
||||||
|
|
||||||
t2 = Thread.start { sq.push(2) }
|
|
||||||
sleep 0.1 until t1.stop? && t2.stop?
|
|
||||||
|
|
||||||
enque_cond = sq.instance_eval{ @enque_cond }
|
|
||||||
queue_wait = enque_cond.instance_eval { @waiters }
|
|
||||||
assert_equal(queue_wait.uniq, queue_wait)
|
|
||||||
end
|
|
||||||
|
|
||||||
def test_queue_pop_interrupt
|
def test_queue_pop_interrupt
|
||||||
q = Queue.new
|
q = Queue.new
|
||||||
t1 = Thread.new { q.pop }
|
t1 = Thread.new { q.pop }
|
||||||
|
Loading…
x
Reference in New Issue
Block a user