From: eregontp@... Date: 2019-08-26T22:22:33+00:00 Subject: [ruby-core:94591] [Ruby master Bug#15992] An exception breaks monitor state and cause deadlock Issue #15992 has been updated by Eregon (Benoit Daloze). Should `mon_enter` and `mon_exit` use `Thread.handle_interrupt` inside their method definitions, so they are safe when called directly too? `Thread.handle_interrupt(Exception => :never)` seems too much for `mon_enter`, I think `Thread.handle_interrupt(Exception => :blocking)` would be better. Otherwise, it's not possible to interrupt a thread trying to get a contended monitor with `Thread#raise`: ``` ruby -rmonitor -e 'o=Object.new.extend(MonitorMixin); Thread.new{ o.mon_enter; sleep }; sleep 0.1; Thread.new{sleep 3; p :kill; Thread.main.raise "bye"}; p o.synchronize { p :in; sleep }' ``` Never exits on trunk, but it does exit on 2.6.2 and before. Even Thread#kill does not help. Ctrl+C does interrupt it, because signal traps are not yet supported by `handle_interrupt`, but that might change. ---------------------------------------- Bug #15992: An exception breaks monitor state and cause deadlock https://bugs.ruby-lang.org/issues/15992#change-81063 * Author: naruse (Yui NARUSE) * Status: Closed * Priority: Normal * Assignee: * Target version: * ruby -v: * Backport: 2.5: DONE, 2.6: DONE ---------------------------------------- lib/monitor.rb provides Monitor. But its state handling is weak for interrupts caused by Thread.kill for example timeout libraries. Timeout exception may happen everywhere. If it raised when the thread is executing ```ruby def mon_exit mon_check_owner @mon_count -=1 if @mon_count == 0 @mon_owner = nil # HERE!!! @mon_mutex.unlock end end ``` It breaks the state of the monitor and it causes deadlock. -- https://bugs.ruby-lang.org/ Unsubscribe: