diff options
author | Matthew Draper <matthew@trebex.net> | 2016-02-07 08:24:57 +1030 |
---|---|---|
committer | Matthew Draper <matthew@trebex.net> | 2016-02-07 08:32:27 +1030 |
commit | 3e4a69e52d8c8f0335e0ddbb46fe21009b962334 (patch) | |
tree | 172481e3ea5e3ed7496ff2541a595343fbd49ae8 /activesupport/test/share_lock_test.rb | |
parent | 8526e9bed21a119266e886c3316d3fe10c9af5ce (diff) | |
download | rails-3e4a69e52d8c8f0335e0ddbb46fe21009b962334.tar.gz rails-3e4a69e52d8c8f0335e0ddbb46fe21009b962334.tar.bz2 rails-3e4a69e52d8c8f0335e0ddbb46fe21009b962334.zip |
Hand off the interlock to the new thread in AC::Live
Most importantly, the original request thread must yield its share lock
while waiting for the live thread to commit -- otherwise a request's
base and live threads can deadlock against each other.
Diffstat (limited to 'activesupport/test/share_lock_test.rb')
-rw-r--r-- | activesupport/test/share_lock_test.rb | 26 |
1 files changed, 26 insertions, 0 deletions
diff --git a/activesupport/test/share_lock_test.rb b/activesupport/test/share_lock_test.rb index 12953d99a6..68fa5bb69e 100644 --- a/activesupport/test/share_lock_test.rb +++ b/activesupport/test/share_lock_test.rb @@ -287,6 +287,32 @@ class ShareLockTest < ActiveSupport::TestCase assert_threads_not_stuck threads end + def test_manual_yield + ready = Concurrent::CyclicBarrier.new(2) + done = Concurrent::CyclicBarrier.new(2) + + threads = [ + Thread.new do + @lock.sharing do + ready.wait + @lock.exclusive(purpose: :x) {} + done.wait + end + end, + + Thread.new do + @lock.sharing do + ready.wait + @lock.yield_shares(compatible: [:x]) do + done.wait + end + end + end, + ] + + assert_threads_not_stuck threads + end + def test_in_shared_section_incompatible_non_upgrading_threads_cannot_preempt_upgrading_threads scratch_pad = [] scratch_pad_mutex = Mutex.new |