Skip to content

Unique Obfuscation Identity System — per-build and per-project fingerprint elimination #69

Description

@mcpolo99

Goal

Make every ConfuserEx build and every obfuscation run produce unique output that cannot be identified by generic deobfuscation tools or AV heuristics. Two levels of uniqueness that stack for maximum stealth.

The Problem

Every ConfuserEx-obfuscated assembly carries identical fingerprints — same namespace (System.Core.Internal), same magic constants (0x3dbb2819), same watermark (ProtectedByAttribute), same algorithm patterns. Tools like de4dot pattern-match these known values. AV heuristics flag the same byte sequences. Every user's output looks identical.

The Solution: Two-Level Uniqueness

Level 1 — Source Identity Script (uniquify.py)

A setup script that makes your ConfuserEx build unrecognizable as ConfuserEx. Run once per environment.

Targets:

Fingerprint Default Value Randomized
Runtime namespace System.Core.Internal Derived from seed
Runtime type names Constant, Resource, Compressor, etc. Derived from seed
Runtime DLL name System.Core.Runtime.dll Derived from seed
Product string "Protected" User's choice
Default magic constants 0x3dbb2819, 0x3ddb2819, etc. Derived from seed
Process name checks "dnspy" Expanded/obfuscated
Watermark attribute name ProtectedByAttribute User's choice or random

Script features:

  • --seed "phrase" — deterministic, reproducible
  • --dry-run — show changes without modifying
  • --test — build + run tests after modification
  • --restore — revert to defaults

Level 2 — Per-Project Obfuscation Identity (runtime)

Randomize cryptographic constants per obfuscation run. Works on stock or script-customized builds.

Targets:

Fingerprint Current After
Anti-tamper feedback constant 0x3dbb2819 hardcoded Derived from project seed
Compressor feedback constant 0x3ddb2819 hardcoded Derived from project seed
Hash constants 0x6fff61 / 0x5e3f1f hardcoded Derived from project seed
CFGCtx multiplier 0x21412321 hardcoded Derived from project seed
XorShift parameters 12/25/27 hardcoded Picked from valid set per seed
Prime moduli 0x143fc089 etc. hardcoded Picked from valid prime set per seed

Implementation: Convert hardcoded constants to Mutation.KeyI* placeholders. The MutationHelper system already injects per-run values — minimal new infrastructure needed.

Watermark Configurability

Currently hardcoded (always on or off via source edit). Should be project-level:

<!-- Disable watermark -->
<protection id="watermark" action="remove" />

<!-- Custom watermark -->
<protection id="watermark">
  <argument name="text" value="MyCompany Security" />
  <argument name="attributeName" value="SecurityStampAttribute" />
</protection>

Default: off (no fingerprint unless explicitly enabled).

How The Levels Stack

Setup de4dot AV heuristics Per-project analysis
Stock ConfuserEx Works Flags it Easy
Level 2 only Constant matching fails Reduced Needed per project
Level 1 only Name detection fails Fails Harder
Level 1 + Level 2 Completely fails Fails Needs reverse engineering per build AND per project

Out of Scope (Hard Fingerprints)

These require architectural redesign, not randomization:

  • JIT hook technique (hooking ICorJitCompiler::compileMethod)
  • Anti-dump PE header zeroing behavior
  • LZMA decompressor algorithm structure
  • Reference proxy DynamicMethod architecture

Documented for awareness but not part of this feature.

Implementation Order

  1. Watermark configurability — quick win, project-level on/off with custom text
  2. Level 2 — convert magic constants to mutation keys, per-run randomization
  3. Level 1 — the uniquify.py script for source-level identity change

Related Issues

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions