mirror of
https://github.com/ran-j/PS2Recomp.git
synced 2026-10-06 19:52:36 -04:00
49617104077a925f7cddc89c668505e7694acaf6
* Add missing VU0 Special1 macro translations * Fix VU0 macro decode and field ops Align Special2 decoding with fhi_flo, implement VCLIPw/VABS, and fix field variants (VADDx/VSUBx/VMULx). Keep C++17 compatibility by replacing unordered_set::contains and remove dead ADDIU return. Update Special2 metadata for VWAITQ. * vu0: complete macro mappings and add coverage test * review: clean up vu macro handling * fix: restore C++20 contains in code generator * fix: correct VU0 Special2 instruction encoding in decoder test --------- Co-authored-by: Antonio Guastella <antonioguastella@energine.it> Co-authored-by: Ranieri <ran-junior@hotmail.com>
PS2Recomp: PlayStation 2 Static Recompiler (Experimental)
Also check our WIKI
This project statically recompiles PS2 ELF binaries into C++ and provides a runtime to execute the generated code.
Modules
ps2xAnalyzer: scans ELF/functions and writes TOML config (stubs,skip, instruction patches).ps2xRecomp: reads TOML + ELF, decodes R5900 instructions, and generates C++ output.ps2xRuntime: hosts memory, function registration, syscall dispatch, and hardware stubs.
Features
- Translates MIPS R5900 instructions to C++ code
- PS2-specific MMI and VU0 macro support.
- Single-file or multi-file output.
- Configurable stubs, skips, and instruction patches.
- Instruction-driven syscall handling.
How It Works
PS2Recomp works by:
- Parsing a PS2 ELF file to extract functions, symbols, and relocations
- Decoding the MIPS R5900 instructions in each function
- Translating those instructions to equivalent C++ code
- Generating a runtime that can execute the recompiled code
The translated code is very literal, with each MIPS instruction mapping to a C++ operation. For example, addiu $r4, $r4, 0x20 becomes ctx->r4 = ADD32(ctx->r4, 0X20);.
Current Behavior
stubsentries generate wrappers that call known runtime syscall/stub handlers by name.skipentries are not recompiled and generate explicitps2_stubs::TODO_NAMED(...)wrappers.- Recompiled
SYSCALLnow callsruntime->handleSyscall(...)with the encoded syscall immediate. - Runtime syscall dispatch tries encoded syscall ID first, then falls back to
$v1.
Requirements
- CMake 3.20+
- C++20 compiler (currently tested mainly with MSVC)
- SSE4/AVX host support for some vector paths
Build
git clone --recurse-submodules https://github.com/ran-j/PS2Recomp.git
cd PS2Recomp
cmake -S . -B out/build
cmake --build out/build --config Debug
Usage
- Analyze ELF and generate config:
./ps2_analyzer your_game.elf config.toml
For better results on retail games, see the Ghidra Workflow.
- Recompile using generated TOML:
./ps2_recomp config.toml
- Build generated output and link with
ps2xRuntime.
Configuration
Main fields in config.toml:
general.input: source ELF path.general.ghidra_output: optional function map CSV.general.output: generated C++ output folder.general.single_file_output: one combined cpp or one file per function.general.patch_syscalls: apply configured patches toSYSCALLinstructions (falserecommended).general.patch_cop0: apply configured patches to COP0 instructions.general.patch_cache: apply configured patches to CACHE instructions.general.stubs: names to force as stubs.general.skip: names to force as skipped wrappers.patches.instructions: raw instruction replacements by address.
Example:
[general]
input = "path/to/game.elf"
ghidra_output = ""
output = "output/"
single_file_output = true
patch_syscalls = false
patch_cop0 = true
patch_cache = true
stubs = ["printf", "malloc", "free"]
skip = ["abort", "exit"]
[patches]
instructions = [
{ address = "0x100004", value = "0x00000000" }
]
Runtime
To execute the recompiled code.
ps2xRuntime currently provides:
- Guest memory model and function dispatch table.
- Some syscall dispatcher with common kernel IDs.
- Basic GS/VU/file/system stubs.
- Foundation to expand and port your game.
Limitations
- Graphics Synthesizer and other hardware components need external implementation
- VU1 microcode is not complete.
- Hardware emulation is partial and many paths are stubbed.
Acknowledgments
- Inspired by N64Recomp
- Uses ELFIO for ELF parsing
- Uses toml11 for TOML parsing
- Uses fmt for string formatting
Languages
C++
97.4%
Java
1.3%
CMake
1.1%
Shell
0.2%