2026-10-14
This monthOpenvm pairing cve 2026 46669 missing subfield check
Produced by the ZK Security research pipeline. Published only after the automated quality gate. The gate is described in the editorial policy.
On 2026-05-15 OpenVM published advisory [GHSA-76mq-v757-53gr](https://github.com/openvm-org/openvm/security/advisories/GHSA-76mq-v757-53gr) (CVE-2026-46669), rated critical. It covers , the Rust guest…
On 2026-05-15 OpenVM published advisory GHSA-76mq-v757-53gr (CVE-2026-46669), rated critical. It covers openvm-pairing, the Rust guest library that zkVM programs call to check pairing equations on BN254 and BLS12-381.
The pairing-check routine relied on an optimization from the paper "On Proving Pairings" by Andrija Novakovic and Liam Eagen (eprint 2024/640). It left out a condition that the optimization depends on. As a result, a dishonest prover could "make any pairing check pass" (advisory). Versions below 1.6.0 are affected; 1.6.0 is patched.
zkSecurity's account appeared on 2026-07-17 (blog). The finding came from zkao, the company's AI auditing tool. Its staff then validated the bug and handled disclosure. The advisory credits StefanosChaliasos as reporter.
Background: checking a pairing product cheaply
Groth16, KZG and BLS verifiers all ask whether a product of pairings, ∏ e(P_i, Q_i), equals 1. Computing a pairing has two steps (blog):
- Miller loops. Their combined output
flies inF_{p^12}*. That output is unique only up to multiplication by anr-th power. - Final exponentiation. Raising
ftoh = (p^12 − 1)/rremoves that ambiguity. The real check isf^h = 1.
Computing f^h inside a circuit is expensive. Instead, the prover supplies a witness c computed outside the circuit, and the circuit checks a cheaper relation.
OpenVM uses the residue-witness form from Novakovic and Eagen: f · u = c^λ with u^(d^i) = 1. Here λ is a curve-specific multiple of r, and u is a scaling factor that the prover also supplies. The code names it u for BN254 and s for BLS12-381 (blog).
The root-of-unity condition on u is part of Theorem 3 of the paper. The advisory notes that, for BN254 and BLS12-381, this condition can be replaced by a cheaper one: show that u lies in a proper subfield of F_{p^12}, namely F_{p^6}. The subfield membership check itself cannot be dropped (GHSA).
OpenVM stores an F_{p^12} element as six F_{p^2} coefficients. Membership in F_{p^6} means coefficients c[1], c[3] and c[5] are all zero, so the test costs only three equality checks (blog; fix commit).
The bug
The vulnerable function is try_honest_pairing_check, in guest-libs/pairing/src/bn254/pairing.rs and guest-libs/pairing/src/bls12_381/pairing.rs (GHSA; pre-fix source). It took the hint (c, u) and returned None only if c was zero. Nothing checked that u was in F_{p^6}.
Without that check, the forgery takes one step for any Miller-loop output f, including one from a false equation. The advisory's PoC sets c = 1 and u = f^{-1}, or s = f^{-1} on BLS12-381. Then c^λ = 1 = f · f^{-1}, and the relation holds (GHSA). zkSecurity points out that f^{-1} is normally a full F_{p^12} element, which is why the subfield check would have caught it.
The routine reported success, so control never reached OpenVM's slower fallback path, the one that performs the full final exponentiation (blog).
The advisory compares this with gnark. Its emulated BN254 and BLS12-381 pairing code checks that the scaling factor lies in Fp6 (GHSA).
Impact
The advisory says: "All users of the openvm-pairing guest library are affected."
zkSecurity is explicit that this is not a soundness bug in OpenVM's proving system. It affects guest programs that call the library (blog). For those programs, the blog lists the consequences of forging an arbitrary pairing check:
- BLS12-381: forged KZG opening proofs.
- BN254: broken Groth16 verifiers and BLS signature checks.
- EVM emulation: guests that emulate the Ethereum
ecPairingprecompile (address0x08) through this check would return forged results.
zkao rated the bug Critical, and OpenVM's maintainers agreed. zkSecurity states: "As far as we know, all partners building on OpenVM have since upgraded" to 1.6.0 (blog).
Fix
The fix is commit a720e2c, "fix(openvm-pairing): add missing Fp6 subfield checks for hinted scalar factor (#112)". It adds a loop over coefficient indices [1, 3, 5] in both curve implementations and returns None if any of those coefficients is non-zero. It also adds host tests confirming that a hint of f^{-1} fails the check.
The commit message makes two further points. Having the hint return Fp6 directly would have been more type-safe, but needed a larger change. And it is "hard to prank the hint" in guest tests, so the tests run on the host.
The fix shipped in v1.6.0, a security release that tells "all users on v1.5.0 or earlier" to upgrade. The same release fixes three other advisories: SHA-256/Keccak under-constraint, native recursion verifier constraints, and system AIR boolean assertions. It also picks up an upstream Plonky3 transcript fix.
What it means for teams shipping circuits
- Upgrade. Any guest program built against
openvm-pairing< 1.6.0 that checks Groth16, KZG, BLS orecPairingshould be rebuilt on 1.6.0 (GHSA). - Treat every hint as hostile. The
c ≠ 0check shows the authors were already guarding the hint. The gap was a second hinted value whose constraint came from a side condition in a theorem, not the main equation (GHSA). - Diff against a reference implementation. gnark's pairing code already had the subfield check, and the fix's code comments cite it directly (fix commit).
Timeline
| Date (UTC) | Event |
|---|---|
| ~March 2026 | zkSecurity scans OpenVM. The blog says "four months ago" in a post dated 2026-07-17 |
| 2026-03-17 | Fix commit a720e2c authored |
| 2026-05-15 17:30 | Fix commit lands in openvm-org/openvm (committer date) |
| 2026-05-15 18:42 | OpenVM v1.6.0 released |
| 2026-05-15 18:52 | GHSA-76mq-v757-53gr / CVE-2026-46669 published |
| 2026-07-17 | zkSecurity publishes its write-up |
Sources
- https://github.com/openvm-org/openvm/security/advisories/GHSA-76mq-v757-53gr
- https://github.com/openvm-org/openvm/commit/a720e2c7ba529becd101dbad24c879bd5c1257f4
- https://github.com/openvm-org/openvm/releases/tag/v1.6.0
- https://blog.zksecurity.xyz/posts/openvm-bugs/
- https://eprint.iacr.org/2024/640
- https://github.com/openvm-org/openvm/blob/69373ff1d06b613025fe4e7a02d735a1609412c4/guest-libs/pairing/src/bn254/pairing.rs
Related guides: under-constrained circuits, auditing circom, choosing a proving system, trusted setup risk, the checklist.