Claude-skill-registry bg3se-macos-ghidra
install
source · Clone the upstream repo
git clone https://github.com/majiayu000/claude-skill-registry
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/majiayu000/claude-skill-registry "$T" && mkdir -p ~/.claude/skills && cp -r "$T/skills/data/bg3se-macos-ghidra" ~/.claude/skills/majiayu000-claude-skill-registry-bg3se-macos-ghidra && rm -rf "$T"
manifest:
skills/data/bg3se-macos-ghidra/SKILL.mdsource content
BG3 Script Extender macOS + Ghidra Development
Project Locations
| Project | Path |
|---|---|
| bg3se-macos | |
| bg3se (Windows ref) | |
Quick Start
# Build cd /Users/tomdimino/Desktop/Programming/bg3se-macos/build cmake .. && cmake --build . # Test ./scripts/launch_bg3.sh tail -f ~/Library/Application\ Support/BG3SE/bg3se.log # Ghidra (headless, optimized) ./ghidra/scripts/run_analysis.sh <script.py>
Key Constraints (macOS)
- Cannot hook main binary - Hardened Runtime blocks
hooks__TEXT - CAN hook libOsiris.dylib - 1,013 exported symbols
- ARM64 ABI - x8 register for structs >16 bytes
- No GetRawComponent - Must traverse ECS manually
See macos-patterns.md for detailed differences.
Module Structure
src/ ├── injector/main.c # Core (~2900 lines): hooks, Osi.*, Lua state ├── entity/ # ECS: guid_lookup, component_lookup, arm64_call ├── lua/ # Ext.* APIs: stats, debug, osiris, json ├── osiris/ # Osiris types, functions, custom_functions ├── stats/ # RPGStats, GlobalStringTable ├── console/ # Socket server, file-based console └── input/ # CGEventTap keyboard capture
API Surface (v0.22.0)
| Namespace | Status | Notes |
|---|---|---|
| 95% | Dynamic metatable, Query/Call/Event |
| 95% | RegisterListener, NewCall/Query/Event |
| 95% | Property read/write |
| 50% | Get, GetComponent, GetAllEntitiesWithComponent |
| 75% | 7 events |
| 100% | Complete |
| 100% | Memory introspection |
Not implemented:
Ext.Net, Ext.UI, Ext.Level, Client Lua State
Key Offsets
| Symbol | Address/Offset |
|---|---|
| |
| EntityWorld | EocServer+ |
| base+ |
| + |
| GlobalStringTable | base+ |
osgrep Usage
# IMPORTANT: cd into project first cd /Users/tomdimino/Desktop/Programming/bg3se-macos osgrep "how does entity lookup work" osgrep "Ext.Stats property resolution" # Windows reference cd /Users/tomdimino/Desktop/Programming/bg3se osgrep "CustomFunctionManager"
Common Tasks
Add new Ext. API:*
- Implement in
src/lua/lua_*.c - Register in
functionlua_*_register() - Test with EntityTest mod
Discover offset:
- Search strings in Ghidra
- Find XREFs, trace ADRP+LDR pattern
- Document in
ghidra/offsets/*.md
Port Windows feature:
- Search Windows BG3SE:
osgrep "feature" -p /path/to/bg3se - Understand pattern, find ARM64 equivalents
- Adapt for macOS constraints
Reference Documentation
- macos-patterns.md - macOS vs Windows, GUID byte order, component traversal
- bg3se-architecture.md - Windows BG3SE structure
- arm64-patterns.md - x8 register, calling conventions
- ghidra-workflows.md - Script usage, analysis patterns
- offset-discovery.md - Finding game addresses
Troubleshooting
Crashes on launch: Check dylib signing (
codesign -dv), verify ARM64 (file)
Hooks not called: Only hook libOsiris, not main binary
Entity lookup NULL: EoCServer may not be initialized; verify offset 0x288
osgrep no results: Run from project directory or use
-p flag