Skip to content

exploreState rejects every valid numeric state #907

Description

@MicroMilo

Summary

Every repository-facing contract declares state numeric, including the native tracePcIndir boundary, but exploreState returns unless state is a string. Thus all valid calls are discarded while invalid strings reach the numeric native API.

Impact: Calls such as the maze example's jazzer.exploreState(hash(x, y), 0) never submit state feedback to libFuzzer, so the documented feature cannot guide exploration. Untyped calls with a string do reach a native function declared to require a number.

Code path

Checked against current main at commit 4c14e1bf63d82475ea057d6208e6f2eac87fa680.

  • packages/fuzzer/trace.ts:198-218
  • packages/fuzzer/addon.ts:56-62
  • packages/bug-detectors/DEVELOPMENT.md:113-118
  • examples/maze/fuzz.js:57-60

Steps to reproduce

Validation level: current HEAD supplemental dynamic witness reproduced.

node -e 'const fs=require("fs"); const source=fs.readFileSync("packages/fuzzer/trace.ts","utf8"); const match=source.match(/export function exploreState\(state: number, id: number\) \{[\s\S]*?\n\}/); if(!match) throw new Error("function not found"); const js=match[0].replace("export ","").replace("state: number","state").replace("id: number","id"); const calls=[]; const fn=Function("tracer",js+"; return exploreState")({tracePcIndir:(...args)=>calls.push(args)}); fn(7,11); console.log(JSON.stringify({input:[7,11],tracePcIndirCalls:calls}));'

Observed output:

{"input":[7,11],"tracePcIndirCalls":[]}

Neighboring control:

node -e 'const fs=require("fs"); const source=fs.readFileSync("packages/fuzzer/trace.ts","utf8"); const match=source.match(/export function exploreState\(state: number, id: number\) \{[\s\S]*?\n\}/); if(!match) throw new Error("function not found"); const js=match[0].replace("export ","").replace("state: number","state").replace("id: number","id"); const calls=[]; const fn=Function("tracer",js+"; return exploreState")({tracePcIndir:(...args)=>calls.push(args)}); fn("7",11); console.log(JSON.stringify({input:["7",11],tracePcIndirCalls:calls}));'

Control output:

{"input":["7",11],"tracePcIndirCalls":[[11,"7"]]}

Expected behavior

The documented/source-grounded contract should hold without the drift described above.

Actual behavior

exploreState rejects every contract-conforming numeric state while allowing strings through to the numeric tracer boundary.

Existing coverage

I checked the current issue and PR lists for overlapping titles/root-cause keywords before filing this. I did not find an item covering this same root cause.

Suggested fix

Correct exploreState's runtime guard to require a numeric state and numeric identifier.

Suggested tests

  • Add a regression test for the reproduction above.
  • Add a neighboring control assertion so the intended non-bug path remains covered.

Submitted with Codex.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions