module Trepan

Attributes

annotate[RW]

gdb-style annotation mode. Used in GNU Emacs interface

cmd_port[R]
control_thread[R]
ctrl_port[R]
handler[RW]
start_sentinal[RW]

If start_sentinal is set, it is a string to look for in caller() and is used to see if the call stack is truncated. Is also defined in app/default.rb

thread[R]
wait_connection[RW]

in remote mode, wait for the remote connection

Public Class Methods

add_command_file(cmdfile, opts={}, stderr=$stderr) click to toggle source
# File lib/trepanning.rb, line 223
def add_command_file(cmdfile, opts={}, stderr=$stderr)
  unless File.readable?(cmdfile)
    if File.exists?(cmdfile)
      stderr.puts "Command file '#{cmdfile}' is not readable."
      return
    else
      stderr.puts "Command file '#{cmdfile}' does not exist."
      return
    end
  end
  @@intf << Trepan::ScriptInterface.new(cmdfile, @output, opts)
end
add_startup_files() click to toggle source
# File lib/trepanning.rb, line 236
def add_startup_files()
  seen = {}
  cwd_initfile = File.join('.', Trepan::CMD_INITFILE_BASE)
  [cwd_initfile, Trepan::CMD_INITFILE].each do |initfile|
    full_initfile_path = File.expand_path(initfile)
    next if seen[full_initfile_path]
    add_command_file(full_initfile_path) if
      File.readable?(full_initfile_path)
    seen[full_initfile_path] = true
  end
end
completion_method(last_token, leading=nil) click to toggle source
FIXME: see if we can put this in app/complete.

The method is called when we want to do debugger command completion such as called from GNU Readline with <TAB>.

# File lib/trepanning.rb, line 21
def self.completion_method(last_token, leading=nil)
  if leading.nil?
      if Readline.respond_to?(:line_buffer)
        completion =
          Trepan.handler.cmdproc.complete(Readline.line_buffer,
                                            last_token)
      else
        completion = Trepan.handler.cmdproc.complete(last_token, '')
      end
  else
    completion = Trepan.handler.cmdproc.complete(leading, last_token)
  end
  if 1 == completion.size
    completion_token = completion[0]
    if last_token.end_with?(' ')
      if last_token.rstrip == completion_token
        # There is nothing more to complete
        []
      else
        []
      end
    else
      [completion_token]
    end
  else
    # We have multiple completions. Get the last token so that will
    # be presented as a list of completions.
    completion
  end
end
process_cmdfile_setting(settings) click to toggle source
# File lib/trepanning.rb, line 248
def process_cmdfile_setting(settings)
  p settings
  puts caller
  exit
  settings[:cmdfiles].each do |item|
    cmdfile, opts =
      if item.kind_of?(Array)
        item
      else
        [item, {}]
      end
    add_command_file(cmdfile, opts)
  end if settings.member?(:cmdfiles)
end
start(options={}, &block) click to toggle source

Trepan.start(options) -> bool Trepan.start(options) { … } -> obj

If it’s called without a block it returns true, unless debugger was already started. If a block is given, it starts debugger and yields to block. When the block is finished executing it stops the debugger with Trepan.stop method.

If a block is given, it starts debugger and yields to block. When the block is finished executing it stops the debugger with Trepan.stop method. Inside the block you will probably want to have a call to Trepan.debugger. For example:

Trepan.start{debugger; foo}  # Stop inside of foo

Also, ruby-debug only allows one invocation of debugger at a time; nested Trepan.start‘s have no effect and you can’t use this inside the debugger itself.

Note that if you want to stop debugger, you must call Trepan.stop as many time as you called Trepan.start method.

options is a hash used to set various debugging options. Set :init true if you want to save ARGV and some variables which make a debugger restart possible. Only the first time :init is set true will values get set. Since ARGV is saved, you should make sure it hasn’t been changed before the (first) call. Set :post_mortem true if you want to enter post-mortem debugging on an uncaught exception. Once post-mortem debugging is set, it can’t be unset.

# File lib/trepanning.rb, line 114
def start(options={}, &block)
  options = Trepan::DEFAULT_START_SETTINGS.merge(options)
  if options[:init]
    Trepan.const_set('ARGV', ARGV.clone) unless
      defined? Trepan::ARGV
    Trepan.const_set('PROG_SCRIPT', $0) unless
      defined? Trepan::PROG_SCRIPT
    Trepan.const_set('INITIAL_DIR', Dir.pwd) unless
      defined? Trepan::INITIAL_DIR
  end
  Trepan.tracing = options[:tracing] unless options[:tracing].nil?
  retval = Debugger.started? ? block && block.call(self) : Debugger.start_(&block)
  if options[:post_mortem]
    post_mortem
  end
  return retval
end
start_client(host = 'localhost', port = PORT) click to toggle source

Connects to the remote debugger

# File lib/trepanning.rb, line 198
def start_client(host = 'localhost', port = PORT)
  require "socket"
  interface = Trepan::LocalInterface.new
  socket = TCPSocket.new(host, port)
  puts "Connected."

  catch(:exit) do
    while (line = socket.gets)
      case line
      when /^PROMPT (.*)$/
        input = interface.read_command($1)
        throw :exit unless input
        socket.puts input
      when /^CONFIRM (.*)$/
        input = interface.confirm($1)
        throw :exit unless input
        socket.puts input
      else
        print line
      end
    end
  end
  socket.close
end
start_remote(host = nil, port = PORT, post_mortem = false) { || ... } click to toggle source

Starts a remote debugger.

# File lib/trepanning.rb, line 139
def start_remote(host = nil, port = PORT, post_mortem = false)
  return if @thread
  return if started?

  self.interface = nil
  start
  self.post_mortem if post_mortem

  if port.kind_of?(Array)
    cmd_port, ctrl_port = port
  else
    cmd_port, ctrl_port = port, port + 1
  end

  ctrl_port = start_control(host, ctrl_port)

  yield if block_given?

  mutex = Mutex.new
  proceed = ConditionVariable.new

  server = TCPServer.new(host, cmd_port)
  @cmd_port = cmd_port = server.addr[1]
  @thread = Debugger::DebugThread.new do
    while (session = server.accept)
      self.interface = RemoteInterface.new(session)
      if wait_connection
        mutex.synchronize do
          proceed.signal
        end
      end
    end
  end
  if wait_connection
    mutex.synchronize do
      proceed.wait(mutex)
    end
  end
end
Also aliased as: start_server
start_server(host = nil, port = PORT, post_mortem = false)
Alias for: start_remote
started?() click to toggle source
# File lib/trepanning.rb, line 132
def started?
  Debugger.started?
end