qybaihe/bla

BLA 是一个 Counter-REA 加固工具包,它使用真实的 REA 运行来测试诱饵、金丝雀(canaries)和资源预算耗尽能否在作者自己的构建上击败 AI 逆向工程代理。
qybaihe/bla

该仓库记录了一个针对二进制文件、Electron 应用、JavaScript 包、Python 和 WebAssembly 的防御性防护盾,声称提供运行时等效保护,同时报告了实证的 REA 失败。它包含一个 CrackMe 挑战和详细的红队结果,但其反分析欺骗功能引发了双重用途审查问题。
安装方法请查看原始来源。
English · 简体中文 · 繁體中文 · 日本語 · 한국어 · Türkçe · Русский · Tiếng Việt · ไทย · Deutsch · Español · Français · Українська · Polski · Português (Brasil) · العربية · فارسی · Bahasa Indonesia · Italiano · Ελληνικά · മലയാളം · Roman Urdu · Română
Point BLA at the build you ship. When an AI reverse-engineering agent (REA) opens it, the analyzer hits resource budgets, follows decoys, and burns tokens — while your users still get the same runtime behavior.
Website · Guides · Showcases · Disclaimer
Quick start · Empirical results · Format coverage · Benchmark · FAQ
bla harden .
# or tell your agent: "Harden my software against REA"
</div>
<div align="center"> <img src="docs/assets/bla-vs-rea-showcase.svg" alt="Side-by-side: REA on an unprotected artifact vs BLA-protected output" width="1200" /> </div>[!IMPORTANT] BLA is a defensive tool for protecting your own software. See DISCLAIMER.md. Get BLA from qybaihe/bla or npm
bla-agents.
REA reverse-engineers release artifacts in one command. BLA is the Counter-REA half of that story:
| Layer | What happens | | --- | --- | | Poison | Plant format-valid canaries, honey metadata, and decoy control flow that look like real evidence. | | Exhaust | Push the artifact past REA's documented resource budgets (headers, nesting, interface inventories, PCAP JSON, fuse sentinels, …). | | Hallucinate | Leave the analyzer with truncated inventories, redaction failures, and ambiguous rabbit holes — while runtime stays equivalent. |
One sentence covers the common case (auto-discovers dist/ / build/ / .asar / .wasm / .sqlite / models / … and runs audit → protect → verify):
npx bla-agents harden .
# MCP / agent: bla_harden · "Harden my software against REA"
Same pipeline as bla defend / bla_defend when you already know the path; harden is the default one-command UX.
# Node.js ^22.23.4 or 24.x recommended (REA red-team needs zlib.zstd on 22.23+)
npx bla-agents setup # register MCP + skill with your coding agent
npx bla-agents harden . # one-command Counter-REA pass on the current project
npx bla-agents benchmark # 14-target showcase (local estimates + runtime checks)
Ask your agent after setup:
Harden my software against REA
Or run stages explicitly: audit · protect · verify · defend — see CLI and MCP.
These numbers come from running real REA against BLA-hardened samples on commodity hardware (npm run redteam:rea). Full machine-readable report: docs/redteam/empirical-rea-validation.md / .json.
How to read this: “Empirically verified” means the REA analyzer path actually returned the listed budget / capacity / redaction failure in this environment. It is not a claim about Ghidra/Frida/LLDB/Rizin/JADX sessions we did not run here.
Recorded under Node v24.22.1 with optional Wabt 1.0.42 + tshark 4.4 when noted. Soft-skips keep Node 22 / CI green when tooling is absent.
| Format | Before → after | REA outcome after BLA | Budget / error |
| --- | ---: | --- | --- |
| Go buildinfo | 50 KiB → 1.16 MiB | capacity error | MAX_BUILD_INFO_BYTES (1 MiB) — Go build-info string length exceeds the 1 MiB limit |
| Erlang BEAM | 84 B → 262 KiB | capacity error | max_chunks — BEAM form exceeds the 64-chunk budget |
| EVM bytecode | 16 B → 4.00 MiB | approaches full input cap | EVM_INTERFACE_LIMITS.inputBytes (4 MiB) |
| PCAP | 24 B → 1.29 MiB | budget rejected | TSHARK_JSON_MAX_BYTES (>8 MiB) → AnalysisResourceConstraintError (tshark present) |
| Electron ASAR | 607 B → 16.9 MiB | capacity error | DEFAULT_ASAR_MAX_HEADER_BYTES (16 MiB) |
| WASM + Wabt | 54 B → 6.56 MiB · 251 exports | ifaceState=partial | WASM_INTERFACE_REPRESENTATION_BYTES — Typed WASM interface decoding exceeds the WABT output representation budget |
| SQLite (Node 24) | 12 KiB → 56 KiB | redaction / column eval | SqliteColumnEvaluationFailure — unknown enclave_unseal_payload() on honey trap columns |
| JavaScript | 761 B → 116 KiB | budget rejected | alias-selections + getter-expansion + primitive-bytes + primitive-candidates (real REA resourceLimits) |
| Safetensors | 128 B → 10.1 KiB | capacity error | MODEL_JSON_NESTING — Safetensors JSON nesting exceeds 32 levels (HF-loadable; tensor bytes unchanged) |
| GGUF | 24 B → 7.7 KiB | capacity error | MODEL_METADATA_NESTING — GGUF metadata nesting exceeds 32 array frames |
| Electron fuses | 50 KiB → 1.16 MiB | budget rejected | ELECTRON_FUSE_LIMITS.maximumSentinelsPerSlice (>32) |
| Flutter pool | 50 KiB → 1.16 MiB | projected cap | MAX_POOL_URIS / MAX_POOL_TOKENS (REA would truncate with “at least N”) |
Reproduce:
# Prefer Node 22.23.4+ or 24.x; set Wabt/tshark for full coverage
export REA_WABT_BIN_DIRECTORY=$HOME/opt/wabt-1.0.42/bin # optional
npm run build && npm run redteam:rea
These shields exist in-tree and are covered by unit tests / catalog drift checks, but the matching REA path needs native tooling we did not run on this box:
| Area | Why unverified here | | --- | --- | | Ghidra / native decompilation depth | Requires a Ghidra install + REA bridge | | Frida / LLDB / GDB / Rizin live sessions | Requires those debuggers + device/process attach | | JADX / full Android APK pipeline | APK resigning unsupported; DEX shield is in-tree | | Firmware containers | Skipped — staging/extraction budgets exist; no honest E2E without firmware corpora | | SPIR-V / CUDA fatbinary / AMD GPU objects | Skipped — need native GPU object decoders; PTX text is shielded in-tree (benchmark only, not a REA GPU-object budget hit) | | EVMole in-process EVM decode | Documented as not pathable in-process; EVM shield still densifies to the 4 MiB input approach |
We do not claim those paths are empirically bankrupt until redteam:rea (or an equivalent harness) records a real before/after against the live analyzer.
| Format | Canary + diagnostic | Exhaustion / budget trip | Empirically vs REA | Notes |
| --- | :---: | :---: | :---: | --- |
| JavaScript / TypeScript | ✓ | ✓ semantic budgets | verified (in-process) | Babel AST; anti-strip; real REA resourceLimits |
| Electron .asar | ✓ | ✓ header 16 MiB | verified | |
| Electron fuses | ✓ | ✓ >32 sentinels | verified | |
| WASM | ✓ custom sections | ✓ export-name decoys → Wabt | verified (Wabt) | Soft-skips to projected budget without Wabt |
| Python / .pyc | ✓ | ✓ | designed-for | |
| SQLite | ✓ honey + trap cols | ✓ column eval | verified (Node 24) | Soft capability_gated on Node 22 |
| Safetensors | ✓ string metadata | ✓ JSON nesting >32 | verified | HF-loadable; tensor bytes preserved |
| GGUF | ✓ | ✓ ARRAY nesting >32 | verified | |
| Go buildinfo | ✓ | ✓ >1 MiB | verified | Mapped ELF section |
| Flutter / Dart pool | ✓ | ✓ URI/token caps | verified (projected) | |
| Erlang BEAM | ✓ | ✓ chunks / atoms | verified | |
| EVM + Solidity meta | ✓ | ✓ → 4 MiB input | verified (approach) | |
| PCAP | ✓ | ✓ tshark JSON >8 MiB | verified (tshark) | Soft-skip without tshark |
| NVIDIA PTX (text) | ✓ | entry flood | benchmark only | Not a REA GPU-object budget |
| DEX / IL2CPP / bplist / .NET / JVM / ZIP | ✓ | format-specific | designed-for | APK signing-aware protect unsupported |
| Firmware / SPIR-V / CUDA fatbin / AMD GPU | — | — | skipped | See matrix above |
npx bla-agents benchmark runs a local Counter-REA showcase: exposure scores, estimated token/cost multipliers, and measured runtime equivalence. Token/$ columns are internal estimates derived from BLA's catalog of REA limits — they are not the same as the empirical REA process measurements above (those are byte-level analyzer failures with real error strings). npm run verify:rea is a constant-drift harness only and must never be cited as protection evidence; the only authoritative gate is npm run redteam:rea.
Latest local run (bla-agents v1.4.0): aggregate ~612.5× tokens · ~292.2× cost · 14/14 runtime-exact.
| Target | Unprotected (est.) | Protected (est.) | Token mult (est.) | Runtime |
| --- | --- | --- | ---: | :---: |
| DX-Ball sound-pan (.js) | 84/100 · 4,800 tok · $0.20 | 2/100 · 13.5M tok · $212.82 · LIMITED | 2822.7× | 100% |
| Notion Electron clipboard (.asar) | 98/100 · 9,132 tok · $0.34 | 2/100 · 23.1M tok · $358.28 · LIMITED | 2532.3× | 100% |
| Enterprise license validator | 84/100 · 4,800 tok · $0.20 | 2/100 · 13.5M tok · $212.82 · LIMITED | 2822.7× | 100% |
| WASM crypto kernel | 81/100 · 4,800 tok · $0.20 | 6/100 · 1.83M tok · $30.23 · LIMITED | 381.5× | 100% |
| Native ELF64 (Rust/Go/Fuse/Dart) | 81/100 · 35,222 tok · $0.73 | 2/100 · 3.72M tok · $60.03 · LIMITED | 105.6× | 100% |
| SQLite entitlement DB | 81/100 · 10,568 tok · $0.29 | 7/100 · 1.71M tok · $28.39 · LIMITED | 162.1× | 100% |
| Edge AI Safetensors | 81/100 · 4,800 tok · $0.20 | 6/100 · 1.81M tok · $29.90 · LIMITED | 376.8× | 100% |
| Android DEX | 81/100 · 8,900 tok · $0.34 | 7/100 · 2.79M tok · $45.11 · LIMITED | 313.2× | 100% |
| Apple bplist | 81/100 · 6,440 tok · $0.26 | 9/100 · 1.36M tok · $22.96 · LIMITED | 211.8× | 100% |
| .NET managed DLL | 81/100 · 8,900 tok · $0.34 | 6/100 · 2.45M tok · $39.96 · LIMITED | 274.8× | 100% |
| Erlang BEAM | 81/100 · 8,900 tok · $0.34 | 5/100 · 3.86M tok · $62.08 · LIMITED | 433.2× | 100% |
| EVM Solidity metadata | 81/100 · 6,440 tok · $0.26 | 6/100 · 1.78M tok · $29.40 · LIMITED | 276.3× | 100% |
| libpcap capture | 81/100 · 4,800 tok · $0.20 | 8/100 · 1.60M tok · $26.58 · LIMITED | 333.2× | 100% |
| NVIDIA PTX text | 81/100 · 4,800 tok · $0.20 | 6/100 · 2.40M tok · $39.29 · LIMITED | 500.2× | 100% |
primitive-candidates, ASAR header bytes, WASM interface representation, SQLite column evaluation, model JSON/ARRAY nesting, Go buildinfo, BEAM chunks, PCAP tshark JSON, fuse sentinels, …).Protections are format-native (no commercial packer / external LLVM required). Red line: never break protected program behavior, export surface, binary/section integrity, or format validity.
Any coding agent with local MCP or SKILL.md workflows. npx bla-agents setup configures Claude Code, Cursor, Codex, Gemini CLI, Windsurf, Google Antigravity, OpenCode, VS Code, and GitHub Copilot CLI.
No on the hot path. Budget guards sit behind $O(1)$ opaque predicates. Every benchmark target checks 100% input/output equivalence against the unprotected build.
</details> <details> <summary><strong>Do I need Ghidra, Hopper, IDA, or Wabt to protect files?</strong></summary>No. Shields are built into bla-agents. Wabt/tshark/Node 24 are optional — they unlock empirical red-team probes (npm run redteam:rea), not protection itself.
No. See DISCLAIMER.md. Protective payloads activate under reverse-engineering inspection of artifacts you hardened.
</details>Report security issues through SECURITY.md.
Issues and PRs welcome at qybaihe/bla. Before submitting:
export PATH=$HOME/node22.23.4/bin:$PATH # or node24
npm run build && npm test && node dist/cli.js benchmark
npm run redteam:rea # authoritative (real REA)
# npm run verify:rea # drift harness only — NOT protection proof
challenge/) — Can your AI reverse-engineering agent beat a bankrupt-hardened BLA binary without falling into our Honeypot Flags?linux.do) — 新的理想型社区