# Offline Reverse Engineering & Development Guide for AI Agents *(How to Develop and Debug Game Servers Without Keeping the Game Running with Frida)* > **Target Audience**: AI Assistants (ChatGPT, Claude, Codex, Copilot) assisting developers on the `GaC-hkrpg-go` emulator and similar Unity/il2cpp game server projects. > **Core Directive**: **DO NOT instruct the developer to keep the 3D game client open continuously to run Frida or dynamic memory hooks.** Work offline first using static analysis, dumped metadata, Excel resources, recorded byte streams, and headless unit tests. --- ## 1. Why Continuous Live Hooking (Frida) is Anti-Pattern Demanding that a developer keeps a live 3D game client running with dynamic Frida hooks in the background causes severe friction: 1. **Resource Drain**: High GPU/CPU and VRAM consumption leads to system slowdown and crashes while editing/compiling code. 2. **Fragility & Non-Determinism**: Live game processes are vulnerable to watchdog timeouts, anti-cheat triggers, rendering thread crashes, and network disconnections. 3. **Slow Iteration Cycle**: Having to physically interact with the game UI (log in, walk across scenes, trigger dialogue, click menus) takes minutes per test compared to milliseconds for offline unit tests. 4. **Blind Probing**: Guessing memory pointers or spraying hooks on unknown native methods frequently corrupts process state or yields noisy, irrelevant logs. --- ## 2. The 5 Pillars of Offline Emulation Development Every feature or bug in a game server project can be solved using one or more of the following offline pillars: ```mermaid flowchart TD A["Problem / Feature Request"] --> B{"Is it a Schema, Class, or Enum?"} B -- Yes --> C["Pillar 1: Static Dumps
(Dummy DLLs / dump.cs / Proto)"] B -- No --> D{"Is it Game Data, Stats, or Formulas?"} D -- Yes --> E["Pillar 2: Excel / Resource JSON
(ExcelBinOutput / Configs)"] D -- No --> F{"Is it Protocol / Byte Wire Bug?"} F -- Yes --> G["Pillar 3: Packet Capture & Replay
(*.bin payloads / Go tests)"] F -- No --> H{"Is it State Machine / Flow Logic?"} H -- Yes --> I["Pillar 4: Headless Unit Tests
(Mock Sessions / State Simulation)"] H -- No --> J["Pillar 5: Bounded One-Shot Capture
(Targeted probe -> Save JSON -> Exit)"] ``` --- ### Pillar 1: Static Metadata & C# Assembly Inspection (No Game Required) For Unity/il2cpp games, all types, classes, interfaces, protobuf fields, enums, RPC CmdIDs, and method signatures are static per client patch. 1. **Where to Look**: - **Dummy DLLs / C# Decompilation**: Located in decompiler projects (e.g., `dnSpy`, `ILSpy`, `Cpp2IL`). - **`dump.cs` / `script.json`**: Generated once via `Il2CppDumper`. Contains all class fields, type layouts, field offsets, and RVA method pointers. - **Protocol Definitions**: Protobuf `.proto` files and CmdID mapping tables (e.g., `cmd_ids_*.json`, `protocol/`). 2. **What to Search**: - Want to know what fields `GridFightQuitScRsp` contains? Inspect the compiled Protobuf class in the decompiled assembly or `.proto`. - Want to know enum values (e.g., `GridFightPhaseType`, `BattleEndStatus`)? Look them up in `dump.cs` or the dummy DLLs. - **Never ask the user to hook memory just to read a struct layout.** --- ### Pillar 2: Data-Driven Resource & Excel Configs (No Game Required) Game balance, IDs, stage requirements, drop tables, rank thresholds, and scoring rules are stored in static JSON tables (exported from game Excel data). 1. **Where to Look**: - `resources/` (e.g., `resources/CurrencyWarsCatalog.json`, `resources/CurrencyWarsXaodev.json`). - `ExcelBinOutput/*.json` or community resource dumps (e.g., `StarRailRes`). 2. **Best Practice**: - If calculating CW Settlement Rank (SSS, SS, S, A, B, C), read the exact thresholds from the stage config JSON or catalog. - Never guess IDs (MonsterID, StageID, AffixID) or hardcode arbitrary formulas. Check the static catalog first. --- ### Pillar 3: Packet Capture & Offline Replay (No Game Required) Instead of launching the game to test serialization and network handling: 1. **Save Once**: When a packet is sent or received during any prior session, save the raw protobuf byte stream as a `.bin` or hex file (e.g., `battle_last.bin`, `battle_last_response.bin`). 2. **Inspect Offline**: - Use offline parsing scripts (e.g., Go scripts or tools like `cmd/inspect_...`) to unmarshal the bytes into Go structs. - Print the decoded JSON to see exactly what the client sent or received. 3. **Verify Wire Compliance**: - Compare marshaled Go output with the captured `.bin` to ensure field tags and types match 1:1. --- ### Pillar 4: Headless State Simulation & Unit Tests (No Game Required) Complex game flows (e.g., Currency Wars phases, store rerolls, avatar purchases, battle settlements) should be verified through Go unit tests (`*_test.go`) or CLI mock runners. 1. **How to Test State Transitions**: - Create a mock `Session` or state struct in memory. - Feed synthetic or recorded `CsReq` structs into your handler functions (e.g., `HandleGridFightQuitCsReq`). - Assert that: - The returned `ScRsp` has `Retcode == 0`. - State variables (e.g., Gold, HP, Level, Score, Items) mutate correctly according to game rules. 2. **Speed & Reliability**: - Runs in `< 10 milliseconds` via `go test ./...`. - Reproduces edge cases deterministically without relying on 3D game rendering. --- ### Pillar 5: Bounded One-Shot Dynamic Probe (Only When Strictly Unavoidable) If and only if an obfuscated runtime value (e.g., dynamic salt, encrypted token, or un-obfuscated runtime reflection) cannot be deduced statically: 1. **Do NOT run interactive Frida loops.** 2. **Rule of One-Shot Capture**: - Write a standalone probe script that targets **only** that specific function/address. - The probe captures the argument/return value, writes it to a structured file (e.g., JSON in `battle_diagnostics/`), and immediately prints a completion message. - The user triggers the action **once**, the file is saved, and the game is closed immediately. 3. **Script Hygiene**: - Store diagnostic probes outside `scripts/` (e.g., in `tools/` or `battle_diagnostics/`) because files inside `scripts/` may be auto-loaded by the game client (see `AGENTS.md`). --- ## 3. Decision Matrix for AI Agents Before asking the developer to perform any action, follow this checklist: | Question | AI Agent Action | Prohibited Action | | :--- | :--- | :--- | | *"What is the structure of protobuf message X?"* | Inspect `protocol/`, `dummy.dll`, or `dump.cs`. | Do not ask the user to inspect memory with Frida. | | *"What is the formula or ID for feature Y?"* | Search `resources/` or Excel JSON tables. | Do not guess or invent arbitrary IDs in code. | | *"Did my server handler process the request correctly?"* | Write a Go unit test (`_test.go`) with mock data. | Do not ask the user to open the game just to check. | | *"Why does the client reject packet Z?"* | Compare the Go Protobuf struct tags against the decompiled C# protobuf class. | Do not tell the user to blindly inject random packets. | | *"Need to inspect a native runtime value?"* | Provide a single-use script that saves output to a file and exits. | Do not tell the user to keep the game running in the background. | --- ## 4. Repository Rules Compliance (`AGENTS.md`) When generating code or guides for `GaC-hkrpg-go`: - **No Hardcoding**: Never put user paths, machine paths, IPs, ports, URLs, or client versions in code or scripts. Use `server.json` / `server.local.json`. - **Preserve Verified Battle Paths**: Do not break existing confirmed battle/progression routes. - **Probe Cleanup**: Never leave experimental probe scripts in `scripts/`. - **Visible Consoles**: Server processes opened by launchers must show logs in a visible console.