mirror of
https://github.com/arnaucube/gnark-plonky2-verifier.git
synced 2026-01-12 09:01:32 +01:00
range check inputted plonky2 proof (#29)
* gl * stage 1 optimizations * working optimized poseidon * Fix posedion tests * in progress gate type refactor * working gates * working e2e * hm' * hm2 * debug saga continues * more debugging cry * more debug * it finally works * optimizations * more optimizations * new changes * more optimizations * more cleanup * some refactoring * new files * flattening of packages * working commit * more refactor * more flattening * more flattening * more more refactor * more optimizations * more optimizations * more optimizations * plonk benchmark * plonk * fix r1cs * resolve kevin's comments * Update goldilocks/base.go Co-authored-by: Kevin Jue <kjue235@gmail.com> * Update goldilocks/base.go Co-authored-by: Kevin Jue <kjue235@gmail.com> * Update goldilocks/base.go Co-authored-by: Kevin Jue <kjue235@gmail.com> * Update goldilocks/quadratic_extension.go Co-authored-by: Kevin Jue <kjue235@gmail.com> * added range check for the inputted proof * removed the go.mod replace directive * removed some hacky code * removed duplicate import * renamed rangecheckQEVariable to rangecheckQE * resolved conflict --------- Co-authored-by: John Guibas <john@succinct.xyz>
This commit is contained in:
2
go.mod
2
go.mod
@@ -29,5 +29,3 @@ require (
|
|||||||
gopkg.in/yaml.v3 v3.0.1 // indirect
|
gopkg.in/yaml.v3 v3.0.1 // indirect
|
||||||
rsc.io/tmplfunc v0.0.3 // indirect
|
rsc.io/tmplfunc v0.0.3 // indirect
|
||||||
)
|
)
|
||||||
|
|
||||||
// replace github.com/consensys/gnark => /Users/kevin/succinctlabs/gnark
|
|
||||||
|
|||||||
@@ -232,3 +232,8 @@ func (p *Chip) AssertIsEqualExtension(
|
|||||||
p.AssertIsEqual(a[0], b[0])
|
p.AssertIsEqual(a[0], b[0])
|
||||||
p.AssertIsEqual(a[1], b[1])
|
p.AssertIsEqual(a[1], b[1])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (p *Chip) RangeCheckQE(a QuadraticExtensionVariable) {
|
||||||
|
p.RangeCheck(a[0])
|
||||||
|
p.RangeCheck(a[1])
|
||||||
|
}
|
||||||
|
|||||||
@@ -12,19 +12,22 @@ import (
|
|||||||
|
|
||||||
type VerifierChip struct {
|
type VerifierChip struct {
|
||||||
api frontend.API `gnark:"-"`
|
api frontend.API `gnark:"-"`
|
||||||
poseidonGlChip *poseidon.GoldilocksChip
|
glChip *gl.Chip `gnark:"-"`
|
||||||
poseidonBN254Chip *poseidon.BN254Chip
|
poseidonGlChip *poseidon.GoldilocksChip `gnark:"-"`
|
||||||
plonkChip *plonk.PlonkChip
|
poseidonBN254Chip *poseidon.BN254Chip `gnark:"-"`
|
||||||
friChip *fri.Chip
|
plonkChip *plonk.PlonkChip `gnark:"-"`
|
||||||
|
friChip *fri.Chip `gnark:"-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewVerifierChip(api frontend.API, commonCircuitData types.CommonCircuitData) *VerifierChip {
|
func NewVerifierChip(api frontend.API, commonCircuitData types.CommonCircuitData) *VerifierChip {
|
||||||
|
glChip := gl.NewChip(api)
|
||||||
friChip := fri.NewChip(api, &commonCircuitData.FriParams)
|
friChip := fri.NewChip(api, &commonCircuitData.FriParams)
|
||||||
plonkChip := plonk.NewPlonkChip(api, commonCircuitData)
|
plonkChip := plonk.NewPlonkChip(api, commonCircuitData)
|
||||||
poseidonGlChip := poseidon.NewGoldilocksChip(api)
|
poseidonGlChip := poseidon.NewGoldilocksChip(api)
|
||||||
poseidonBN254Chip := poseidon.NewBN254Chip(api)
|
poseidonBN254Chip := poseidon.NewBN254Chip(api)
|
||||||
return &VerifierChip{
|
return &VerifierChip{
|
||||||
api: api,
|
api: api,
|
||||||
|
glChip: glChip,
|
||||||
poseidonGlChip: poseidonGlChip,
|
poseidonGlChip: poseidonGlChip,
|
||||||
poseidonBN254Chip: poseidonBN254Chip,
|
poseidonBN254Chip: poseidonBN254Chip,
|
||||||
plonkChip: plonkChip,
|
plonkChip: plonkChip,
|
||||||
@@ -144,14 +147,70 @@ func (c *VerifierChip) generateProofInput(commonData common.CommonCircuitData) c
|
|||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
func (c *VerifierChip) rangeCheckProof(proof types.Proof) {
|
||||||
|
// Need to verify the plonky2 proof's openings, openings proof (other than the sibling elements), fri's final poly, pow witness.
|
||||||
|
|
||||||
|
// Note that this is NOT range checking the public inputs (first 32 elements should be no more than 8 bits and the last 4 elements should be no more than 64 bits). Since this is currently being inputted via the smart contract,
|
||||||
|
// we will assume that caller is doing that check.
|
||||||
|
|
||||||
|
// Range check the proof's openings.
|
||||||
|
for _, constant := range proof.Openings.Constants {
|
||||||
|
c.glChip.RangeCheckQE(constant)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, plonkSigma := range proof.Openings.PlonkSigmas {
|
||||||
|
c.glChip.RangeCheckQE(plonkSigma)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, wire := range proof.Openings.Wires {
|
||||||
|
c.glChip.RangeCheckQE(wire)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, plonkZ := range proof.Openings.PlonkZs {
|
||||||
|
c.glChip.RangeCheckQE(plonkZ)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, plonkZNext := range proof.Openings.PlonkZsNext {
|
||||||
|
c.glChip.RangeCheckQE(plonkZNext)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, partialProduct := range proof.Openings.PartialProducts {
|
||||||
|
c.glChip.RangeCheckQE(partialProduct)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, quotientPoly := range proof.Openings.QuotientPolys {
|
||||||
|
c.glChip.RangeCheckQE(quotientPoly)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Range check the openings proof.
|
||||||
|
for _, queryRound := range proof.OpeningProof.QueryRoundProofs {
|
||||||
|
for _, initialTreesElement := range queryRound.InitialTreesProof.EvalsProofs[0].Elements {
|
||||||
|
c.glChip.RangeCheck(initialTreesElement)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, queryStep := range queryRound.Steps {
|
||||||
|
for _, eval := range queryStep.Evals {
|
||||||
|
c.glChip.RangeCheckQE(eval)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Range check the fri's final poly.
|
||||||
|
for _, coeff := range proof.OpeningProof.FinalPoly.Coeffs {
|
||||||
|
c.glChip.RangeCheckQE(coeff)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Range check the pow witness.
|
||||||
|
c.glChip.RangeCheck(proof.OpeningProof.PowWitness)
|
||||||
|
}
|
||||||
|
|
||||||
func (c *VerifierChip) Verify(
|
func (c *VerifierChip) Verify(
|
||||||
proof types.Proof,
|
proof types.Proof,
|
||||||
publicInputs []gl.Variable,
|
publicInputs []gl.Variable,
|
||||||
verifierData types.VerifierOnlyCircuitData,
|
verifierData types.VerifierOnlyCircuitData,
|
||||||
commonData types.CommonCircuitData,
|
commonData types.CommonCircuitData,
|
||||||
) {
|
) {
|
||||||
glApi := gl.NewChip(c.api)
|
c.rangeCheckProof(proof)
|
||||||
// TODO: Need to range check all the proof and public input elements to make sure they are within goldilocks field
|
|
||||||
|
|
||||||
// Generate the parts of the witness that is for the plonky2 proof input
|
// Generate the parts of the witness that is for the plonky2 proof input
|
||||||
publicInputsHash := c.GetPublicInputsHash(publicInputs)
|
publicInputsHash := c.GetPublicInputsHash(publicInputs)
|
||||||
@@ -166,27 +225,8 @@ func (c *VerifierChip) Verify(
|
|||||||
proof.QuotientPolysCap,
|
proof.QuotientPolysCap,
|
||||||
}
|
}
|
||||||
|
|
||||||
// Seems like there is a bug in the emulated field code.
|
|
||||||
// Add ZERO to all of the fri challenges values to reduce them.
|
|
||||||
proofChallenges.PlonkZeta[0] = glApi.Add(proofChallenges.PlonkZeta[0], gl.Zero())
|
|
||||||
proofChallenges.PlonkZeta[1] = glApi.Add(proofChallenges.PlonkZeta[1], gl.Zero())
|
|
||||||
|
|
||||||
proofChallenges.FriChallenges.FriAlpha[0] = glApi.Add(proofChallenges.FriChallenges.FriAlpha[0], gl.Zero())
|
|
||||||
proofChallenges.FriChallenges.FriAlpha[1] = glApi.Add(proofChallenges.FriChallenges.FriAlpha[1], gl.Zero())
|
|
||||||
|
|
||||||
for i := 0; i < len(proofChallenges.FriChallenges.FriBetas); i++ {
|
|
||||||
proofChallenges.FriChallenges.FriBetas[i][0] = glApi.Add(proofChallenges.FriChallenges.FriBetas[i][0], gl.Zero())
|
|
||||||
proofChallenges.FriChallenges.FriBetas[i][1] = glApi.Add(proofChallenges.FriChallenges.FriBetas[i][1], gl.Zero())
|
|
||||||
}
|
|
||||||
|
|
||||||
proofChallenges.FriChallenges.FriPowResponse = glApi.Add(proofChallenges.FriChallenges.FriPowResponse, gl.Zero())
|
|
||||||
|
|
||||||
for i := 0; i < len(proofChallenges.FriChallenges.FriQueryIndices); i++ {
|
|
||||||
proofChallenges.FriChallenges.FriQueryIndices[i] = glApi.Add(proofChallenges.FriChallenges.FriQueryIndices[i], gl.Zero())
|
|
||||||
}
|
|
||||||
|
|
||||||
c.friChip.VerifyFriProof(
|
c.friChip.VerifyFriProof(
|
||||||
fri.GetInstance(&commonData, glApi, proofChallenges.PlonkZeta, commonData.DegreeBits),
|
fri.GetInstance(&commonData, c.glChip, proofChallenges.PlonkZeta, commonData.DegreeBits),
|
||||||
fri.ToOpenings(proof.Openings),
|
fri.ToOpenings(proof.Openings),
|
||||||
&proofChallenges.FriChallenges,
|
&proofChallenges.FriChallenges,
|
||||||
initialMerkleCaps,
|
initialMerkleCaps,
|
||||||
|
|||||||
Reference in New Issue
Block a user