Skip to content

v0.8.4 - #251

Merged
BinFlip merged 44 commits into
masterfrom
develop
Jul 27, 2026
Merged

v0.8.4#251
BinFlip merged 44 commits into
masterfrom
develop

Conversation

@BinFlip

@BinFlip BinFlip commented Jul 27, 2026

Copy link
Copy Markdown
Owner

Added

  • Memory optimization pass (compiler::MemoryOptimizationPass): store-to-load forwarding, redundant load elimination, and block-local dead store elimination, every rewrite gated on a Memory SSA alias proof. Registered in the deobfuscation pipeline's normalize phase and enabled by default; disable with PassConfig::memory_optimization = false. This reaches the field and array traffic obfuscators use to keep values out of SSA registers, which the register-level passes cannot see through
  • Field-sensitive points-to for CIL (CilTarget::field_member_index): the field's metadata token supplies the stable per-field cell identity Andersen's analysis keys on, so &o.a and &o.b no longer alias. An unresolved (null) field token falls back to the sound whole-object approximation
  • x86 segment overrides reach the IR: X86Memory gained a segment field, decoded from the instruction's explicit prefix, and fs:/gs:-qualified accesses now lower to LoadIndirect/StoreIndirect with a distinct address_space (257/256, following LLVM's numbering). Alias analysis treats the spaces as disjoint, so TEB/PEB and stack-cookie accesses stop colliding with flat memory at the same displacement. cs:/ds:/es:/ss: deliberately stay in the flat default — in flat user mode they share a base, and marking them would let alias analysis prove two names for one cell disjoint
  • Re-exports for analyssa's new alias machinery: analysis::{pointsto, address} modules plus MemorySsa, IndirectLocation, ArrayIndex, AliasResult, MemoryDefSite, MemoryPhiOperand, and MemorySsaStats
  • Cross-block value promotion before CFF restructuring (deobfuscation::passes::unflattening::spill): unflattening rewires the CFG, so the SSA has to be reconstructed afterwards — and reconstruction is a reaching-definition problem that can only be solved for values with a storage location. Arguments and locals have one; a stack temporary produced in one block and consumed in another exists only as an SSA name, and the sole record that two names denote the same value is the phi that merges them. Rewiring discards exactly that record, and for an edge the patch creates no phi ever described it. Every value crossing a block boundary is now promoted to a local slot before any terminator is touched — the classical "spill temporaries before restructuring" step — so rebuild can recover versions and phi placement for all of them by the ordinary algorithm. This is what makes .NET Reactor NecroBit samples reconstruct at all, and it is correct for any rewiring rather than only the shapes whose phis happen to survive
  • Zero-initialization for undefined SSA definitions (SsaConverter): a new construction phase materializes definitions for variables that had none, following ECMA-335 §I.12.3.2.2 — a typed zero Const for primitives and references, and LoadLocalAddr; InitObj; LoadLocal for value types. Previously such variables were registered with no defining instruction, so they survived initial construction but vanished the moment the variable table was rebuilt from real definitions
  • Emulation and CFF smoke tests (tests/emulation_smoke.rs): five samples whose deobfuscation depends on emulation or the unflattening tracer producing byte-identical results, each checked for semantic preservation against original.exe. The full packer suites take hours; this runs in seconds, so a change to the emulation layer or the tracer is validated against real output rather than only wall-clock time
  • Deobfuscation benchmark (benches/deobfuscation.rs): ConfuserEx and .NET Reactor groups plus a detection-only control, behind --features deobfuscation

Fixed

  • Taint-driven neutralization could produce IR with dangling reads: SentinelTaintRemovalPass and NeutralizationPass rewrote every tainted instruction to Nop and dropped every tainted phi, destroying definitions that surviving code still read. PhiTaintMode::NoPropagation makes phis taint barriers by design, so a phi routinely merges a tainted definition into code the analysis never marks. Both passes now shrink the removal set to a fixpoint (utils::retain_removable) — a candidate whose result still has a reader is kept rather than the removal widening into legitimate code. NeutralizationPass also excludes its protected DecryptedString constants from the candidate set rather than at rewrite time, so branch-target selection sees what is actually removed
  • AssemblyDependencyGraph::find_cycles reports participants, not a closed walk: following analyssa's switch to a single deterministic Tarjan pass, a self-dependency now names the assembly once rather than twice. The stale "modified DFS with three-color marking" documentation was corrected to match
  • CIL emulation fetched instructions in O(n) (emulation::engine::context::MethodCode): every executed instruction cloned the method's entire instruction vector and scanned it linearly for the current offset. A 3-million-instruction run performed 3.2 billion Instruction clones — about 1052 per step. Method bodies are now cached per token with an offset-to-index map, and the execution loop borrows the instruction instead of cloning it. Synthetic bodies bypass the cache, since ILGenerator can mutate them
  • Emulation rebuilt the assembly context on every instruction: loaded_assembly_context constructed a fresh EmulationContext and took an RwLock per executed instruction; contexts are now memoized per assembly index
  • optimize_locals split values it renumbered (SsaFunctionCilExt): renumbering a local moved its origin but left its rename group pointing at the old slot. rebuild_ssa groups variables by rename group while resolving argument/local representatives by origin, so the two views disagreed about which names denote the same local and the value ended up with no reaching definition. Both now move together
  • CFF tracer could escape its visit budget: entering an expression-switch false arm deliberately resets total_visits so each arm gets its own budget. On heavily nested methods that reset fired often enough to make the budget unbounded — a 348-block ConfuserEx method reached 3.3 million block visits against a 50,000 cap. A monotonic counter now bounds total work per trace without changing the per-arm semantics
  • CFF reconstruction produced invalid SSA after block cloning: cloned blocks duplicated every definition they contained, phi operands survived pointing at predecessors the patched CFG no longer has, and operands were left naming redirected blocks. Clones now allocate fresh variable ids (after state-tainted filtering, which keys on the original ids), phi operands are pruned against the patched predecessor sets and definedness, and redirected operands are resolved through a bounded hop limit
  • Cleanup deleted live types reachable only through another deletion candidate ([Bug]: Large amount of valid code removal on confuserex obfuscated executables #249, fix contributed in fix: stopped cleanup from removing types needed by other candidate types #248 by @agski331): find_unreferenced_types computed a single step of what is a transitive reachability problem. A candidate rescued partway through a pass never propagated that liveness onwards, so any cluster reachable solely through it was still read as isolated infrastructure — on reactor_virtualization that cut the assembly from 854 methods to 45, deleting a VM interpreter whose stubs remain live because nothing devirtualizes it. Reachability is now a worklist drain over a type-level call graph, in O(V+E) rather than O(depth × edges). CustomAttribute constructor types are seeded as roots before propagation rather than filtered afterwards, so the types those constructors call survive too, and liveness propagates from a nested type to its enclosing type — deleting an enclosing type cascades to its children through expand_type_tokens, which was dropping nested types that live code still called. The deletion set is sorted for a reproducible order
  • Technique cleanup ran whether or not the transformation it implies succeeded: a technique builds its cleanup request from detection findings alone, so it scheduled the decryptor, its infrastructure type, the initializer and the encrypted data for deletion even when no call site was reversed, leaving those call sites pointing at metadata that no longer exists and emptying the methods holding them. Removal now requires that nothing still calls the decryptor — a successful decryption rewrites its call site to the constant, so the absence of remaining callers is the evidence of reversal. Absence of recorded failures is not, since a decryptor that was never exercised has none either. Note that the caller check reads the SSA call graph, which covers only methods that converted successfully
  • ConfuserEx constant decryption missed builds that differ from stock 1.6.0 ([Bug]: Large amount of valid code removal on confuserex obfuscated executables #249): four defects, each masking the next. The blob index was matched against int32 alone, so builds emitting T Get<T>(uint32) yielded no decryptor at all — any integer width is now accepted, the surrounding constraints carrying the selectivity. stobj rejected reference types, though ECMA-335 §III.4.29 defines it over any typeTok and makes it equivalent to stind.ref for reference types, which is what stobj !!T becomes at T = string. ldelema hand-rolled its index match to I32/NativeInt while ldelem/stelem share a helper accepting every width, so a native uint index aborted emulation. And stfld through a pointer to a value-type array element replaced the whole element with the field's value instead of updating the field inside it, which is the path LZMA's bit-decoder struct arrays take
  • ConfuserEx LZMA blobs were rejected or misparsed ([Bug]: Large amount of valid code removal on confuserex obfuscated executables #249): the sniffer required the compressed payload to be smaller than its declared output, but LZMA expands small high-entropy input and the constants blob is XOR-encrypted before compression — a 44-byte blob compresses to 51 and was refused. The header was also modelled as 5 property bytes plus a 4-byte size, while builds calling the LZMA SDK's stream API write the standard 13-byte header with an 8-byte size; reading that as 9 bytes shifts the payload and corrupts the range coder. Both layouts are now attempted and held to the size each declares, and the size ceiling is documented as an allocation guard rather than a property of the format

Changed

  • Deobfuscating heavily flattened methods is roughly 25× faster, through changes that leave what the tracer computes unchanged:
    • Forks mark the evaluator instead of copying it, using analyssa 0.4.1's new checkpoint/rollback. A flattened method forks millions of times and the evaluator's state grows with everything the trace has learned, so copying it per fork was measured at 99% of tracer time. The same journal treatment is applied to the tracer's own visited-state set, whose sole writer only ever inserts
    • Per-block structural facts — dispatcher-target and foreign-dispatcher membership, constant-producer targets, and the overflow-dispatch-site predecessor walk — are computed once per trace rather than per block visit
    • The cross-scope local bridge indexes variables by local slot instead of scanning the whole variable table inside the per-instruction loop
    • PatchPlan keeps membership and redirect-target indexes beside its ordered vectors, replacing linear scans that ran once per block of every node in the trace tree
    • Trace nodes store their visited blocks inline (SmallVec); a 1200-block method produced 92 million nodes averaging about one block each, so the per-node heap allocation dominated the allocator
    • The per-node instruction log was removed: it recorded operand values nothing read, and its only consumer needed opcodes that are available from the SSA
  • Dependencies: bumped analyssa (0.3.0 → 0.4.1) and added smallvec (1.15)

Measured end-to-end on the packer samples, deobfuscating the whole assembly: ConfuserEx maximum 63.6 s → 2.0 s, and .NET Reactor necrobit — which previously failed to reconstruct at all — 385 s → 15.1 s. Part of that comes from analyssa 0.4.1 rather than from dotscope: alongside the evaluator's checkpoint/rollback, it batches the rebuild-mode substitution in eliminate_trivial_phis, which had been applying one whole-function scan per trivial phi. A rebuild produces trivial phis in proportion to the function, so the round was quadratic — on a 1200-block method it was the single largest cost in the pipeline.

BinFlip and others added 30 commits May 3, 2026 21:13
Brings the v0.8.1 (#220) release commit from master into develop.
Conflicts in the release-bookkeeping files (dotscope/Cargo.toml,
dotscope-cli/Cargo.toml, Cargo.lock, README.md, CHANGELOG.md) resolved
in favour of develop, which already carries the newer 0.8.2 state
(version bump, 0.8.2 changelog entry, #218 fat-header fix + regression
test, and the docs.rs ci.yml fix). Master contributed no unique content.
Backmerge the v0.8.1 (#220) release commit from master so develop
contains it as an ancestor, unblocking the v0.8.2 develop->master PR.
Release-bookkeeping conflicts (dotscope/Cargo.toml, dotscope-cli/Cargo.toml,
Cargo.lock, README.md, CHANGELOG.md) resolved in favour of develop's
newer 0.8.2 state. Master contributed no unique source content.
Bumps
[codecov/codecov-action](https://github.com/codecov/codecov-action) from
6 to 7.
<details>
<summary>Release notes</summary>
<p><em>Sourced from <a
href="https://github.com/codecov/codecov-action/releases">codecov/codecov-action's
releases</a>.</em></p>
<blockquote>
<h2>v7.0.0</h2>
<p>⚠️ Due to migration issues with keybase, we are unable to update our
keys under the <code>codecovsecurity</code> account. We have deleted the
account and are using <code>codecovsecops</code> with the original gpg
key</p>
<h2>What's Changed</h2>
<ul>
<li>ci: remove Enforce License Compliance workflow by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1950">codecov/codecov-action#1950</a></li>
<li>chore(release): 7.0.0 by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1957">codecov/codecov-action#1957</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v6.0.1...v7.0.0">https://github.com/codecov/codecov-action/compare/v6.0.1...v7.0.0</a></p>
<h2>v6.0.2</h2>
<p>This is a copy of the <code>v7.0.0</code> release to make updates
easier</p>
<h2>What's Changed</h2>
<ul>
<li>ci: remove Enforce License Compliance workflow by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1950">codecov/codecov-action#1950</a></li>
<li>chore(release): 7.0.0 by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1957">codecov/codecov-action#1957</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v6.0.1...v6.0.2">https://github.com/codecov/codecov-action/compare/v6.0.1...v6.0.2</a></p>
<h2>v6.0.1</h2>
<h2>What's Changed</h2>
<ul>
<li>fix: prevent template injection in run: steps (VULN-1652) by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1947">codecov/codecov-action#1947</a></li>
<li>chore(release): 6.0.1 by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1949">codecov/codecov-action#1949</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v6.0.0...v6.0.1">https://github.com/codecov/codecov-action/compare/v6.0.0...v6.0.1</a></p>
</blockquote>
</details>
<details>
<summary>Changelog</summary>
<p><em>Sourced from <a
href="https://github.com/codecov/codecov-action/blob/main/CHANGELOG.md">codecov/codecov-action's
changelog</a>.</em></p>
<blockquote>
<h2>v5.5.2</h2>
<h3>What's Changed</h3>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v5.5.1..v5.5.2">https://github.com/codecov/codecov-action/compare/v5.5.1..v5.5.2</a></p>
<h2>v5.5.1</h2>
<h3>What's Changed</h3>
<ul>
<li>fix: overwrite pr number on fork by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1871">codecov/codecov-action#1871</a></li>
<li>build(deps): bump actions/checkout from 4.2.2 to 5.0.0 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1868">codecov/codecov-action#1868</a></li>
<li>build(deps): bump github/codeql-action from 3.29.9 to 3.29.11 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1867">codecov/codecov-action#1867</a></li>
<li>fix: update to use local app/ dir by <a
href="https://github.com/thomasrockhu-codecov"><code>@​thomasrockhu-codecov</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1872">codecov/codecov-action#1872</a></li>
<li>docs: fix typo in README by <a
href="https://github.com/datalater"><code>@​datalater</code></a> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1866">codecov/codecov-action#1866</a></li>
<li>Document a <code>codecov-cli</code> version reference example by <a
href="https://github.com/webknjaz"><code>@​webknjaz</code></a> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1774">codecov/codecov-action#1774</a></li>
<li>build(deps): bump github/codeql-action from 3.28.18 to 3.29.9 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1861">codecov/codecov-action#1861</a></li>
<li>build(deps): bump ossf/scorecard-action from 2.4.1 to 2.4.2 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1833">codecov/codecov-action#1833</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v5.5.0..v5.5.1">https://github.com/codecov/codecov-action/compare/v5.5.0..v5.5.1</a></p>
<h2>v5.5.0</h2>
<h3>What's Changed</h3>
<ul>
<li>feat: upgrade wrapper to 0.2.4 by <a
href="https://github.com/jviall"><code>@​jviall</code></a> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1864">codecov/codecov-action#1864</a></li>
<li>Pin actions/github-script by Git SHA by <a
href="https://github.com/martincostello"><code>@​martincostello</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1859">codecov/codecov-action#1859</a></li>
<li>fix: check reqs exist by <a
href="https://github.com/joseph-sentry"><code>@​joseph-sentry</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1835">codecov/codecov-action#1835</a></li>
<li>fix: Typo in README by <a
href="https://github.com/spalmurray"><code>@​spalmurray</code></a> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1838">codecov/codecov-action#1838</a></li>
<li>docs: Refine OIDC docs by <a
href="https://github.com/spalmurray"><code>@​spalmurray</code></a> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1837">codecov/codecov-action#1837</a></li>
<li>build(deps): bump github/codeql-action from 3.28.17 to 3.28.18 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1829">codecov/codecov-action#1829</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v5.4.3..v5.5.0">https://github.com/codecov/codecov-action/compare/v5.4.3..v5.5.0</a></p>
<h2>v5.4.3</h2>
<h3>What's Changed</h3>
<ul>
<li>build(deps): bump github/codeql-action from 3.28.13 to 3.28.17 by
<code>@​app/dependabot</code> in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1822">codecov/codecov-action#1822</a></li>
<li>fix: OIDC on forks by <a
href="https://github.com/joseph-sentry"><code>@​joseph-sentry</code></a>
in <a
href="https://redirect.github.com/codecov/codecov-action/pull/1823">codecov/codecov-action#1823</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/codecov/codecov-action/compare/v5.4.2..v5.4.3">https://github.com/codecov/codecov-action/compare/v5.4.2..v5.4.3</a></p>
<h2>v5.4.2</h2>
<!-- raw HTML omitted -->
</blockquote>
<p>... (truncated)</p>
</details>
<details>
<summary>Commits</summary>
<ul>
<li>See full diff in <a
href="https://github.com/codecov/codecov-action/compare/v6...v7">compare
view</a></li>
</ul>
</details>
<br />


[![Dependabot compatibility
score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=codecov/codecov-action&package-manager=github_actions&previous-version=6&new-version=7)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores)

Dependabot will resolve any conflicts with this PR as long as you don't
alter it yourself. You can also trigger a rebase manually by commenting
`@dependabot rebase`.

[//]: # (dependabot-automerge-start)
[//]: # (dependabot-automerge-end)

---

<details>
<summary>Dependabot commands and options</summary>
<br />

You can trigger Dependabot actions by commenting on this PR:
- `@dependabot rebase` will rebase this PR
- `@dependabot recreate` will recreate this PR, overwriting any edits
that have been made to it
- `@dependabot show <dependency name> ignore conditions` will show all
of the ignore conditions of the specified dependency
- `@dependabot ignore this major version` will close this PR and stop
Dependabot creating any more for this major version (unless you reopen
the PR or upgrade to it yourself)
- `@dependabot ignore this minor version` will close this PR and stop
Dependabot creating any more for this minor version (unless you reopen
the PR or upgrade to it yourself)
- `@dependabot ignore this dependency` will close this PR and stop
Dependabot creating any more for this dependency (unless you reopen the
PR or upgrade to it yourself)


</details>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [actions/checkout](https://github.com/actions/checkout) from 6 to
7.
<details>
<summary>Release notes</summary>
<p><em>Sourced from <a
href="https://github.com/actions/checkout/releases">actions/checkout's
releases</a>.</em></p>
<blockquote>
<h2>v7.0.0</h2>
<h2>What's Changed</h2>
<ul>
<li>block checking out fork pr for pull_request_target and workflow_run
by <a href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2454">actions/checkout#2454</a></li>
<li>Bump actions/publish-immutable-action from 0.0.3 to 0.0.4 in the
minor-actions-dependencies group across 1 directory by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2458">actions/checkout#2458</a></li>
<li>Bump flatted from 3.3.1 to 3.4.2 by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2460">actions/checkout#2460</a></li>
<li>Bump js-yaml from 4.1.0 to 4.2.0 by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2461">actions/checkout#2461</a></li>
<li>Bump <code>@​actions/core</code> and
<code>@​actions/tool-cache</code> and Remove uuid by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2459">actions/checkout#2459</a></li>
<li>upgrade module to esm and update dependencies by <a
href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2463">actions/checkout#2463</a></li>
<li>Bump the minor-npm-dependencies group across 1 directory with 3
updates by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2462">actions/checkout#2462</a></li>
<li>getting ready for checkout v7 release by <a
href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2464">actions/checkout#2464</a></li>
<li>update error wording by <a
href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2467">actions/checkout#2467</a></li>
</ul>
<h2>New Contributors</h2>
<ul>
<li><a href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> made
their first contribution in <a
href="https://redirect.github.com/actions/checkout/pull/2454">actions/checkout#2454</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/actions/checkout/compare/v6.0.3...v7.0.0">https://github.com/actions/checkout/compare/v6.0.3...v7.0.0</a></p>
<h2>v6.0.3</h2>
<h2>What's Changed</h2>
<ul>
<li>Update changelog by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2357">actions/checkout#2357</a></li>
<li>fix: expand merge commit SHA regex and add SHA-256 test cases by <a
href="https://github.com/yaananth"><code>@​yaananth</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2414">actions/checkout#2414</a></li>
<li>Fix checkout init for SHA-256 repositories by <a
href="https://github.com/yaananth"><code>@​yaananth</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2439">actions/checkout#2439</a></li>
<li>Update changelog for v6.0.3 by <a
href="https://github.com/yaananth"><code>@​yaananth</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2446">actions/checkout#2446</a></li>
</ul>
<h2>New Contributors</h2>
<ul>
<li><a href="https://github.com/yaananth"><code>@​yaananth</code></a>
made their first contribution in <a
href="https://redirect.github.com/actions/checkout/pull/2414">actions/checkout#2414</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/actions/checkout/compare/v6...v6.0.3">https://github.com/actions/checkout/compare/v6...v6.0.3</a></p>
<h2>v6.0.2</h2>
<h2>What's Changed</h2>
<ul>
<li>Add orchestration_id to git user-agent when ACTIONS_ORCHESTRATION_ID
is set by <a
href="https://github.com/TingluoHuang"><code>@​TingluoHuang</code></a>
in <a
href="https://redirect.github.com/actions/checkout/pull/2355">actions/checkout#2355</a></li>
<li>Fix tag handling: preserve annotations and explicit fetch-tags by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2356">actions/checkout#2356</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/actions/checkout/compare/v6.0.1...v6.0.2">https://github.com/actions/checkout/compare/v6.0.1...v6.0.2</a></p>
<h2>v6.0.1</h2>
<h2>What's Changed</h2>
<ul>
<li>Update all references from v5 and v4 to v6 by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2314">actions/checkout#2314</a></li>
<li>Add worktree support for persist-credentials includeIf by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2327">actions/checkout#2327</a></li>
<li>Clarify v6 README by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2328">actions/checkout#2328</a></li>
</ul>
<p><strong>Full Changelog</strong>: <a
href="https://github.com/actions/checkout/compare/v6...v6.0.1">https://github.com/actions/checkout/compare/v6...v6.0.1</a></p>
</blockquote>
</details>
<details>
<summary>Changelog</summary>
<p><em>Sourced from <a
href="https://github.com/actions/checkout/blob/main/CHANGELOG.md">actions/checkout's
changelog</a>.</em></p>
<blockquote>
<h1>Changelog</h1>
<h2>v7.0.0</h2>
<ul>
<li>Block checking out fork PR for pull_request_target and workflow_run
by <a href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2454">actions/checkout#2454</a></li>
<li>Bump actions/publish-immutable-action from 0.0.3 to 0.0.4 in the
minor-actions-dependencies group across 1 directory by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2458">actions/checkout#2458</a></li>
<li>Bump flatted from 3.3.1 to 3.4.2 by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2460">actions/checkout#2460</a></li>
<li>Bump js-yaml from 4.1.0 to 4.2.0 by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2461">actions/checkout#2461</a></li>
<li>Bump <code>@​actions/core</code> and
<code>@​actions/tool-cache</code> and Remove uuid by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2459">actions/checkout#2459</a></li>
<li>upgrade module to esm and update dependencies by <a
href="https://github.com/aiqiaoy"><code>@​aiqiaoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2463">actions/checkout#2463</a></li>
<li>Bump the minor-npm-dependencies group across 1 directory with 3
updates by <a
href="https://github.com/dependabot"><code>@​dependabot</code></a>[bot]
in <a
href="https://redirect.github.com/actions/checkout/pull/2462">actions/checkout#2462</a></li>
</ul>
<h2>v6.0.3</h2>
<ul>
<li>Fix checkout init for SHA-256 repositories by <a
href="https://github.com/yaananth"><code>@​yaananth</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2439">actions/checkout#2439</a></li>
<li>fix: expand merge commit SHA regex and add SHA-256 test cases by <a
href="https://github.com/yaananth"><code>@​yaananth</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2414">actions/checkout#2414</a></li>
</ul>
<h2>v6.0.2</h2>
<ul>
<li>Fix tag handling: preserve annotations and explicit fetch-tags by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2356">actions/checkout#2356</a></li>
</ul>
<h2>v6.0.1</h2>
<ul>
<li>Add worktree support for persist-credentials includeIf by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2327">actions/checkout#2327</a></li>
</ul>
<h2>v6.0.0</h2>
<ul>
<li>Persist creds to a separate file by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2286">actions/checkout#2286</a></li>
<li>Update README to include Node.js 24 support details and requirements
by <a href="https://github.com/salmanmkc"><code>@​salmanmkc</code></a>
in <a
href="https://redirect.github.com/actions/checkout/pull/2248">actions/checkout#2248</a></li>
</ul>
<h2>v5.0.1</h2>
<ul>
<li>Port v6 cleanup to v5 by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2301">actions/checkout#2301</a></li>
</ul>
<h2>v5.0.0</h2>
<ul>
<li>Update actions checkout to use node 24 by <a
href="https://github.com/salmanmkc"><code>@​salmanmkc</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2226">actions/checkout#2226</a></li>
</ul>
<h2>v4.3.1</h2>
<ul>
<li>Port v6 cleanup to v4 by <a
href="https://github.com/ericsciple"><code>@​ericsciple</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2305">actions/checkout#2305</a></li>
</ul>
<h2>v4.3.0</h2>
<ul>
<li>docs: update README.md by <a
href="https://github.com/motss"><code>@​motss</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/1971">actions/checkout#1971</a></li>
<li>Add internal repos for checking out multiple repositories by <a
href="https://github.com/mouismail"><code>@​mouismail</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/1977">actions/checkout#1977</a></li>
<li>Documentation update - add recommended permissions to Readme by <a
href="https://github.com/benwells"><code>@​benwells</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2043">actions/checkout#2043</a></li>
<li>Adjust positioning of user email note and permissions heading by <a
href="https://github.com/joshmgross"><code>@​joshmgross</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2044">actions/checkout#2044</a></li>
<li>Update README.md by <a
href="https://github.com/nebuk89"><code>@​nebuk89</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2194">actions/checkout#2194</a></li>
<li>Update CODEOWNERS for actions by <a
href="https://github.com/TingluoHuang"><code>@​TingluoHuang</code></a>
in <a
href="https://redirect.github.com/actions/checkout/pull/2224">actions/checkout#2224</a></li>
<li>Update package dependencies by <a
href="https://github.com/salmanmkc"><code>@​salmanmkc</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/2236">actions/checkout#2236</a></li>
</ul>
<h2>v4.2.2</h2>
<ul>
<li><code>url-helper.ts</code> now leverages well-known environment
variables by <a href="https://github.com/jww3"><code>@​jww3</code></a>
in <a
href="https://redirect.github.com/actions/checkout/pull/1941">actions/checkout#1941</a></li>
<li>Expand unit test coverage for <code>isGhes</code> by <a
href="https://github.com/jww3"><code>@​jww3</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/1946">actions/checkout#1946</a></li>
</ul>
<h2>v4.2.1</h2>
<ul>
<li>Check out other refs/* by commit if provided, fall back to ref by <a
href="https://github.com/orhantoy"><code>@​orhantoy</code></a> in <a
href="https://redirect.github.com/actions/checkout/pull/1924">actions/checkout#1924</a></li>
</ul>
<!-- raw HTML omitted -->
</blockquote>
<p>... (truncated)</p>
</details>
<details>
<summary>Commits</summary>
<ul>
<li><a
href="https://github.com/actions/checkout/commit/9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0"><code>9c091bb</code></a>
update error wording (<a
href="https://redirect.github.com/actions/checkout/issues/2467">#2467</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/1044a6dea927916f2c38ba5aeffbc0a847b1221a"><code>1044a6d</code></a>
getting ready for checkout v7 release (<a
href="https://redirect.github.com/actions/checkout/issues/2464">#2464</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/f0282184c7ce73ab54c7e4ab5a617122602e575f"><code>f028218</code></a>
Bump the minor-npm-dependencies group across 1 directory with 3 updates
(<a
href="https://redirect.github.com/actions/checkout/issues/2462">#2462</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/d914b262ffc244530a203ab40decab34c3abf34d"><code>d914b26</code></a>
upgrade module to esm and update dependencies (<a
href="https://redirect.github.com/actions/checkout/issues/2463">#2463</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/537c7ef99cef6e5ddb5e7ff5d16d14510503801d"><code>537c7ef</code></a>
Bump <code>@​actions/core</code> and <code>@​actions/tool-cache</code>
and Remove uuid (<a
href="https://redirect.github.com/actions/checkout/issues/2459">#2459</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/130a169078a413d3a5246a393625e8e742f387f6"><code>130a169</code></a>
Bump js-yaml from 4.1.0 to 4.2.0 (<a
href="https://redirect.github.com/actions/checkout/issues/2461">#2461</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/7d09575332117a40b46e5e020664df234cd416f3"><code>7d09575</code></a>
Bump flatted from 3.3.1 to 3.4.2 (<a
href="https://redirect.github.com/actions/checkout/issues/2460">#2460</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/0f9f3aa320cb53abeb534aeb54048075d9697a0e"><code>0f9f3aa</code></a>
Bump actions/publish-immutable-action (<a
href="https://redirect.github.com/actions/checkout/issues/2458">#2458</a>)</li>
<li><a
href="https://github.com/actions/checkout/commit/f9e715a95fcd1f9253f77dd28f11e88d2d6460c7"><code>f9e715a</code></a>
block checking out fork pr for pull_request_target and workflow_run (<a
href="https://redirect.github.com/actions/checkout/issues/2454">#2454</a>)</li>
<li>See full diff in <a
href="https://github.com/actions/checkout/compare/v6...v7">compare
view</a></li>
</ul>
</details>
<br />


[![Dependabot compatibility
score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=actions/checkout&package-manager=github_actions&previous-version=6&new-version=7)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores)

Dependabot will resolve any conflicts with this PR as long as you don't
alter it yourself. You can also trigger a rebase manually by commenting
`@dependabot rebase`.

[//]: # (dependabot-automerge-start)
[//]: # (dependabot-automerge-end)

---

<details>
<summary>Dependabot commands and options</summary>
<br />

You can trigger Dependabot actions by commenting on this PR:
- `@dependabot rebase` will rebase this PR
- `@dependabot recreate` will recreate this PR, overwriting any edits
that have been made to it
- `@dependabot show <dependency name> ignore conditions` will show all
of the ignore conditions of the specified dependency
- `@dependabot ignore this major version` will close this PR and stop
Dependabot creating any more for this major version (unless you reopen
the PR or upgrade to it yourself)
- `@dependabot ignore this minor version` will close this PR and stop
Dependabot creating any more for this minor version (unless you reopen
the PR or upgrade to it yourself)
- `@dependabot ignore this dependency` will close this PR and stop
Dependabot creating any more for this dependency (unless you reopen the
PR or upgrade to it yourself)


</details>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Johann Kempter <code@binflip.rs>
Reconciles the squash-merge divergence from v0.8.2 (#223), which was
squash-merged to master but never merged back into develop.

The divergence was bookkeeping only: develop already contained the
v0.8.2 content via a8408cb (the pre-squash original of the fat exception
header fix) and already carried the [0.8.2] CHANGELOG section. The
resulting tree is identical to pre-merge develop.

Conflicts in CHANGELOG.md, Cargo.lock, dotscope/Cargo.toml and
dotscope-cli/Cargo.toml were all release metadata and resolved in
develop's favour, which is strictly newer (0.8.3 > 0.8.2).
Re-scanning the whole call graph once per rescue round is O(depth x edges);
collapsing it to a type-level graph once and draining a worklist is O(V+E)
and needs no convergence loop. Also seeds CustomAttribute constructor types
as reachability roots rather than filtering them afterwards, so the types
those constructors call stay alive too, and sorts the result for a
reproducible deletion order.
Deleting an enclosing type cascades to its nested types through
expand_type_tokens, so a nested type that live code still calls was being
dropped along with a parent that only looked dead. Liveness now propagates
from a nested type to the type that encloses it.
BinFlip added 13 commits July 26, 2026 20:02
ECMA-335 III.4.29 defines stobj over any typeTok and makes it equivalent to
stind.ref when that type is a reference type, which is what 'stobj !!T'
compiles to once T is instantiated with one. The handler rejected anything
outside a value-type whitelist that also omitted U4, Boolean, Char and the
remaining integer widths.
ldelem and stelem both go through extract_array_index, which accepts every
integer width plus boxed indices. ldelema hand-rolled a match on I32 and
NativeInt only, so a native uint index aborted emulation.
ldelema on a value-type array yields a pointer to the element, so a stfld
through it updates one field inside that struct. Falling through to
store_through_pointer replaced the entire element with the field's value
instead. Read-modify-write the element, and route reference-type elements
to the object they point at.
The constant-blob index was matched against I4 alone. Stock ConfuserEx 1.6.0
emits 'T Get<T>(int32)' but other builds emit uint32, and those decryptors
went undetected entirely. The surrounding constraints (static, <Module> or
non-ASCII owner, arity 1, string or !!0 return) carry the selectivity, so
the width does not need pinning.
Two defects kept real constant blobs from decompressing. The sniffer
required the payload to be smaller than its declared output, but LZMA
expands small high-entropy input and the blob is XOR-encrypted before
compression, so a 44-byte blob compresses to 51. And the header was modelled
as 5 property bytes plus a 4-byte size, while builds using the LZMA SDK's
stream API write the standard 13-byte header with an 8-byte size — reading
that as 9 bytes shifts the payload and corrupts the range coder.

Both layouts are now tried and validated against the size each declares. The
size guard is documented as an allocation guard rather than a format rule
and raised to a value no real blob approaches.
A technique builds its cleanup request from detection findings alone, so it
schedules the decryptor, its infrastructure type, the initializer and the
encrypted data for deletion whether or not a single call site was reversed.
When decryption fails the call sites remain and are left pointing at
metadata that no longer exists, which empties the methods holding them.

Removal now requires that nothing still calls the decryptor: a successful
decryption rewrites its call site to the constant, so no remaining callers
is the evidence that it was reversed. Absence of recorded failures is not,
since a decryptor that was never exercised has none either.
reactor_virtualization is not devirtualized by any technique, so the VM
interpreter and its handler types stay reachable through the stubs left in
the virtualized methods. Non-transitive reachability read that cluster as
isolated infrastructure and cut the assembly from 854 methods to 45.
Pushing to master triggered the release workflow, guarded only by a check
that the version in Cargo.toml had no release yet. That made 'will this
publish?' something to reason about rather than read, and it is the reason
merging anywhere near master felt unsafe.

Publishing is now driven by publishing a GitHub release. The version comes
from the release tag and is checked against Cargo.toml, so a mistyped tag
fails before anything ships rather than releasing under the wrong version.
Creating the release and writing its notes is a manual step; the workflow
attaches the CLI binaries and publishes the crate.
Work happens on master now, so the three places that named develop would
have gone stale. Dependabot is the one that fails silently: with
target-branch pointing at a branch that no longer exists it stops opening
pull requests altogether rather than reporting an error, so the pins are
removed and updates target the default branch.
Bumps both workspace crates, dates the changelog section, and brings the
README install snippet up to date — it still advertised 0.8.2, having been
missed when 0.8.3 shipped.
The version gate only inspected dotscope/Cargo.toml, so the CLI could ship
attached to a release as dotscope-v0.8.4-*.zip while reporting 0.8.3 for
itself. Both manifests are checked, and both mismatches are reported before
failing rather than stopping at the first.
master and develop diverged because each release was squash-merged into
master, creating a commit develop never saw. The content never diverged:
master's tree is identical to develop's at e2d68c8, so this merge records
the shared ancestry without changing a single file.

Retires the divergence ahead of develop being removed.
@BinFlip
BinFlip enabled auto-merge (rebase) July 27, 2026 04:08
@BinFlip
BinFlip disabled auto-merge July 27, 2026 04:08
@BinFlip
BinFlip merged commit 1cd43e0 into master Jul 27, 2026
8 checks passed
@BinFlip
BinFlip deleted the develop branch July 27, 2026 04:21
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant