Skip to content

fix: tolerate absent/non-bytearray context var in DeserializeContext substitution#879

Open
mwaddip wants to merge 2 commits into
ergoplatform:developfrom
mwaddip:fix/deserialize-context-absent-var
Open

fix: tolerate absent/non-bytearray context var in DeserializeContext substitution#879
mwaddip wants to merge 2 commits into
ergoplatform:developfrom
mwaddip:fix/deserialize-context-absent-var

Conversation

@mwaddip

@mwaddip mwaddip commented Jun 4, 2026

Copy link
Copy Markdown

substitute_deserialize rewrites the whole tree, so a DeserializeContext over a context-extension variable that is absent (or present but not Coll[Byte]) errored even when the node sat on a branch the live reduction never takes.

The JVM Interpreter.substDeserialize returns None in both cases, leaving the node; the sibling DeserializeRegister already does the same. This mirrors them. A leftover node on the live path still errors at eval (DeserializeContext cannot be evaluated), so a live-path deserialize cannot silently pass.

Fixes a full-node sync wedge on testnet block 111,927 (tx 2 input 0: empty proof, empty extension, DeserializeContext(0) on a dead if branch).

Two commits: absent var, then non-bytearray var (full substDeserialize parity).

mwaddip and others added 2 commits June 4, 2026 15:36
…ubstitution

substitute_deserialize rewrites the whole tree, so a DeserializeContext over a context-extension variable absent from the transaction errored (ExtensionKeyNotFound) even when the node sat on a branch the live reduction never takes. This diverges from the JVM: Interpreter.substDeserialize returns None for an absent var, leaving the node in place (everywherebu), and the sibling DeserializeRegister branch here already does the same.

Leave the node unchanged on an absent var, mirroring both. A leftover node on the live path still errors at eval ("DeserializeContext cannot be evaluated"), so this cannot make a live-path deserialize silently pass. Fixes a sync wedge on testnet block 111,927 (tx 2, input 0: empty proof, empty extension, DeserializeContext(0) on a dead `if` branch). The now-unreachable ExtensionKeyNotFound variant is removed.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ntext substitution

Completes parity with Interpreter.substDeserialize, whose inner match returns None not only for an absent var but also for a present var that is not an SByteArray (`case _ => None`), leaving the node in place. Mirror it: a DeserializeContext over a present-but-wrong-typed var on a dead branch no longer sinks reduction. A wrong-typed var on the live path still errors at eval (eval_context_extension_wrong_type), so this stays safe.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
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