NationalSecurityAgency/ghidra · error · RuntimeError

No register mapper

Error message

No register mapper

What it means

Thrown by Extra.require_rm() when the register_mapper attribute is None — no architecture-specific register mapper has been configured. Like error 115 but for registers: any command requiring register value translation (read/write registers) will fail until the register mapper is initialized with the correct byte order and register name mappings.

Source

Thrown at Ghidra/Debug/Debugger-agent-dbgeng/src/main/py/src/ghidradbg/commands.py:110

        self.code = code

    def __str__(self) -> str:
        return repr(self.code)


class Extra(object):
    def __init__(self) -> None:
        self.memory_mapper: Optional[arch.DefaultMemoryMapper] = None
        self.register_mapper: Optional[arch.DefaultRegisterMapper] = None

    def require_mm(self) -> arch.DefaultMemoryMapper:
        if self.memory_mapper is None:
            raise RuntimeError("No memory mapper")
        return self.memory_mapper

    def require_rm(self) -> arch.DefaultRegisterMapper:
        if self.register_mapper is None:
            raise RuntimeError("No register mapper")
        return self.register_mapper


class State(object):

    def __init__(self) -> None:
        self.reset_client()

    def require_client(self) -> Client:
        if self.client is None:
            raise RuntimeError("Not connected")
        return self.client

    def require_no_client(self) -> None:
        if self.client != None:
            raise RuntimeError("Already connected")

    def reset_client(self) -> None:

View on GitHub (pinned to d5f144c24d)

Solutions

  1. Connect to the target and run architecture detection before issuing register commands.
  2. Verify that the register mapper initialization code runs after connection establishment.
  3. Check that DefaultRegisterMapper is constructed with a valid byte_order ('big' or 'little') for the target.
  4. Re-run the setup sequence if the session was reset.

Example fix

# Before: issuing register command without mapper
# ghidra_trace_putreg(...)
#
# After: ensure register mapper is initialized
# if STATE.extra.register_mapper is None:
#     arch.compute_ghidra_lcsp()  # triggers arch detection and mapper setup
# ghidra_trace_putreg(...)
Defensive patterns

Strategy: validation

Validate before calling

# Before calling require_rm, check and initialize if needed:
if STATE.extra.register_mapper is None:
    # run architecture detection to set up register mapper
    lang = arch.compute_ghidra_language()
    # mapper is set during arch detection
STATE.extra.require_rm()

Type guard

def has_register_mapper(extra) -> bool:
    return extra.register_mapper is not None

Try / catch

try:
    rm = STATE.extra.require_rm()
except RuntimeError as e:
    if str(e) == 'No register mapper':
        # run setup/arch detection, then retry
        pass
    else:
        raise

Prevention

When it happens

Trigger: STATE.require_rm() (via Extra.require_rm()) is called by register-related commands (e.g., ghidra_trace_putreg, ghidra_trace_getreg), but Extra.register_mapper is still None. Occurs when register commands are issued before architecture detection sets up the mapper.

Common situations: The user issues a register read/write command before the architecture is configured. Architecture detection failed or hasn't run. The debugging session was reset (reset_client/reset_trace) without re-initializing the register mapper.

Related errors


AI-assisted analysis of NationalSecurityAgency/ghidra@d5f144c24d (2026-08-14). Data as JSON: /api/errors/2cd2fbc8179f10b7. Report an issue: GitHub.