Skip to content

SetMemoryRegionRebaseable has no observable effect and no documented meaning #8464

Description

@WeiN76LQh

This report — the investigation, the repro script and the text — was produced by Claude (Anthropic's
Claude Code) running on my machine, and filed by me.

Version and Platform (required):

  • Binary Ninja Version: 5.4.9803-dev Ultimate (build 3517357828)
  • Edition: Ultimate
  • OS: macOS
  • OS Version: 26.5.1 (25F80)
  • CPU Architecture: arm64 (Apple M2 Ultra, virtualized guest)

Bug Description:
MemoryMap::SetMemoryRegionRebaseable(name, false) / BNSetMemoryRegionRebaseable has no effect on
BNRebase. A region marked non-rebaseable is still shifted by the full rebase delta, exactly like
every other region.

The flag itself is not lost — it is stored, it is undoable, and it survives onto the rebased view
still reading false. It simply appears never to be consulted, so the API reads as though it offers
a way to pin a region against a rebase when it does not.

I may have the intent wrong: if rebaseable governs some path other than BNRebase, then this is a
documentation bug rather than a behaviour one, and it would help to say what it does govern. The
only documentation I can find is the one-line Python docstring, "Set the rebaseable state for the
named region."

Steps To Reproduce:
Headless, with any binary. Reproduces with all user plugins disabled (BN_DISABLE_USER_PLUGINS=1).

import binaryninja
from binaryninja.enums import SegmentFlag

bv = binaryninja.load("/bin/ls")
mm = bv.memory_map

mm.add_memory_region("pinned", 0x500000000, b"\xaa" * 0x1000, SegmentFlag.SegmentReadable)
mm.set_memory_region_rebaseable("pinned", False)

r = mm.get_region("pinned")
print("before rebase: view start %#x, region start %#x, rebaseable %s" % (bv.start, r.start, r.rebaseable))

new = bv.rebase(0x200000000, force=True)
r = new.memory_map.get_region("pinned")
print("after  rebase: view start %#x, region start %#x, rebaseable %s" % (new.start, r.start, r.rebaseable))

Output:

before rebase: view start 0x100000000, region start 0x500000000, rebaseable False
after  rebase: view start 0x200000000, region start 0x600000000, rebaseable False

The view moved by 0x100000000 and so did the region, despite rebaseable being False on both
sides of the rebase.

Expected Behavior:
One of:

  1. A region with rebaseable = false keeps its address across a rebase while the rest of the view
    moves; or
  2. if the flag means something other than "this region moves when the view is rebased", the API
    documents what it does mean.

Screenshots/Video Recording:
N/A — headless, output included above.

Binary:
Not applicable. The repro uses stock /bin/ls and reproduces with any file; it is not
binary-specific.

Additional Information:

  • No caller anywhere in binaryninja-api at HEAD (e0e3650, 2026-08-21). rebaseable appears
    only in the BNMemoryRegionInfo struct, the BNIs/BNSet declarations, the inline C++ wrappers,
    and the Python and Rust bindings. No builtin view type sets it, and there is no example or doc
    page for it.
  • The Rust binding carries // TODO: Should we just call this is_memory_region_relocatable? at
    rust/src/binary_view/memory_map.rs:394, which suggests the intended meaning may still be open.
  • The state is genuine and persisted, not a stub field: libbinaryninjacore contains
    SetMemoryRegionRebaseableUndoAction carrying oldRebaseable / newRebaseable, plus log strings
    ' as rebaseable' and ' as non-rebaseable'. Setting the flag is a real, undoable change and the
    value migrates onto the view produced by the rebase.
  • Combinations tested, all of which shift by the full delta:
    • byte-backed regions and file-backed regions;

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions