This repo is dedicated to implementing a simplified version of the Zcash protocol. More precisely, we are interested in the spend(sprout) protocol and how zkps were used. To do this, just start with a few basic circuits to defuse the development flow, and become more familiar with the Circom language.
Install snarkjs, circom, and circomlib
1- Develop circuits in circom
2- Compile circom cubicEq.circom to get r1cs and witness generator as follows: circom "circom file" --r1cs --wasm -o ../build/... --r1cs outputs the constraints in r1cs format in binary format --wasm Compiles the circuit to wasm
In this case, we create an R1CS file, along with a folder with the files generate_witness.js, cubicEq.wasm and witness_calculator.j. The R1CS format is used to represent all the wires in the circuit, and so that they can be checked for the proof — this is known as a Quadratic Arithmetic Program (QAP).
3- Computing our witness to create the actual proofs. We need to create a file named input.json containing the inputs of the circuit written in the standard json format. node generate_witness.js poseidonWitness.wasm input.json witness.wtns
4- Generate Trusted setup (CrS) including proof key and verification key. We are going to use the Groth16 zk-SNARK protocol. To use this protocol, you will need to generate a trusted setup. Groth16 requires a per circuit trusted setup. In more detail, the trusted setup consists of 2 parts:
Phase 1 called the powers of tau, which is independent of the circuit. The phase 2, which depends on the circuit.
5- Generate proof: takes circuit in c1rs format, proofing key and witness, and then creates a proof
snarkjs groth16 prove cubicEq_0001.zkey witness.wtns proof.json public1.json
6- verification: takes circuit in r1cs format, proof and public inputs, and verification key and outputs the verification result.
7- Also it is possible to create a smart contract verifier.sol and deploy it on the blockchain. Then we can send the proof and see the results.