Skip to content

zk step provers (risc0 + zisk)#353

Closed
mpernambuco wants to merge 4 commits intomainfrom
perna/risc0-tweaks
Closed

zk step provers (risc0 + zisk)#353
mpernambuco wants to merge 4 commits intomainfrom
perna/risc0-tweaks

Conversation

@mpernambuco
Copy link
Copy Markdown
Collaborator

@mpernambuco mpernambuco commented Feb 6, 2026

  • ZK step verification pipeline, from proof generation through on-chain Groth16
    verification.
  • Initial ZisK prover integration.

Verification layers

Each layer builds on the one below it. The commands show the full
pipeline from recording a step to verifying it on Ethereum.

The same three values — hash_before, mcycle_count, hash_after — flow
through every layer:

Layer 1 — Replay (emulator)

Record a step log. The emulator automatically replays and verifies
the step log before returning:

cartesi-machine --log-step=mcycle_count,tep.log

The step log embeds hash_before, mcycle_count, and hash_after in its
header. Standalone verification is available via the library API
(machine:verify_step).

Layer 2 — ZK Proof (RISC0 STARK)

The replay runs inside RISC Zero's zkVM, producing a receipt:

cartesi-risc0-cli prove hash_before step.log mcycle_count hash_after receipt.bin
cartesi-risc0-cli verify receipt.bin hash_before mcycle_count hash_after

Layer 3 — Compact Proof (Groth16)

The STARK receipt is compressed into a 256-byte Groth16 seal and a
96-byte ABI-encoded journal, small enough to verify on-chain:

cartesi-risc0-cli prove-groth16 hash_before step.log mcycle_count hash_after seal.bin journal.bin
cartesi-risc0-cli verify-groth16 seal.bin journal.bin hash_before mcycle_count hash_after

Layer 4 — On-chain (Solidity)

CartesiStepVerifier receives the Groth16 seal and journal, verifies
the proof via the RISC Zero Verifier Router, and decodes the step
transition values:

contract CartesiStepVerifier {
    IRiscZeroVerifier public immutable verifier;

    function verifyStep(bytes calldata seal, bytes calldata journal)
        external view
        returns (bytes32 rootHashBefore, uint64 mcycleCount, bytes32 rootHashAfter)
    {
        verifier.verify(seal, ImageID.CARTESI_STEP_VERIFIER_ID, sha256(journal));
        (rootHashBefore, mcycleCount, rootHashAfter) = abi.decode(journal, (bytes32, uint64, bytes32));
    }
}

The ImageID constant is auto-generated from the reproducible guest
build (make -C risc0/solidity image-id). The Foundry test deploys
this contract against a Sepolia fork and exercises valid proofs,
tampered journals, and wrong Image IDs.

Emulator changes

  • Step log now embeds a 72-byte header (root_hash_before, mcycle_count,
    root_hash_after) before the page data and sibling hashes

RISC0

  • Upgraded to risc0-zkvm v3 (3.0.5)
  • Groth16 proving and verification (256-byte seal + 96-byte journal)
  • Reproducible guest builds via Docker (canonical Image ID across platforms)
  • CUDA GPU acceleration support (compile-time feature flag)
  • CLI tool (cartesi-risc0-cli) for prove, verify, Groth16, and artifact export
  • Foundry integration test against the RISC Zero Verifier Router on Sepolia
  • Boundless remote proving workflow (decentralized proving marketplace)
  • Runtime guest ELF override for non-Docker environments

RISC0 GPU Benchmark

STARK proving on an RTX 5090 (32 GB VRAM), RISC0 v3.0.5 with CUDA.

Step logs attached step-logs-benchmark.zip

To reproduce:

  mcycles   prove     verify   step log   receipt
  -------   --------  -------  --------   -------
        1     3.4 s    0.2 s      19 KB    789 KB
      100     5.2 s    0.2 s      35 KB    1.1 MB
  100,000   1m 40 s    2.7 s     153 KB     27 MB
1,000,000  14m 26 s   22.9 s     161 KB    230 MB

  # Build host with CUDA (requires rzup toolchain + NVIDIA GPU)
  make -C risc0 RISC0_FEATURES=cuda

  # If the build machine cannot run Docker (e.g. GPU containers),
  # build the guest elsewhere and pass it at runtime:
  #   make -C risc0 export-artifacts   (on a Docker-capable machine)
  #   cartesi-risc0-cli --guest-elf risc0/artifacts/cartesi-risc0-guest-step-prover.bin ...

  # Prove
  cartesi-risc0-cli prove \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    step-1.log 1 \
    f32e9c3d21f00fe5bcd85d381890568bc83dfedd9089153428722b426c98b01a \
    receipt-1.bin

  cartesi-risc0-cli prove \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    step-100.log 100 \
    9dd5dc81f0d49a8b5348c55b003fed5ca9fae35c7f88541ce93bf70280a3865e \
    receipt-100.bin

  cartesi-risc0-cli prove \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    step-100000.log 100000 \
    6dd4c569985af96b2bdfdefd614d046889fffe393593b503c9cae0a4b5ef6272 \
    receipt-100000.bin

  cartesi-risc0-cli prove \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    step-1000000.log 1000000 \
    b74578832e9b4168c790e59eab95549bea9c8a845cba5f7088e63fd92d6842a3 \
    receipt-1000000.bin

  # Verify
  cartesi-risc0-cli verify receipt-1.bin \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    1 \
    f32e9c3d21f00fe5bcd85d381890568bc83dfedd9089153428722b426c98b01a

  cartesi-risc0-cli verify receipt-100.bin \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    100 \
    9dd5dc81f0d49a8b5348c55b003fed5ca9fae35c7f88541ce93bf70280a3865e

  cartesi-risc0-cli verify receipt-100000.bin \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    100000 \
    6dd4c569985af96b2bdfdefd614d046889fffe393593b503c9cae0a4b5ef6272

  cartesi-risc0-cli verify receipt-1000000.bin \
    ee41a238926648eec0f6fadf2bf7d749b3554dab08d96930ac602ebf1a5f47d9 \
    1000000 \
    b74578832e9b4168c790e59eab95549bea9c8a845cba5f7088e63fd92d6842a3
	

ZisK

Adds initial ZisK prover integration targeting riscv64ima. The ZisK
guest shares the same C++ replay code and step log format as RISC0.
Building requires LLVM 20 and the ZisK toolchain (cargo-zisk, ziskemu).
All 285 step logs pass the ZisK emulator. Constraint verification and
proof generation are supported via cargo-zisk. On-chain verification
depends on the FFLONK pipeline under development by the ZisK team.

@mpernambuco mpernambuco changed the title Perna/risc0 tweaks zk step provers (risc0 + zisk) Feb 16, 2026
@github-project-automation github-project-automation Bot moved this from Todo to Done in Machine Unit Mar 14, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Archived in project

Development

Successfully merging this pull request may close these issues.

1 participant