Skip to content

Undefined method '+' for nil #1134

Description

@paul

Your environment

  • ruby -v: ruby 3.4.1 (2024-12-25 revision 48d4efcb85) +PRISM [x86_64-linux]
  • rdbg -v: rdbg 1.10.0

Describe the bug

I'm trying to debug a separate issue, where it seems the WebConsole thread is hanging instead of reporting an error. When I connect to the puma server with rdbg -A, do th to list the threads, then th 13 (or whatever to pick the stuck thread), then do bt, I get a big exception printed to the puma output:

[
  "DEBUGGER Exception: /home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/debug-1.10.0/lib/debug/thread_client.rb:1252", 
  #<NoMethodError: undefined method '+' for nil>, 
  [
    "/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/debug-1.10.0/lib/debug/thread_client.rb:85:in 'DEBUGGER__::ThreadClient#default_frame_formatter'", 
    "/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/debug-1.10.0/lib/debug/thread_client.rb:755:in 'Method#call'", 
    "/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/debug-1.10.0/lib/debug/thread_client.rb:755:in 'DEBUGGER__::ThreadClient#frame_str'", 
    "/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/debug-1.10.0/lib/debug/thread_client.rb:742:in 'block in DEBUGGER__::ThreadClient#show_frames'", 
    "<internal:numeric>:257:in 'Integer#times'",
    # ...

(formatted for readability, such as it is)

Also, when this happens, the console input for rdbg doesn't return. I have to hit ^C, and it prints "Stop by SIGURG", and I'm able to input commands again.

To Reproduce

  1. Have a stuck thread using 100% CPU (I'm not sure that that's a requirement, its what I'm investigating).
  2. Connect rdbg to the process, and switch to the stuck thread.
  3. Print the backtrace for that thread.

Expected behavior

Successfully print the backtrace for a frame with nil for block_loc, or determine why a frame would have that.

Additional context

It looks like its coming from thread_client.rb:85, so I printed out the values for level, block_loc, args and frame:

{
  :level     => "",
  :block_loc => nil,
  :args      => [],
  :frame     => #<Object:ActionDispatch::ServerTiming:0x00045ba0
    attr_reader :callee = nil,
    attr_reader :local_variables = nil,
    binding = #<Binding:0x00007f67cf5e0e78>,
    class = ActionDispatch::ServerTiming < Object,
    dupped_binding = nil,
    frame_depth = 17,
    has_raised_exception = nil,
    has_return_value = nil,
    iseq = <RubyVM::InstructionSequence:block in call@/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/actionpack-7.1.5.1/lib/action_dispatch/middleware/server_timing.rb:58>,
    location = "/home/rando/.local/share/mise/installs/ruby/3.4.1/lib/ruby/gems/3.4.0/gems/actionpack-7.1.5.1/lib/action_dispatch/middleware/server_timing.rb:24:in 'ActionDispatch::ServerTiming::Subscriber#collect_events'",
    raised_exception = nil,
    return_value = nil,
    self = #<ActionDispatch::ServerTiming:0x00007f67e8e5f1f8 ...wall of text, looks like a middleware stack...>,
    show_line = nil
  >
}

I'm able to get it to not blow up by changing the code like this:

-          "#{colorize_blue("block")}#{args_str} in #{colorize_blue(block_loc + level)}"
+          "#{colorize_blue('block')}#{args_str} in #{colorize_blue([block_loc, level].compact.join)}"

But, I'm not sure why block_loc is nil (and level is empty string), and if that indicates a larger problem.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions