From: "tagomoris (Satoshi TAGOMORI)" Date: 2021-12-04T06:49:16+00:00 Subject: [ruby-core:106478] [Ruby master Feature#14835] Support TracePoint#raised_exception on non-:raise events Issue #14835 has been updated by tagomoris (Satoshi TAGOMORI). We cannot know how "return" events are triggered. It can be triggered by usual returns (return values), and also be triggered by raised exceptions (does not return values). This also makes it impossible to know where the raised exception was rescued. If the "return" event contains exceptions (as `raised_exception`) when it is triggered by raised events, we can distinguish "return" events, by usual returns, or by raised exceptions. That is my request. Currently, calling `raised_exception` method on "return" event causes the exception below: ``` :338:in `raised_exception': not supported by this event (RuntimeError) from /Users/tagomoris/hoge.rb:20:in `block in
' from /Users/tagomoris/hoge.rb:9:in `caller_with_rescue' from /Users/tagomoris/hoge.rb:26:in `
' ``` ---------------------------------------- Feature #14835: Support TracePoint#raised_exception on non-:raise events https://bugs.ruby-lang.org/issues/14835#change-95135 * Author: tagomoris (Satoshi TAGOMORI) * Status: Feedback * Priority: Normal ---------------------------------------- TracePoint supports :raise and :return events, and :return event will be invoked when an exception occurs in a method. But its TracePoint block parameter instance doesn't have any information about raised exceptions. That means, we can know an exception was raised in a method, but we cannot know an exception was rescued or not there. ```ruby def thrower raise "exception" end def caller_without_rescue thrower end tp = TracePoint.trace(:raise, :return) do |tp| case tp.event when :raise p(here: "trace", event: :raise, klass: tp.defined_class, method: tp.method_id, exception: tp.raised_exception) else p(here: "trace", event: tp.event, klass: tp.defined_class, method: tp.method_id, value: tp.return_value) end end caller_with_rescue puts "\n----------------------\n" begin caller_without_rescue rescue => e2 puts "outer rescue: #{e2}" end ``` The script above shows these events, but TracePoint events are completely same in these two examples. ``` # caller_with_rescue {:here=>"trace", :event=>:raise, :klass=>Object, :method=>:thrower, :exception=>#} {:here=>"trace", :event=>:return, :klass=>Object, :method=>:thrower, :value=>nil} rescue: exception {:here=>"trace", :event=>:return, :klass=>Object, :method=>:caller_with_rescue, :value=>nil} ---------------------- # caller_without_rescue {:here=>"trace", :event=>:raise, :klass=>Object, :method=>:thrower, :exception=>#} {:here=>"trace", :event=>:return, :klass=>Object, :method=>:thrower, :value=>nil} {:here=>"trace", :event=>:return, :klass=>Object, :method=>:caller_without_rescue, :value=>nil} outer rescue: exception ``` My expectation is that TracePoint instance should contain exception instance in `raised_exception` at the time when it's not rescued. -- https://bugs.ruby-lang.org/ Unsubscribe: