class Byebug::DAP::Server

Byebug DAP Server

Public Class Methods

new(capture: true, forward: true) click to toggle source

Create a new server. @param capture [Boolean] if `true`, the debugee's STDOUT and STDERR will be captured @param forward [Boolean] if `false`, the debugee's STDOUT and STDERR will be supressed

# File lib/byebug/dap/server.rb, line 8
def initialize(capture: true, forward: true)
  @started = false
  @mu = Mutex.new
  @cond = ConditionVariable.new
  @configured = false
  @capture = capture
  @forward = forward
end

Public Instance Methods

start(host, port = 0) click to toggle source

Starts the server. Calls {#start_stdio} if `host == :stdio`. Calls {#start_unix} with `port` if `host == :unix`. Calls {#start_tcp} with `host` and `port` otherwise. @param host `:stdio`, `:unix`, or the TCP host name @param port the Unix socket path or TCP port @return [Server]

# File lib/byebug/dap/server.rb, line 23
def start(host, port = 0)
  case host
  when :stdio
    start_stdio
  when :unix
    start_unix port
  else
    start_tcp host, port
  end
end
start_stdio() click to toggle source

Starts the server using STDIN and STDOUT to communicate. @return [Server]

# File lib/byebug/dap/server.rb, line 59
def start_stdio
  return if @started
  @started = true

  stream = STDIO.new
  STDIN.close
  @ios = CapturedIO.new(false, @forward) if @capture
  launch stream
end
start_tcp(host, port) click to toggle source

Starts the server, listening on a TCP socket. @param host [std:String] the IP to listen on @param port [std:Number] the port to listen on @return [Server]

# File lib/byebug/dap/server.rb, line 38
def start_tcp(host, port)
  return if @started
  @started = true

  @ios = CapturedIO.new(@forward, @forward) if @capture
  launch_accept TCPServer.new(host, port)
end
start_unix(socket) click to toggle source

Starts the server, listening on a Unix socket. @param socket [std:String] the Unix socket path @return [Server]

# File lib/byebug/dap/server.rb, line 49
def start_unix(socket)
  return if @started
  @started = true

  @ios = CapturedIO.new(@forward, @forward) if @capture
  launch_accept UNIXServer.new(socket)
end
wait_for_client() click to toggle source

Blocks until a client connects and begins debugging.

# File lib/byebug/dap/server.rb, line 70
def wait_for_client
  @mu.synchronize do
    loop do
      return if @configured

      @cond.wait(@mu)
    end
  end
end

Private Instance Methods

debug(connection) click to toggle source
# File lib/byebug/dap/server.rb, line 116
def debug(connection)
  session = Byebug::DAP::Session.new(connection, @ios) do
    @mu.synchronize do
      @configured = true
      @cond.broadcast
    end
  end

  session.execute

rescue IOError, Errno::EPIPE, Errno::ECONNRESET, Errno::ECONNABORTED
  log.puts "Client disconnected"

rescue StandardError => e
  log.puts "#{e.message} (#{e.class})", *e.backtrace

ensure
  session.stop!
end
launch(stream) click to toggle source
# File lib/byebug/dap/server.rb, line 92
def launch(stream)
  DebugThread.new do
    debug stream

  ensure
    @ios&.restore
  end

  self
end
launch_accept(server) click to toggle source
# File lib/byebug/dap/server.rb, line 103
def launch_accept(server)
  DebugThread.new do
    while socket = server.accept
      debug socket
    end

  ensure
    @ios&.restore
  end

  self
end
log() click to toggle source
# File lib/byebug/dap/server.rb, line 82
def log
  if @ios
    @ios.log
  elsif defined?(LOG)
    LOG
  else
    STDERR
  end
end