diff options
Diffstat (limited to 'spec/ruby/core/mutex')
| -rw-r--r-- | spec/ruby/core/mutex/lock_spec.rb | 70 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/locked_spec.rb | 8 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/owned_spec.rb | 22 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/sleep_spec.rb | 20 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/synchronize_spec.rb | 8 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/try_lock_spec.rb | 8 | ||||
| -rw-r--r-- | spec/ruby/core/mutex/unlock_spec.rb | 6 |
7 files changed, 99 insertions, 43 deletions
diff --git a/spec/ruby/core/mutex/lock_spec.rb b/spec/ruby/core/mutex/lock_spec.rb index 7a39817b11..4fee29091a 100644 --- a/spec/ruby/core/mutex/lock_spec.rb +++ b/spec/ruby/core/mutex/lock_spec.rb @@ -1,10 +1,6 @@ require_relative '../../spec_helper' describe "Mutex#lock" do - before :each do - ScratchPad.clear - end - it "returns self" do m = Mutex.new m.lock.should == m @@ -24,11 +20,73 @@ describe "Mutex#lock" do # Unable to find a specific ticket but behavior change may be # related to this ML thread. - it "raises a ThreadError when used recursively" do + it "raises a deadlock ThreadError when used recursively" do m = Mutex.new m.lock -> { m.lock - }.should raise_error(ThreadError) + }.should.raise(ThreadError, /deadlock/) + end + + it "raises a deadlock ThreadError when multiple fibers from the same thread try to lock" do + m = Mutex.new + + m.lock + f0 = Fiber.new do + m.lock + end + -> { f0.resume }.should.raise(ThreadError, /deadlock/) + + m.unlock + f1 = Fiber.new do + m.lock + Fiber.yield + end + f2 = Fiber.new do + m.lock + end + f1.resume + -> { f2.resume }.should.raise(ThreadError, /deadlock/) + end + + it "does not raise deadlock if a fiber's attempt to lock was interrupted" do + lock = Mutex.new + main = Thread.current + + t2 = nil + t1 = Thread.new do + loop do + # interrupt fiber below looping on synchronize + sleep 0.01 + t2.raise if t2 + end + end + + # loop ten times to try to handle the interrupt during synchronize + t2 = Thread.new do + 10.times do + Fiber.new do + begin + loop { lock.synchronize {} } + rescue RuntimeError + end + end.resume + + Fiber.new do + -> do + lock.synchronize {} + end.should_not.raise(ThreadError) + end.resume + rescue RuntimeError + retry + end + end + t2.join + ensure + t1.kill rescue nil + t2.kill rescue nil + + t1.join + t2.join end end diff --git a/spec/ruby/core/mutex/locked_spec.rb b/spec/ruby/core/mutex/locked_spec.rb index 1bf3ed6394..1818cdb4f3 100644 --- a/spec/ruby/core/mutex/locked_spec.rb +++ b/spec/ruby/core/mutex/locked_spec.rb @@ -4,12 +4,12 @@ describe "Mutex#locked?" do it "returns true if locked" do m = Mutex.new m.lock - m.locked?.should be_true + m.locked?.should == true end it "returns false if unlocked" do m = Mutex.new - m.locked?.should be_false + m.locked?.should == false end it "returns the status of the lock" do @@ -27,10 +27,10 @@ describe "Mutex#locked?" do Thread.pass until m1_locked - m1.locked?.should be_true + m1.locked?.should == true m2.unlock # release th th.join # A Thread releases its locks upon termination - m1.locked?.should be_false + m1.locked?.should == false end end diff --git a/spec/ruby/core/mutex/owned_spec.rb b/spec/ruby/core/mutex/owned_spec.rb index 1f843cd576..ea7d5faf1c 100644 --- a/spec/ruby/core/mutex/owned_spec.rb +++ b/spec/ruby/core/mutex/owned_spec.rb @@ -4,7 +4,7 @@ describe "Mutex#owned?" do describe "when unlocked" do it "returns false" do m = Mutex.new - m.owned?.should be_false + m.owned?.should == false end end @@ -12,7 +12,7 @@ describe "Mutex#owned?" do it "returns true" do m = Mutex.new m.lock - m.owned?.should be_true + m.owned?.should == true end end @@ -37,19 +37,17 @@ describe "Mutex#owned?" do end Thread.pass until locked - m.owned?.should be_false + m.owned?.should == false end end - ruby_version_is "3.0" do - it "is held per Fiber" do - m = Mutex.new - m.lock + it "is held per Fiber" do + m = Mutex.new + m.lock - Fiber.new do - m.locked?.should == true - m.owned?.should == false - end.resume - end + Fiber.new do + m.locked?.should == true + m.owned?.should == false + end.resume end end diff --git a/spec/ruby/core/mutex/sleep_spec.rb b/spec/ruby/core/mutex/sleep_spec.rb index 9832e3125e..a78e4c4b62 100644 --- a/spec/ruby/core/mutex/sleep_spec.rb +++ b/spec/ruby/core/mutex/sleep_spec.rb @@ -4,21 +4,21 @@ describe "Mutex#sleep" do describe "when not locked by the current thread" do it "raises a ThreadError" do m = Mutex.new - -> { m.sleep }.should raise_error(ThreadError) + -> { m.sleep }.should.raise(ThreadError) end it "raises an ArgumentError if passed a negative duration" do m = Mutex.new - -> { m.sleep(-0.1) }.should raise_error(ArgumentError) - -> { m.sleep(-1) }.should raise_error(ArgumentError) + -> { m.sleep(-0.1) }.should.raise(ArgumentError) + -> { m.sleep(-1) }.should.raise(ArgumentError) end end it "raises an ArgumentError if passed a negative duration" do m = Mutex.new m.lock - -> { m.sleep(-0.1) }.should raise_error(ArgumentError) - -> { m.sleep(-1) }.should raise_error(ArgumentError) + -> { m.sleep(-0.1) }.should.raise(ArgumentError) + -> { m.sleep(-1) }.should.raise(ArgumentError) end it "pauses execution for approximately the duration requested" do @@ -38,7 +38,7 @@ describe "Mutex#sleep" do th = Thread.new { m.lock; locked = true; m.sleep } Thread.pass until locked Thread.pass until th.stop? - m.locked?.should be_false + m.locked?.should == false th.run th.join end @@ -47,7 +47,7 @@ describe "Mutex#sleep" do m = Mutex.new m.lock m.sleep(0.001) - m.locked?.should be_true + m.locked?.should == true end it "relocks the mutex when woken by an exception being raised" do @@ -65,7 +65,7 @@ describe "Mutex#sleep" do Thread.pass until locked Thread.pass until th.stop? th.raise(Exception) - th.value.should be_true + th.value.should == true end it "returns the rounded number of seconds asleep" do @@ -79,7 +79,7 @@ describe "Mutex#sleep" do Thread.pass until locked Thread.pass until th.stop? th.wakeup - th.value.should be_kind_of(Integer) + th.value.should.is_a?(Integer) end it "wakes up when requesting sleep times near or equal to zero" do @@ -97,7 +97,7 @@ describe "Mutex#sleep" do m.lock times.each do |time| # just testing that sleep completes - -> {m.sleep(time)}.should_not raise_error + -> {m.sleep(time)}.should_not.raise end end end diff --git a/spec/ruby/core/mutex/synchronize_spec.rb b/spec/ruby/core/mutex/synchronize_spec.rb index 7942885197..823f29a634 100644 --- a/spec/ruby/core/mutex/synchronize_spec.rb +++ b/spec/ruby/core/mutex/synchronize_spec.rb @@ -14,15 +14,15 @@ describe "Mutex#synchronize" do m2.lock raise Exception end - end.should raise_error(Exception) + end.should.raise(Exception) end Thread.pass until synchronized - m1.locked?.should be_true + m1.locked?.should == true m2.unlock th.join - m1.locked?.should be_false + m1.locked?.should == false end it "blocks the caller if already locked" do @@ -60,7 +60,7 @@ describe "Mutex#synchronize" do m = Mutex.new m.synchronize do - -> { m.synchronize { } }.should raise_error(ThreadError) + -> { m.synchronize { } }.should.raise(ThreadError) end end end diff --git a/spec/ruby/core/mutex/try_lock_spec.rb b/spec/ruby/core/mutex/try_lock_spec.rb index 8d521f4c6b..1da0735d6a 100644 --- a/spec/ruby/core/mutex/try_lock_spec.rb +++ b/spec/ruby/core/mutex/try_lock_spec.rb @@ -4,13 +4,13 @@ describe "Mutex#try_lock" do describe "when unlocked" do it "returns true" do m = Mutex.new - m.try_lock.should be_true + m.try_lock.should == true end it "locks the mutex" do m = Mutex.new m.try_lock - m.locked?.should be_true + m.locked?.should == true end end @@ -18,7 +18,7 @@ describe "Mutex#try_lock" do it "returns false" do m = Mutex.new m.lock - m.try_lock.should be_false + m.try_lock.should == false end end @@ -26,7 +26,7 @@ describe "Mutex#try_lock" do it "returns false" do m = Mutex.new m.lock - Thread.new { m.try_lock }.value.should be_false + Thread.new { m.try_lock }.value.should == false end end end diff --git a/spec/ruby/core/mutex/unlock_spec.rb b/spec/ruby/core/mutex/unlock_spec.rb index d999e66842..ed493cf84a 100644 --- a/spec/ruby/core/mutex/unlock_spec.rb +++ b/spec/ruby/core/mutex/unlock_spec.rb @@ -3,7 +3,7 @@ require_relative '../../spec_helper' describe "Mutex#unlock" do it "raises ThreadError unless Mutex is locked" do mutex = Mutex.new - -> { mutex.unlock }.should raise_error(ThreadError) + -> { mutex.unlock }.should.raise(ThreadError) end it "raises ThreadError unless thread owns Mutex" do @@ -19,7 +19,7 @@ describe "Mutex#unlock" do Thread.pass until mutex.locked? Thread.pass until th.stop? - -> { mutex.unlock }.should raise_error(ThreadError) + -> { mutex.unlock }.should.raise(ThreadError) wait.unlock th.join @@ -33,6 +33,6 @@ describe "Mutex#unlock" do th.join - -> { mutex.unlock }.should raise_error(ThreadError) + -> { mutex.unlock }.should.raise(ThreadError) end end |
