Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 7 additions & 1 deletion conformance/.clusterfuzzlite/fuzz_receipt.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
from trace_tests.inclusion import (
InclusionError,
canonical_claim_bytes,
parse_entry,
parse_proof,
parse_receipt,
verify_inclusion,
)
Expand Down Expand Up @@ -121,8 +123,12 @@ def TestOneInput(data: bytes) -> None:
findings = tr_anc.check(claim, receipt=receipt, entry=_ENTRY)
if any(f.code == "TR-ANC-002" and f.passed() for f in findings):
assert claim is _CLAIMS[_TARGET], f"inclusion proven for the wrong claim: {receipt!r}"
root = parse_receipt(receipt)[3]
index, path, _, _ = parse_proof(receipt)
root, count, _, _ = parse_entry(_ENTRY)
assert root == _ROOT, f"inclusion proven under another root: {receipt!r}"
assert verify_inclusion(claim, index, path, count, root), (
f"inclusion not reproduced against the supplied entry: {receipt!r}"
)


def main() -> None:
Expand Down
58 changes: 58 additions & 0 deletions conformance/tests/test_fuzz_receipt.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
"""Deterministic receipt-harness regressions without requiring Atheris."""

import contextlib
import json
import runpy
import sys
import types
from pathlib import Path

import pytest


@pytest.fixture
def harness(monkeypatch):
# Exercise the real fuzz callback's raw-JSON branch; only instrumentation
# and byte selection are replaced, not the parser, verifier, or assertions.
class DataProvider:
def __init__(self, data):
self.data = data

def ConsumeIntInRange(self, lower, upper):
return 3 # The genuine fixture's target claim.

def ConsumeBool(self):
return False

def remaining_bytes(self):
return len(self.data)

def ConsumeBytes(self, length):
return self.data[:length]

stub = types.ModuleType("atheris")
stub.instrument_imports = contextlib.nullcontext
stub.FuzzedDataProvider = DataProvider
monkeypatch.setitem(sys.modules, "atheris", stub)
path = Path(__file__).parents[1] / ".clusterfuzzlite" / "fuzz_receipt.py"
return runpy.run_path(str(path))


@pytest.mark.parametrize(
"omitted",
[(), ("leaf_count",), ("merkle_root",), ("leaf_count", "merkle_root")],
)
def test_pass_oracle_accepts_entry_backed_proofs(harness, omitted):
receipt = {k: v for k, v in harness["_RECEIPT"].items() if k not in omitted}
claim = harness["_CLAIMS"][harness["_TARGET"]]
findings = harness["tr_anc"].check(claim, receipt=receipt, entry=harness["_ENTRY"])
assert any(f.code == "TR-ANC-002" and f.passed() for f in findings)
harness["TestOneInput"](json.dumps(receipt).encode())


def test_pass_oracle_independently_replays_proof(harness, monkeypatch):
receipt = {"leaf_index": harness["_TARGET"], "audit_path": []}
fake_pass = types.SimpleNamespace(code="TR-ANC-002", passed=lambda: True)
monkeypatch.setattr(harness["tr_anc"], "check", lambda *a, **kw: [fake_pass])
with pytest.raises(AssertionError, match="not reproduced against the supplied entry"):
harness["TestOneInput"](json.dumps(receipt).encode())
Loading