Feature #15289
Updated by nobu (Nobuyoshi Nakada) over 5 years ago
# Abstract To enable TracePoint for specific location, I propose new keyword argument `target:` to `TracePoint#enable` for specific events (`line`, `call`, `return`, `class`, `end`). Usage: ```ruby ``` line_trace = TracePoint.new(:line){|tp| p tp } def foo p 1 end line_trace.enable(target: method(:foo)) do foo end ``` In this case, a line trace is enable only on the method `foo`. `target:` keyword accepts `Method`, `UnboundMethod`, `Proc` and `RubyVM::InstructionSequence` (ISeq for short) . All of objects can pull ISeq objects. Further more, I propose `target_lines:` keyword too, which specify effective line(s). These features can improve "break point" feature and so on. # Background If we want to insert break point in Ruby's source code, we can use `TracePoint` (line event, for example). However, it enables all locations. It hurt performance. This proposal overcomes this performance penalty. # Implementation Now basic design are completed in my mind :p # Discussion ## line or lines For breakpoint purpose, we only need to specify a line. Specifying lines is needed? ## no events on lines It is not clear that if line is specified (for example: 10) and there are no line event (for example, empty line). Possible options: * (1) raise an exception * (2) adjust before/after effective event * (3) ignore I prefer (1). ## no events in Proc Similar to last topic, if we specify `call` event on `Proc` object, there are no `call` event. What happens? ## recursive or not If method `foo` refers other blocks, I think we need to enable recursively. ## how to get File target? Sometimes we want to specify breakponit to the location specified by "file:line". How to get the lines? https://github.com/ko1/iseq_collector provides the feature to collect all of ISeqs. debugger can collects all of them and debugger can filter with path name. Also [Feature #15287] will help to hook not loaded locations. ## `enable` w/ keywords or other method name? I have no strong opinion, but `TracePoint#enable_on(target, lines: ...)` is another idea? # reference Related: https://github.com/ruby/ruby/pull/2000 This implementation is based on `trace_` insn.