ReviewOS

zig-utils/zig-js

Wasm: over-long LEB128 encodings are accepted instead of rejected as malformed

#877
Closed glennmichael123 opened this 11 days ago ·
11 days ago

Two commands in the pinned wg-1.0 corpus expect a WebAssembly.CompileError and instead get a module that compiles successfully. This is an acceptance gap, not a diagnostic difference: we admit a module the specification says is malformed.

zig build wasm-spec -Doptimize=ReleaseFast
binary-leb128.wast:403 [assert_malformed]
  expected WebAssembly.CompileError containing "integer representation too long", module compiled
binary-leb128.wast:460 [assert_malformed]
  expected WebAssembly.CompileError containing "integer representation too long", module compiled

Both cases encode an integer with more LEB128 continuation bytes than the target width permits. The decoder currently consumes the redundant bytes and proceeds; the spec requires rejecting the encoding itself, independently of whether the decoded value is in range.

Distinct from the diagnostic-wording failures in the same file (lines 729/748/842/861), which do reject and only differ in message text — those are tracked separately.

Found because the full corpus is not gated in CI; see the umbrella issue for why these went unnoticed on a green main.

11 days ago

Umbrella / why this went unnoticed on a green main: #880. Sibling failures in the same corpus run: #878 (diagnostic wording), #879 (behavioral).

11 days ago

Root cause was narrower than this issue assumed, and shared with #878: readMemArg decoded every offset with readU64Leb, so a six-byte LEB128 — over-long for a u32, in range for a u64 — decoded cleanly and the module compiled. Without the memory64 feature no memory can be 64-bit, so the offset is now read as the u32 field it is, and the over-long encoding is malformed at decode with the spec's own wording.

Corpus (Debug): 18,790 pass / 1 fail, from 18,778 / 13. New regression test wasm.decode memory32 memarg offsets reject u32-overlong encodings covers both malformed shapes and asserts the same bytes still decode under memory64.

Sign in to comment on this issue.