UNPKG

o1js

Version:

TypeScript framework for zk-SNARKs and zkApps

97 lines (86 loc) 2.33 kB
import { ZkProgram } from '../../proof-system/zkprogram.js'; import { equivalentProvable as equivalent, equivalentAsync, field, fieldWithRng, record, } from '../../testing/equivalent.js'; import { Field } from '../wrapped.js'; import { Gadgets } from '../gadgets/gadgets.js'; import { provable } from '../types/provable-derivers.js'; import { assert } from '../gadgets/common.js'; import { Random } from '../../testing/random.js'; let uint = (length: number) => fieldWithRng(Random.biguint(length)); let Arithmetic = ZkProgram({ name: 'arithmetic', publicOutput: provable({ remainder: Field, quotient: Field }), methods: { divMod32: { privateInputs: [Field], async method(a: Field) { return { publicOutput: Gadgets.divMod32(a) }; }, }, divMod64: { privateInputs: [Field], async method(a: Field) { return { publicOutput: Gadgets.divMod64(a) }; }, }, }, }); await Arithmetic.compile(); const divMod32Helper = (x: bigint) => { let quotient = x >> 32n; let remainder = x - (quotient << 32n); return { remainder, quotient }; }; const divMod64Helper = (x: bigint) => { let quotient = x >> 64n; let remainder = x - (quotient << 64n); return { remainder, quotient }; }; const divModOutput = record({ remainder: field, quotient: field }); equivalent({ from: [field], to: divModOutput, })( (x) => { assert(x < 1n << 64n, `x needs to fit in 64bit, but got ${x}`); return divMod32Helper(x); }, (x) => { return Gadgets.divMod32(x); } ); equivalent({ from: [uint(64)], to: divModOutput, })( (x) => { assert(x < 1n << 128n, `x needs to fit in 128bit, but got ${x}`); return divMod64Helper(x); }, (x) => { return Gadgets.divMod64(x); } ); await equivalentAsync({ from: [field], to: divModOutput }, { runs: 3 })( (x) => { assert(x < 1n << 64n, `x needs to fit in 64bit, but got ${x}`); return divMod32Helper(x); }, async (x) => { return (await Arithmetic.divMod32(x)).proof.publicOutput; } ); await equivalentAsync({ from: [field], to: divModOutput }, { runs: 3 })( (x) => { assert(x < 1n << 128n, `x needs to fit in 128bit, but got ${x}`); return divMod64Helper(x); }, async (x) => { return (await Arithmetic.divMod64(x)).proof.publicOutput; } );