From arc-probe
Identifies C++ class from object pointer using RTTI, maps vtable with virtual functions, inheritance chain, and field offsets via probing. For reverse engineering binaries.
npx claudepluginhub vzco/arc-probe --plugin arc-probeThis skill uses the workspace's default tool permissions.
Identify a C++ class from an object pointer using RTTI, then map its vtable.
Discovers C++ classes by name via RTTI in target processes, maps vtables, disassembles virtual functions, explores inheritance hierarchies, and labels structures for analysis.
Reconstruct data structures by analyzing memory access patterns across functions
Decompiles x64dbg-debugged binary functions to C-like pseudocode using angr. Specify address/symbol or uses current RIP/EIP.
Share bugs, ideas, or general feedback.
Identify a C++ class from an object pointer using RTTI, then map its vtable.
address (required): Address of the object instance (hex)module (optional): Module name to search withinCheck if it's a C++ object — read the first 8 bytes:
probe_read_pointer address=<addr>
If the value looks like a code address (in the 0x7FF... range), it's likely a vtable pointer. If it's NULL or a small value, this isn't a C++ object (or it hasn't been constructed yet).
Resolve the class name via RTTI:
probe_rtti_resolve address=<addr>
This walks: object -> vtable -> vtable[-1] (COL) -> TypeDescriptor -> mangled name. Returns the demangled class name.
If rtti resolve fails, do it manually:
a. Read vtable pointer: probe_read_pointer address=<addr> → vtable_addr
b. Read COL pointer (vtable - 8): probe_read_pointer address=<vtable_addr - 8> → col_addr
c. Read TypeDescriptor RVA: probe_read_int address=<col_addr + 0xC> → td_rva
d. Get module base from probe_modules
e. Read mangled name: probe_read_string address=<module_base + td_rva + 0x10>
f. Demangle: strip .?AV prefix and @@ suffix → class name
Get the inheritance chain:
probe_rtti_hierarchy class=<class_name> module=<module>
Shows parent classes. Critical for understanding which fields come from which base class.
Map the vtable:
probe_rtti_vtable class=<class_name> module=<module> limit=20
This dumps virtual function entries with first-instruction disassembly previews. Look for:
this+offset or set a fieldjmp to another function): inherited methods that just redirectExplore interesting vtable entries:
probe_disassemble_function address=<vtable_entry>
For small getter functions, you can directly read what offset they access:
mov eax, [rcx+0x354] ; rcx = this, returns field at offset 0x354
ret
This tells you: vtable index N is a getter for field at offset 0x354.
Report:
Class: C_BaseEntity (inherits: CEntityInstance)
Vtable: 0x7FFB23456789 (42 entries)
vtable[0]: 0x7FFB21234000 — destructor
vtable[1]: 0x7FFB21234100 — getter: returns [this+0x354] (int32)
vtable[5]: 0x7FFB21234500 — large function (~0x200 bytes), references "health"
...
Known fields from vtable analysis:
+0x354 int32 (getter at vtable[1])
+0x35C int32 (getter at vtable[3])
Some binaries strip RTTI (/GR- compiler flag). Signs:
rtti scan returns very few or zero types for the module.?AV strings in the module's .rdata sectionFallbacks when RTTI is stripped: