@ecls-studio/rerius
v1.1.1
Published
Rerius — binary analysis, disassembler, CFG, symbolic execution, decompiler. x86-64 · AArch64 · RISC-V. Zero external dependencies.
Maintainers
Readme
Rerius
Multi-architecture binary analysis framework — disassembler, CFG builder, decompiler, emulator.
C99 · No external dependencies · x86-64 · AArch64 · RISC-V · ELF · PE · Mach-O
What this is
Rerius is a static (and, for two architectures, dynamic) binary analysis toolkit: a disassembler, control-flow/call-graph builder, a pseudo-C decompiler, a concrete emulator, and a set of heuristic passes for spotting packing, obfuscation, and anti-analysis tricks. It ships as a standalone CLI, a C library, and a Node.js addon.
It is a research and reverse-engineering aid, not a fully automated malware classifier or a guaranteed decompiler — heuristic passes (entropy, obfuscation signals, function detection on stripped binaries) report a confidence score rather than a certainty, and should be read as leads to investigate, not verdicts.
Quick Start
git clone https://github.com/ECLS-Studio/rerius.git
cd Rerius
makemake runs setup.sh, an interactive script for choosing what to build: the CLI binary, the JS addon, or a local copy of the /learn docs. Choose Code to compile the native binary, then:
./rerius -x ./binaryOr install via npm (no clone required):
npm install @ecls-studio/reriusconst rerius = require('@ecls-studio/rerius');
rerius.withBinary('/path/to/binary', bin => {
console.log(bin.arch, bin.sha256);
console.log(bin.sections().length, 'sections');
console.log(bin.functions().length, 'functions');
});Android / Termux:
pkg install nodejs clang make git
git clone https://github.com/ECLS-Studio/rerius.git
cd Rerius && makeSupported Formats & Architectures
| | x86-64 | AArch64 | RISC-V RV64 | |---------|:------:|:-------:|:-----------:| | ELF64 | ✓ | ✓ | ✓ | | ELF32 | ✗ (see note) | ✗ (see note) | ✓ (RV32) | | PE64+ | ✓ | ✓ | - | | PE32 | ✗ (not supported) | - | - | | Mach-O 64 | ✓ | ✓ | - | | Mach-O FAT | ✓ | ✓ | - | | Raw | ✓ | ✓ | ✓ |
Known gap: the ELF32 loader currently checks e_machine against the 64-bit machine IDs, so genuine 32-bit x86/ARM ELF files are rejected rather than parsed — only ELF32 RISC-V (RV32, which shares its machine ID with RV64) loads correctly today. PE32 (32-bit) isn't handled at all — the PE loader only recognizes the 64-bit x86-64 and ARM64 machine types. See BINARY_FORMATS.md for details.
Feature Map
Core Analysis
| Feature | Flag | Description |
|---|---|---|
| Disassembly | (default) | x86-64, AArch64, RISC-V RV64GC |
| Section listing | -l | Virtual address, file offset, size, flags, instruction count |
| Hex bytes | -a | Raw bytes alongside instructions |
| Symbol resolution | -y | ELF symtab/dynsym, PE exports, Mach-O nlist |
| C++ demangling | -d | Itanium ABI |
| Function detection | -f | Symbol table when present, heuristic boundary detection otherwise |
| Instruction groups | -g | Color-coded call/branch/ret/stack/syscall classes |
| Cross-references | -r | Call and branch xref table |
| String references | -t | Inline .rodata string annotations |
| CFG | -C | Two-pass control-flow graph construction, with handling for common jump-table and opaque-predicate patterns |
| Loop detection | -L | Natural loops via dominator analysis |
| Call graph | -G | Caller/callee relationships |
| Switch tables | -W | Jump-table pattern detection |
| Unicode strings | -u | UTF-8 and UTF-16LE/BE extraction with a false-positive filter |
| All standard | -x | Runs all of the above |
Advanced Analysis
| Feature | Flag | JS API | Platform |
|---|---|---|---|
| Symbolic execution | -P | .symexec(idx) | ARM64, x86-64, RISC-V |
| SSA / typed IR lifting | -Q | .ssa(idx) | ARM64, RISC-V |
| Decompiler (pseudo-C) | -D | .decompile(idx) | ARM64, RISC-V |
| Concrete emulator | -I | .emulate(idx, regs) | ARM64, RISC-V |
| Entropy analysis | -e | .entropy() | All |
| Recursive descent | -R | .rda(section) | ARM64, x86-64, RISC-V |
| Instruction validity filter (IVF) | -V | .ivf() | ARM64, x86-64, RISC-V |
| Polymorphic obfuscation map | --poly | — | All |
| DSA (dynamic single assignment, all functions) | --dsa | — | ARM64, RISC-V |
| AIRE (heuristic pattern signals) | --aire | — | All |
| VM dispatch trace | --vm-trace | — | ARM64, x86-64, RISC-V |
| Everything | -X | — | — |
On "AIRE": the --aire flag runs a set of weighted heuristics (function shape, caller/callee counts, instruction mix, DSA signals) that surface candidate observations — possible VM dispatch, packing, crypto constants, anti-debug checks — each with a numeric confidence score. It is rule-based pattern matching, not a trained model, and its output is a set of leads for a human analyst rather than a classification. Results are cached to .aire_memory and referenced on the next run against the same binary.
The -Q/.ssa() pass is referred to internally as "NR" in src/analysis/decomp.c and as "SSA Form" in the web UI; both names refer to the same pass. It lifts instructions to a typed intermediate representation using standard SSA-style variable versioning (each register write becomes a new versioned variable), with basic type tags (pointer, flags, sized integer) inferred from the producing instruction, and resolves direct call targets against the function table where possible.
Robustness (v1.0.0+)
| Feature | Description |
|---|---|
| Per-pass fault isolation | Each of the 32 analysis passes invoked from main.c runs inside a DAX_RUN_PASS wrapper; a pass that hits a structural fault reports it and the remaining passes still run |
| DAX_GUARD_BIN / DAX_GUARD_FUNC | Public entry points validate size/count fields against DAX_MAX_* bounds before touching memory |
| Overflow-safe section arithmetic | Offset/size checks use the subtraction form (size > total - offset) rather than addition, to avoid integer-overflow bypasses |
| Counter normalization | dax_clamp_counts() re-clamps struct counters after each load phase |
| Loop budget guard | Decode loops cap at 65536 iterations per function to bound worst-case runtime on malformed input |
This reduces the blast radius of a single malformed input; it is not a formal memory-safety guarantee. See SECURITY.md for what is and isn't covered.
npm Usage
npm install @ecls-studio/reriusnpm install compiles the native addon as part of the install step — no separate build command needed.
const rerius = require('@ecls-studio/rerius');
// One-liner with auto-close
rerius.withBinary('/path/to/binary', bin => {
const r = bin.analyze();
console.log(r.functions.length, 'functions,', r.xrefs.length, 'xrefs');
console.log(bin.decompile(0)); // pseudo-C (ARM64/RISC-V)
console.log(bin.entropy()); // packing/encryption signal
});TypeScript declarations are included (js/index.d.ts); no separate @types/rerius package is needed.
See NPM_USAGE.md for Express, Fastify, Docker, and TypeScript examples.
Web UI
rerius.sbs is the official documentation site and also hosts a live instance for trying the tool without installing anything.
To run it against your own binaries over a local REST API instead:
node js/server/server.js
# API available at http://localhost:7070The UI exposes 23 panels covering overview, sections, symbols, functions, disassembly, CFG basic blocks, call graph, loop detection, cross-references, ASCII/Unicode strings, decompiler, SSA form, symbolic execution, emulator, entropy, recursive descent, instruction validity filter, polymorphic obfuscation map, obfuscation score, AIRE, and VM dispatch trace.
The server binds to localhost by default and is intended for local or LAN use — see SECURITY.md before exposing it publicly.
All CLI Flags
| Flag | Description |
|------|-------------|
| -a | Hex bytes |
| -s <sec> | Target section (default .text) |
| -S | All executable sections |
| -A / -E | Start / end address (hex) |
| -l | Section listing |
| -n | No color |
| -v | Verbose |
| -y | Resolve symbols |
| -d | Demangle C++ |
| -f | Detect functions |
| -g | Instruction group coloring |
| -r | Cross-reference annotations |
| -t | String reference annotations |
| -C | Control flow graphs |
| -L | Loop detection |
| -G | Call graph |
| -W | Switch/jump table detection |
| -u | Unicode string scan |
| -P | Symbolic execution |
| -Q | SSA / typed IR lifting (internally "NR") |
| -D | Decompile to pseudo-C (type tagging + resolved direct calls) |
| -I | Emulate functions (ARM64, RISC-V) |
| -e | Entropy analysis |
| -R | Recursive descent disassembly |
| -V | Instruction validity filter |
| --poly | Polymorphic obfuscation map |
| --dsa | DSA — dynamic single assignment (all functions) |
| --aire | AIRE — heuristic pattern signals with confidence scoring |
| --vm-trace | Print VM dispatch trace after emulation |
| -x | All standard analysis |
| -X | Everything (includes --poly --aire --vm-trace --dsa) — also enables interactive mode (see note below) |
| -i | Interactive shell (REPL) |
| -eox <folder> | Load plugins from folder |
| -eox-list | List loaded plugins |
| -o <file> | Save .daxc snapshot |
| -c | Convert .daxc → .S |
| -h | Help |
Note on -X: in src/cli/main.c, -X sets opts.interactive = 1 along with every analysis flag — after printing all the analysis output, it drops into the interactive shell rather than returning to your terminal. With stdin closed or redirected (e.g. < /dev/null, or piped in a script), the shell reads EOF immediately and the process exits normally; run directly at an interactive terminal, it will wait for shell commands instead of returning. If you want a batch "run everything and exit" invocation, either redirect stdin from /dev/null or use -x -P -Q -D -I -e -R -V --poly --aire --vm-trace --dsa (same passes as -X, without the interactive flag).
Documentation
| File | Description |
|------|-------------|
| BUILDING.md | Build instructions for all platforms |
| NPM_USAGE.md | Using Rerius as an npm dependency |
| PUBLISHING.md | CI/CD and npm publish guide |
| CLI_REFERENCE.md | Complete CLI reference with examples |
| API.md | C API reference (includes fault isolation API) |
| ARCHITECTURE.md | Internal module design and fault isolation model |
| ALGORITHMS.md | CFG, entropy, RDA, and SSA/NR algorithms |
| js/README.md | JavaScript API and REST server |
| MACHO_SUPPORT.md | Mach-O / macOS format details |
| DECOMPILER.md | SSA/NR IR and pseudo-C decompiler |
| EMULATOR.md | ARM64 and RISC-V concrete emulator |
| EXAMPLES.md | Usage recipes (CLI, JS, REST) |
| FAQ.md | Frequently asked questions |
| OBFUSCATION.md | Analyzing obfuscated/packed binaries |
| UNICODE_DETECTION.md | Unicode scanner design |
| FORMAT_DAXC.md | .daxc snapshot format spec |
| PERFORMANCE.md | Benchmarks and optimization notes |
| FUZZING.md | AFL++, libFuzzer, ASan guide |
| INTEGRATION.md | VS Code, Docker, Python, CI integration |
| SECURITY.md | Vulnerability reporting and defense-in-depth model |
| TROUBLESHOOTING.md | Build and runtime troubleshooting |
| PORTING.md | Porting to new architectures/formats |
| CICD_GUIDE.md | GitHub Actions workflows explained |
| CONTRIBUTING.md | Contribution guidelines |
| CODE_OF_CONDUCT.md | Community standards |
| CHANGELOG.md | Release history |
Requirements
- C99 compiler: GCC ≥ 7 or Clang ≥ 6 (tested with Clang 21 on Termux)
- GNU Make (or
gmakeon BSD) - No external libraries for the C core
- For the JS addon / npm package: Node.js ≥ 16 with development headers
License
Apache 2.0 — see LICENSE.
