You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Add a deliberate deception layer — decoy code, honeypot data, and stronger opaque predicates — to send reverse engineers down rabbit holes, and to modernize the existing "junk code" which is effectively dead on current runtimes. Goal: raise manual-RE cost and defeat pattern/tooling that keys on the real logic, for legitimate IP protection.
Predicate types (PredicateType): Normal (simple), Expression (ExpressionPredicate → DynCipher.GenerateExpressionPair, a reversible arithmetic transform), x86 (x86Predicate, native — Windows/x86 only).
Junk code (CFContext.AddJunk) and opaque junk branches (CFContext.AddJump): crude invalid-IL (pop/dup/throw/ldarg 0xff/ldloc 0xff/ldtoken) placed on never-taken paths.
Gaps
Gap
Detail
Junk is dead on modern runtimes
AddJunk and the fancy AddJump branches are gated if (Method.Module.IsClr40 ...) return; → off for .NET 4.x / Core / 5–10. Only pre-CLR-4 (net2.0/3.5) gets them.
Junk is invalid-IL, not deceptive logic
It's anti-decompiler noise that would crash if executed — not plausible fake code that wastes an analyst's time.
No decoy methods
No plausible fake routines (fake license check, fake crypto, fake config parsing) to sink RE effort into.
No honeypot data
No fake strings/constants/metadata (fake keys, fake endpoints) that lead nowhere.
Opaque predicates aren't synthesis-resistant
Expression is reversible arithmetic → resolvable by symbolic execution / program synthesis (Syntia/QSynth-class).
Nothing survives pruning
No reachable / data-dependent decoys; static dead code gets removed by reachability analysis.
Proposed improvements
Modern valid junk/decoy — replace invalid-IL junk with valid, verifiable dead-but-plausible code that runs on CLR 4.0+ (not gated off), guarded by strong predicates so it isn't trivially dead-code-eliminated.
Decoy methods + honeypot data — inject plausible fake routines and fake strings/constants/metadata; make some data-dependent / reachable-looking so dynamic tracing can't cleanly separate real from fake.
Synthesis-resistant opaque predicates — add predicates hard for symbolic execution / synthesis (verified-complex / MBA-style, LOKI-inspired), beyond the current reversible-arithmetic Expression.
Survive reachability/dead-code elimination — weave decoys into reachable paths; where a VM is present (Feature: method virtualization (VM-based protection) #111), place decoy handlers/bytecode inside the VM's dispatched paths so they can't be cheaply pruned.
The honest catch
Naive decoys get pruned — reachability analysis and dynamic tracing strip static dead code and ignore never-executed branches. Decoys are effective only when guarded by strong opaque predicates or woven into genuinely reachable/dispatched paths. Deception raises cost; it does not prevent RE.
Modernizing junk to run on CLR 4.0+ is a concrete, standalone win independent of the VM — the current behavior means modern targets get no junk at all.
Scope as opt-in, incremental (junk-modernization first; decoy methods/honeypots and synthesis-resistant predicates as follow-ups).
Summary
Add a deliberate deception layer — decoy code, honeypot data, and stronger opaque predicates — to send reverse engineers down rabbit holes, and to modernize the existing "junk code" which is effectively dead on current runtimes. Goal: raise manual-RE cost and defeat pattern/tooling that keys on the real logic, for legitimate IP protection.
What we have today (source analysis)
Confuser.Protections/ControlFlow:SwitchMangler/JumpMangler+ a key-transformed switch dispatcher. Solid baseline.PredicateType):Normal(simple),Expression(ExpressionPredicate→DynCipher.GenerateExpressionPair, a reversible arithmetic transform),x86(x86Predicate, native — Windows/x86 only).CFContext.AddJunk) and opaque junk branches (CFContext.AddJump): crude invalid-IL (pop/dup/throw/ldarg 0xff/ldloc 0xff/ldtoken) placed on never-taken paths.Gaps
AddJunkand the fancyAddJumpbranches are gatedif (Method.Module.IsClr40 ...) return;→ off for .NET 4.x / Core / 5–10. Only pre-CLR-4 (net2.0/3.5) gets them.Expressionis reversible arithmetic → resolvable by symbolic execution / program synthesis (Syntia/QSynth-class).Proposed improvements
Expression.The honest catch
Naive decoys get pruned — reachability analysis and dynamic tracing strip static dead code and ignore never-executed branches. Decoys are effective only when guarded by strong opaque predicates or woven into genuinely reachable/dispatched paths. Deception raises cost; it does not prevent RE.
Relationship
Scope as opt-in, incremental (junk-modernization first; decoy methods/honeypots and synthesis-resistant predicates as follow-ups).