debug_agent)debug_agent is the target-side backend stub for the Fuchsia debugger. It runs on the target Fuchsia system (and experimentally on Linux hosts). It communicates over debug_ipc (../ipc) with the zxdb frontend (../zxdb) on the developer's workstation.
Read the debugger setup and usage guides for user-facing workflows.
Test these four workflows whenever you edit process attachment or component starting:
run-component fuchsia-pkg://fuchsia.com/debug_agent#meta/debug_agent.cm (or another component URL).attach some_filter when a matching process already exists.attach some_filter before a matching process starts.attach 56421 to attach by numeric PID/KOID (debug_agent uses separate code paths for PID and filter attachment).Public headers expose these core classes and helpers:
debug_agent::DebugAgent / debug_agent::DebugAgentOptions: Core backend state machine managing attached jobs, processes, breakpoints, filters, and RemoteAPI dispatch (debug_agent.h).debug_agent::DebugAgentServer: fuchsia.debugger.DebugAgent FIDL server that bridges FIDL requests and FilterIterator attachment into DebugAgent (debug_agent_server.h).debug_agent::DebuggedJob / debug_agent::DebuggedJobCreateInfo: Job exception channel observer that intercepts newly starting processes (debugged_job.h).debug_agent::DebuggedProcess / debug_agent::DebuggedProcessCreateInfo: Per-process state controller managing threads, memory access, module notifications, stdout/stderr capture, and serialized breakpoint step-over queues (debugged_process.h).debug_agent::DebuggedThread: Per-thread execution state, suspension ref-counting (ClientSuspend, InternalSuspend), single-stepping, and register/exception handling (debugged_thread.h).debug_agent::Breakpoint / debug_agent::ProcessBreakpoint: Logical (Breakpoint) and per-process address/range (ProcessBreakpoint) breakpoint abstractions (breakpoint.h, process_breakpoint.h).debug_agent::SoftwareBreakpoint, debug_agent::HardwareBreakpoint, debug_agent::Watchpoint: Concrete ProcessBreakpoint subclasses for instruction-patching traps, CPU debug register breakpoints, and memory read/write watchpoints (software_breakpoint.h, hardware_breakpoint.h, watchpoint.h).debug_agent::RemoteAPI / debug_agent::RemoteAPIAdapter: Abstract RPC handler interface for debug_ipc requests and stream dispatch adapter (remote_api.h, remote_api_adapter.h).debug_agent::SystemInterface / debug_agent::ZirconSystemInterface: Abstract and Zircon-backed representations of the target job tree, component manager, and limbo provider (system_interface.h, zircon_system_interface.h).debug_agent::ComponentManager: Component lifecycle event listener, test runner (fuchsia.test.manager), and component matcher (component_manager.h).debug_agent::LimboProvider: Interface to ProcessLimbo for inspecting, claiming, and releasing crashed processes waiting in limbo (limbo_provider.h).debug_agent::ExceptionHandle: Wrapper around a kernel exception token and its resolution state (exception_handle.h).debug_agent::Filter: Job, process name, and component moniker/URL filter matcher (filter.h).debug_agent::UnwindStack: Stack unwinding wrapper around //src/lib/unwinder (unwind.h).debug_agent::AutomationHandler: Executor for automated memory and register readout instructions attached to breakpoint hits (automation_handler.h).HANDLE_EINTR, IGNORE_EINTR, linux::DirReaderLinux, posix::ShuffleFileDescriptors).Callers and implementations must preserve these invariants:
debug::PlatformMessageLoop (debug::MessageLoopFuchsia on Fuchsia) on the current thread before constructing DebugAgent. The debug::StreamBuffer passed to DebugAgent::Connect or RemoteAPIAdapter must outlive the adapter.DebugAgent::SendNotification requires ipc_version_ > 0 (negotiated via the IPC Hello handshake) before serializing notifications to a stream.Init() and check for an OK debug::Status before using any DebuggedJob or DebuggedProcess instance.DebuggedThread runs only when neither client_suspend_handle_ nor any internal SuspendHandle token exists.DebuggedProcess serializes breakpoint step-overs through step_over_queue_ so only one ProcessBreakpoint steps over at a time. DebuggedProcess ignores duplicate step-over requests for the same thread and breakpoint.SoftwareBreakpoint::StepOverCleanup must run only after the next queued breakpoint's ExecuteStepOver acquires its suspend tokens. It uses a per-thread multimap (suspend_tokens_) to prevent premature thread resumption between consecutive step-overs.LimboProvider lack ZX_RIGHT_DESTROY. When killing a from_limbo process fails with ZX_ERR_ACCESS_DENIED, DebugAgent detaches, records its KOID in killed_limbo_procs_, and calls LimboProvider::ReleaseProcess once it re-enters limbo.ProcessBreakpoint::OnHit does not delete one-shot breakpoints internally. Callers must inspect BreakpointStats::should_delete and delete the breakpoint afterward to avoid self-deletion during hit handling.SystemInterface is non-movable because ComponentManager holds a raw back-pointer to it.kComponentMonikerPrefix filters only for moniker patterns not already present in DebugAgent::filters_.DebuggedJob and AttachConfig distinguish the exclusive "job" exception channel (crash exceptions) from the non-exclusive "job debugger" channel (ZX_EXCP_PROCESS_STARTING). Process attachment uses the process debugger exception channel instead.kMinimal or kNone priority do not claim the debugger exception channel and do not receive upfront ZX_EXCP_PROCESS_STARTING or ZX_EXCP_THREAD_STARTING notifications. Exception handlers in DebuggedJob and DebuggedProcess must lazily create DebuggedProcess and call PopulateCurrentThreads upon receiving an exception.debug_agent produces these target and IPC side effects:
SoftwareBreakpoint) and thread general/debug registers (HardwareBreakpoint, Watchpoint, single-stepping, and unwinding).SuspendHandle tokens, and resolves or forwards kernel exceptions via ExceptionHandle.zxdb clients over debug_ipc streams (BufferedStream / RemoteAPIAdapter) and serves the fuchsia.debugger.DebugAgent FIDL protocol via DebugAgentServer.BinaryLauncher, ComponentManager), watch component lifecycle events, and claim or release crashed processes in ProcessLimbo.DebugAgentObserver without an active debug_ipc client quits the message loop and exits debug_agent.stdout/stderr streams to emit NotifyIO messages to the client, and generates process minidumps on request.Run these commands to build and test debug_agent:
fx build //src/developer/debug/debug_agentfx test debug_agent_unit_tests.cm debug_agent_launcher_unit_tests debug_agent_integration_tests