Circuits Overview
ZeroStyl ships three halo2 circuits, each implementing a distinct privacy primitive. All circuits use the KZG polynomial commitment scheme over the BN254 curve (PSE halo2 fork) with Poseidon commitments, aligning with the BN254 precompiles on Arbitrum.
Included Circuits
| Circuit | Privacy Primitive | Public Inputs |
|---|---|---|
state_mask | Bounded range + threshold comparison over committed state | commitment, threshold |
tx_privacy | Private token transfer with Merkle membership | commitment_old, commitment_new, merkle_root, nullifier |
private_vote | Anonymous on-chain governance vote | balance_commitment, threshold, vote_commitment |
Each circuit is selected by name when invoking zerostyl-debug or zerostyl-prove:
zerostyl-debug debug --circuit state_mask --witnesses witness.json
zerostyl-debug debug --circuit tx_privacy --witnesses witness.json
zerostyl-debug debug --circuit private_vote --witnesses witness.json
To see the exact witness a circuit expects, plus a copy-pastable template, run:
zerostyl-prove info <circuit>
Witness file format
A witness is a flat JSON object mapping each field name to a value. There is no nested
private_inputs/public_inputs wrapper — the field names come straight from the circuit's schema
(zerostyl-prove info <circuit> lists them):
{
"state_value": "42",
"nonce": "7",
"collateral_ratio": "200",
"hidden_balance": "5000",
"threshold": "1000"
}
Value encoding
-
Scalars are decimal strings (or
0x-prefixed hex for field elements), avoiding JSON number-precision loss on 254-bit field elements. -
Arrays (such as Merkle paths) are JSON arrays of strings:
{"merkle_siblings": ["0", "0", "0"],"merkle_indices": ["0", "1", "0"]}
Values are elements of the BN254 scalar field; a value at or above the field modulus is rejected by the witness parser.
Workflow
- Write the witness — consult the per-circuit page (or
zerostyl-prove info <circuit>). - Validate —
zerostyl-debug debug --circuit <name> --witnesses witness.json. - Prove —
zerostyl-prove generate --circuit <name> --witnesses witness.json --output proof.bin. - Verify —
zerostyl-prove verify --circuit <name> --proof proof.bin --inputs public_inputs.json.
See the Quick Start for the full worked example.
Proving system and setup
All three circuits prove with halo2 using a KZG commitment on BN254. KZG requires a structured reference string (SRS).
ZeroStyl derives its SRS deterministically from a fixed seed (DEV_SRS_SEED) — a reproducible
development setup, not a secure Powers-of-Tau ceremony. A production deployment must replace it
with a real ceremony. See the zk-STARKs feasibility study
for the trade-offs, and treat all circuits as unaudited pending independent review.