Circuit Breaker: The Missing Constraint That Compromised RISC Zero’s zkVM

Danylo Tkachov
Danylo Tkachov
Security Analyst

Intro

Imagine proving to the world that 7 % 5 equals 50,000 — and having that proof verified as mathematically correct. In the realm of zero-knowledge cryptography, where mathematical certainty is sacred, such an impossibility should never happen. Yet for months, this exact scenario was possible within one of the industry’s most promising zkVM platforms.

RISC Zero was founded in 2021 with an ambitious mission: to tackle the biggest challenge facing our industry and potentially our society — the increased centralization and consolidation of not just the applications we use, but the infrastructure we use to build and manage them. The company set out to bring general-purpose computing to the zero-knowledge ecosystem, enabling users to trust programs run anywhere while allowing developers to use the tools they already know and love.

At the heart of this vision lies the RISC Zero zero-knowledge virtual machine (zkVM), a groundbreaking platform that lets developers prove correct execution of arbitrary Rust code. By allowing users to build zero-knowledge applications that leverage existing Rust packages, the RISC Zero zkVM promised to make it quick and easy to build powerful verifiable software applications. In a world where trust is increasingly digital and decentralized, such guarantees of computational integrity represent nothing short of a revolution.

Summary

On May 15, 2025 Christoph “zkCrusher” Hochrainer found that due to a missing constraint in the rv32im circuit, any 3-register RISC-V instruction (including remu and divu) in risc0-zkvm 2.0.0, 2.0.1, and 2.0.2 are vulnerable to an attack by a malicious prover.

Vulnerability Analysis

The rv32im circuit in RISC Zero is responsible for describing all the rules that govern valid RISC-V code execution. These rules are implemented as mathematical constraints that ensure a verifier can be certain the RISC-V code was executed properly. The fundamental assumption in zero-knowledge systems is that the prover is untrusted — they can lie about the execution trace.

What Hochrainer discovered was a critical gap in these constraints. In RISC Zero’s implementation, CPU registers are loaded and stored in a regular region of RAM. For 3-register instructions (operations with two inputs and one output), there was a missing constraint that should have prevented confusion between the two input registers.

The vulnerability allows a malicious prover to confuse rs1 (input register 1) with rs2 (input register 2), essentially treating them as the same value. This affects critical RISC-V instructions including remu (remainder unsigned) and divu(divide unsigned).

The attack works because a lying prover can implement a broken execution trace, but the circuit’s constraint system fails to catch the error. Instead of rejecting invalid statements, the verifier accepts mathematically impossible results as valid proofs, completely breaking the soundness guarantees that make zero-knowledge proofs trustworthy.

Proof of Concept

To reproduce this issue we need to set up the environment. We will use a simple docker setup

Circuit Breaker: The Missing Constraint That Compromised RISC Zero’s zkVM

Clone the repository and move it to the unzipped supplementary folder, so that the hierarchy would be something like this:

Circuit Breaker: The Missing Constraint That Compromised RISC Zero’s zkVM

After building the RISC Zero project, navigate to the my_project directory. Here, you’ll find a minimal example that demonstrates the vulnerability in action.

The project consists of two main components: a guest program, which runs inside the zkVM and performs a simple computation, and a host program, which generates and verifies the zero-knowledge proof.

The guest code is straightforward—it reads two numbers, computes their remainder, and commits the result to the proof’s journal:

Circuit Breaker: The Missing Constraint That Compromised RISC Zero’s zkVM

The host code sets up the inputs, runs the guest code inside the zkVM, and verifies the resulting proof:

Circuit Breaker: The Missing Constraint That Compromised RISC Zero’s zkVM

Now, build and run the host program. Under normal circumstances, you would expect the output to be:

verified that 7 % 5 = 2

and the proof would guarantee that this computation was performed honestly.

However, due to the missing constraint in the RISC Zero rv32im circuit, a malicious prover could generate a proof for any value of c—even if it’s mathematically incorrect. For example, the prover could produce a proof that “verifies” the statement:

verified that 7 % 5 = 0

and the verifier would accept it as valid.

Impact

This vulnerability represents a complete compromise of the zkVM’s soundness — the fundamental property that guarantees a verifier will only accept proofs for true statements. When soundness is violated, the entire cryptographic foundation becomes unreliable.

The practical impact was severe:

  • Any mathematical computation could be proven false while appearing valid
  • Every application built on RISC Zero zkVM versions 2.0.0-2.0.2 was affected
  • On-chain verification could accept fraudulent proofs, potentially causing financial losses
  • No way existed for downstream developers to protect themselves at the application layer

Unlike typical vulnerabilities that affect individual applications, this circuit-level flaw impacted the foundational layer where mathematical certainty should be absolute. The vulnerability affected all RISC Zero zkVM versions 2.0.0 through 2.0.2 during a critical period when the platform was gaining adoption across DeFi protocols and scaling solutions.

Remediation

The fix for the circuit was implemented in zirgen/pull/238, and the update to risc0 was implemented in risc0/pull/3181. Impacted on-chain verifiers have already been disabled via the estop mechanism outlined in the Verifier Management Design.

Acknowledgment

We extend our sincere appreciation to Christoph Hochrainer for their exceptional technical expertise and responsible disclosure of this critical vulnerability. Their sophisticated analysis of circuit constraints not only identified a fundamental flaw but highlighted important considerations for the entire zero-knowledge community. Our gratitude also goes to the RISC Zero team for their exemplary response — implementing immediate fixes, coordinating emergency measures through the estop mechanism, and providing generous bounty compensation. This collaboration between researcher, platform, and project team exemplifies the gold standard for vulnerability disclosure and demonstrates how the security community can work together to strengthen the infrastructure upon which our decentralized future is built.

Share article:

Read more on HackenProof Blog