class DEBUGGER__::Session

def activate ui = nil, on_fork: false

def activate ui = nil, on_fork: false
  @ui = ui if ui
  @tp_thread_begin&.disable
  @tp_thread_end&.disable
  @tp_thread_begin = nil
  @tp_thread_end = nil
  @ui.activate self, on_fork: on_fork
  q = Queue.new
  first_q = Queue.new
  @session_server = Thread.new do
    # make sure `@session_server` is assigned
    first_q.pop; first_q = nil
    Thread.current.name = 'DEBUGGER__::SESSION@server'
    Thread.current.abort_on_exception = true
    # Thread management
    setup_threads
    thc = get_thread_client Thread.current
    thc.mark_as_management
    if @ui.respond_to?(:reader_thread) && thc = get_thread_client(@ui.reader_thread)
      thc.mark_as_management
    end
    @tp_thread_begin = TracePoint.new(:thread_begin) do |tp|
      get_thread_client
    end
    @tp_thread_begin.enable
    @tp_thread_end = TracePoint.new(:thread_end) do |tp|
      @th_clients.delete(Thread.current)
    end
    @tp_thread_end.enable
    if CONFIG[:irb_console] && !CONFIG[:open]
      require_relative "irb_integration"
      thc.activate_irb_integration
    end
    # session start
    q << true
    session_server_main
  end
  first_q << :ok
  q.pop
end