Browse Source

added verifier_test

main
Kevin Jue 2 years ago
parent
commit
4498f175f1
5 changed files with 79 additions and 28 deletions
  1. +1
    -1
      go.mod
  2. +2
    -2
      go.sum
  3. +4
    -18
      plonky2_verifier/plonk.go
  4. +19
    -0
      plonky2_verifier/verifier.go
  5. +53
    -7
      plonky2_verifier/verifier_test.go

+ 1
- 1
go.mod

@ -30,4 +30,4 @@ require (
// For now, use a forked version of gnark so that the emaulated fields are // For now, use a forked version of gnark so that the emaulated fields are
// mod'ed when printed. See here: https://github.com/kevjue/gnark/commit/0b216679a380b4b8d29f10dd96f34e8a5702463e // mod'ed when printed. See here: https://github.com/kevjue/gnark/commit/0b216679a380b4b8d29f10dd96f34e8a5702463e
replace github.com/consensys/gnark v0.7.2-0.20220921094618-a121a3074ee8 => github.com/kevjue/gnark v0.7.2-0.20221109003544-edd49e7202a7
replace github.com/consensys/gnark v0.7.2-0.20220921094618-a121a3074ee8 => github.com/kevjue/gnark v0.7.2-0.20221123002814-bcc0d7d32d60

+ 2
- 2
go.sum

@ -16,8 +16,8 @@ github.com/google/go-cmp v0.5.8 h1:e6P7q2lk1O+qJJb4BtCQXlK8vWEO8V1ZeuEdJNOqZyg=
github.com/google/pprof v0.0.0-20220729232143-a41b82acbcb1 h1:8pyqKJvrJqUYaKS851Ule26pwWvey6IDMiczaBLDKLQ= github.com/google/pprof v0.0.0-20220729232143-a41b82acbcb1 h1:8pyqKJvrJqUYaKS851Ule26pwWvey6IDMiczaBLDKLQ=
github.com/google/pprof v0.0.0-20220729232143-a41b82acbcb1/go.mod h1:gSuNB+gJaOiQKLEZ+q+PK9Mq3SOzhRcw2GsGS/FhYDk= github.com/google/pprof v0.0.0-20220729232143-a41b82acbcb1/go.mod h1:gSuNB+gJaOiQKLEZ+q+PK9Mq3SOzhRcw2GsGS/FhYDk=
github.com/google/subcommands v1.2.0/go.mod h1:ZjhPrFU+Olkh9WazFPsl27BQ4UPiG37m3yTrtFlrHVk= github.com/google/subcommands v1.2.0/go.mod h1:ZjhPrFU+Olkh9WazFPsl27BQ4UPiG37m3yTrtFlrHVk=
github.com/kevjue/gnark v0.7.2-0.20221109003544-edd49e7202a7 h1:pU9438pFjuTjtDA4iV/oOPcdnzL7KelKXp4aHuqn2o4=
github.com/kevjue/gnark v0.7.2-0.20221109003544-edd49e7202a7/go.mod h1:iN7/IRE6Eu2QKnTJEsoS48suBV0O5XrM+Nzo1ipp6Zw=
github.com/kevjue/gnark v0.7.2-0.20221123002814-bcc0d7d32d60 h1:Z7hWN0/Spz1H18rBm9qpqzy0dX1/uWhGSMxMMEaruVY=
github.com/kevjue/gnark v0.7.2-0.20221123002814-bcc0d7d32d60/go.mod h1:iN7/IRE6Eu2QKnTJEsoS48suBV0O5XrM+Nzo1ipp6Zw=
github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0= github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0=
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=

+ 4
- 18
plonky2_verifier/plonk.go

@ -174,20 +174,13 @@ func (p *PlonkChip) evalVanishingPoly(proofChallenges ProofChallenges, openings
} }
vanishingTerms := append(vanishingZ1Terms, vanishingPartialProductsTerms...) vanishingTerms := append(vanishingZ1Terms, vanishingPartialProductsTerms...)
vanishingTerms = append(vanishingTerms, []QuadraticExtension{p.qeAPI.ZERO_QE, p.qeAPI.ZERO_QE, p.qeAPI.ZERO_QE, p.qeAPI.ZERO_QE}...)
reducedValues := make([]QuadraticExtension, p.commonData.Config.NumChallenges) reducedValues := make([]QuadraticExtension, p.commonData.Config.NumChallenges)
for i := uint64(0); i < p.commonData.Config.NumChallenges; i++ { for i := uint64(0); i < p.commonData.Config.NumChallenges; i++ {
reducedValues[i] = p.qeAPI.ZERO_QE reducedValues[i] = p.qeAPI.ZERO_QE
} }
// TODO: Enable this check once the custom gate evaluations are added to the
// vanishingTerms array
/*
if len(vanishingTerms) != int(p.commonData.QuotientDegreeFactor) {
panic("evalVanishingPoly: len(vanishingTerms) != int(p.commonData.QuotientDegreeFactor)")
}
*/
// reverse iterate the vanishingPartialProductsTerms array // reverse iterate the vanishingPartialProductsTerms array
for i := len(vanishingTerms) - 1; i >= 0; i-- { for i := len(vanishingTerms) - 1; i >= 0; i-- {
for j := uint64(0); j < p.commonData.Config.NumChallenges; j++ { for j := uint64(0); j < p.commonData.Config.NumChallenges; j++ {
@ -219,8 +212,8 @@ func (p *PlonkChip) Verify(proofChallenges ProofChallenges, openings OpeningSet)
// So to reconstruct `t(zeta)` we can compute `reduce_with_powers(chunk, zeta^n)` for each // So to reconstruct `t(zeta)` we can compute `reduce_with_powers(chunk, zeta^n)` for each
// `quotient_degree_factor`-sized chunk of the original evaluations. // `quotient_degree_factor`-sized chunk of the original evaluations.
for i := 0; i < len(vanishingPolysZeta); i++ { for i := 0; i < len(vanishingPolysZeta); i++ {
quotientPolysStartIdx := i * len(vanishingPolysZeta)
quotientPolysEndIdx := quotientPolysStartIdx + len(vanishingPolysZeta)
quotientPolysStartIdx := i * int(p.commonData.QuotientDegreeFactor)
quotientPolysEndIdx := quotientPolysStartIdx + int(p.commonData.QuotientDegreeFactor)
prod := p.qeAPI.MulExtension( prod := p.qeAPI.MulExtension(
zHZeta, zHZeta,
p.qeAPI.ReduceWithPowers( p.qeAPI.ReduceWithPowers(
@ -229,13 +222,6 @@ func (p *PlonkChip) Verify(proofChallenges ProofChallenges, openings OpeningSet)
), ),
) )
// TODO: Uncomment this after adding in the custom gates evaluations
//p.qeAPI.AssertIsEqual(vanishingPolysZeta[i], prod)
// For now, just put in a dummy equality check so that VS stops complaining about unused variables
p.qeAPI.AssertIsEqual(
p.qeAPI.MulExtension(vanishingPolysZeta[i], p.qeAPI.ZERO_QE),
p.qeAPI.MulExtension(prod, p.qeAPI.ZERO_QE),
)
p.qeAPI.AssertIsEqual(vanishingPolysZeta[i], prod)
} }
} }

+ 19
- 0
plonky2_verifier/verifier.go

@ -82,6 +82,25 @@ func (c *VerifierChip) Verify(proofWithPis ProofWithPublicInputs, verifierData V
proofWithPis.Proof.QuotientPolysCap, proofWithPis.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] = c.fieldAPI.Add(proofChallenges.PlonkZeta[0], ZERO_F).(F)
proofChallenges.PlonkZeta[1] = c.fieldAPI.Add(proofChallenges.PlonkZeta[1], ZERO_F).(F)
proofChallenges.FriChallenges.FriAlpha[0] = c.fieldAPI.Add(proofChallenges.FriChallenges.FriAlpha[0], ZERO_F).(F)
proofChallenges.FriChallenges.FriAlpha[1] = c.fieldAPI.Add(proofChallenges.FriChallenges.FriAlpha[1], ZERO_F).(F)
for i := 0; i < len(proofChallenges.FriChallenges.FriBetas); i++ {
proofChallenges.FriChallenges.FriBetas[i][0] = c.fieldAPI.Add(proofChallenges.FriChallenges.FriBetas[i][0], ZERO_F).(F)
proofChallenges.FriChallenges.FriBetas[i][1] = c.fieldAPI.Add(proofChallenges.FriChallenges.FriBetas[i][1], ZERO_F).(F)
}
proofChallenges.FriChallenges.FriPowResponse = c.fieldAPI.Add(proofChallenges.FriChallenges.FriPowResponse, ZERO_F).(F)
for i := 0; i < len(proofChallenges.FriChallenges.FriQueryIndicies); i++ {
proofChallenges.FriChallenges.FriQueryIndicies[i] = c.fieldAPI.Add(proofChallenges.FriChallenges.FriQueryIndicies[i], ZERO_F).(F)
}
c.friChip.VerifyFriProof( c.friChip.VerifyFriProof(
commonData.GetFriInstance(c.qeAPI, proofChallenges.PlonkZeta, commonData.DegreeBits), commonData.GetFriInstance(c.qeAPI, proofChallenges.PlonkZeta, commonData.DegreeBits),
proofWithPis.Proof.Openings.ToFriOpenings(), proofWithPis.Proof.Openings.ToFriOpenings(),

+ 53
- 7
plonky2_verifier/verifier_test.go

@ -9,7 +9,7 @@ import (
"github.com/consensys/gnark/test" "github.com/consensys/gnark/test"
) )
type TestVerifierCircuit struct {
type TestVerifierChallengesCircuit struct {
fieldAPI frontend.API `gnark:"-"` fieldAPI frontend.API `gnark:"-"`
qeAPI *QuadraticExtensionAPI `gnark:"-"` qeAPI *QuadraticExtensionAPI `gnark:"-"`
hashAPI *HashAPI `gnark:"-"` hashAPI *HashAPI `gnark:"-"`
@ -35,7 +35,7 @@ type TestVerifierCircuit struct {
verifierChip *VerifierChip verifierChip *VerifierChip
} }
func (c *TestVerifierCircuit) GetChallengesSanityCheck(
func (c *TestVerifierChallengesCircuit) GetChallengesSanityCheck(
proofWithPis ProofWithPublicInputs, proofWithPis ProofWithPublicInputs,
verifierData VerifierOnlyCircuitData, verifierData VerifierOnlyCircuitData,
commonData CommonCircuitData, commonData CommonCircuitData,
@ -90,7 +90,7 @@ func (c *TestVerifierCircuit) GetChallengesSanityCheck(
} }
} }
func (c *TestVerifierCircuit) Define(api frontend.API) error {
func (c *TestVerifierChallengesCircuit) Define(api frontend.API) error {
proofWithPis := DeserializeProofWithPublicInputs(c.proofWithPIsFilename) proofWithPis := DeserializeProofWithPublicInputs(c.proofWithPIsFilename)
commonCircuitData := DeserializeCommonCircuitData(c.commonCircuitDataFilename) commonCircuitData := DeserializeCommonCircuitData(c.commonCircuitDataFilename)
verfierOnlyCircuitData := DeserializeVerifierOnlyCircuitData(c.verifierOnlyCircuitDataFilename) verfierOnlyCircuitData := DeserializeVerifierOnlyCircuitData(c.verifierOnlyCircuitDataFilename)
@ -112,7 +112,7 @@ func TestFibonacciVerifierWitness(t *testing.T) {
assert := test.NewAssert(t) assert := test.NewAssert(t)
testCase := func() { testCase := func() {
circuit := TestVerifierCircuit{
circuit := TestVerifierChallengesCircuit{
proofWithPIsFilename: "./data/fibonacci/proof_with_public_inputs.json", proofWithPIsFilename: "./data/fibonacci/proof_with_public_inputs.json",
commonCircuitDataFilename: "./data/fibonacci/common_circuit_data.json", commonCircuitDataFilename: "./data/fibonacci/common_circuit_data.json",
verifierOnlyCircuitDataFilename: "./data/fibonacci/verifier_only_circuit_data.json", verifierOnlyCircuitDataFilename: "./data/fibonacci/verifier_only_circuit_data.json",
@ -183,7 +183,7 @@ func TestFibonacciVerifierWitness(t *testing.T) {
NewFieldElement(13636347200053048758), NewFieldElement(13636347200053048758),
}, },
} }
witness := TestVerifierCircuit{}
witness := TestVerifierChallengesCircuit{}
err := test.IsSolved(&circuit, &witness, TEST_CURVE.ScalarField()) err := test.IsSolved(&circuit, &witness, TEST_CURVE.ScalarField())
assert.NoError(err) assert.NoError(err)
} }
@ -195,7 +195,7 @@ func TestDummyVerifierWitness(t *testing.T) {
assert := test.NewAssert(t) assert := test.NewAssert(t)
testCase := func() { testCase := func() {
circuit := TestVerifierCircuit{
circuit := TestVerifierChallengesCircuit{
proofWithPIsFilename: "./data/dummy_2^14_gates/proof_with_public_inputs.json", proofWithPIsFilename: "./data/dummy_2^14_gates/proof_with_public_inputs.json",
commonCircuitDataFilename: "./data/dummy_2^14_gates/common_circuit_data.json", commonCircuitDataFilename: "./data/dummy_2^14_gates/common_circuit_data.json",
verifierOnlyCircuitDataFilename: "./data/dummy_2^14_gates/verifier_only_circuit_data.json", verifierOnlyCircuitDataFilename: "./data/dummy_2^14_gates/verifier_only_circuit_data.json",
@ -279,10 +279,56 @@ func TestDummyVerifierWitness(t *testing.T) {
NewFieldElement(11238419549114325157), NewFieldElement(11238419549114325157),
}, },
} }
witness := TestVerifierCircuit{} // No real witness as the test circuit's Define function will inject in the witness
witness := TestVerifierChallengesCircuit{} // No real witness as the test circuit's Define function will inject in the witness
err := test.IsSolved(&circuit, &witness, TEST_CURVE.ScalarField()) err := test.IsSolved(&circuit, &witness, TEST_CURVE.ScalarField())
assert.NoError(err) assert.NoError(err)
} }
testCase() testCase()
} }
type TestVerifierCircuit struct {
proofWithPIsFilename string `gnark:"-"`
commonCircuitDataFilename string `gnark:"-"`
verifierOnlyCircuitDataFilename string `gnark:"-"`
}
func (c *TestVerifierCircuit) Define(api frontend.API) error {
proofWithPis := DeserializeProofWithPublicInputs(c.proofWithPIsFilename)
commonCircuitData := DeserializeCommonCircuitData(c.commonCircuitDataFilename)
verfierOnlyCircuitData := DeserializeVerifierOnlyCircuitData(c.verifierOnlyCircuitDataFilename)
fieldAPI := NewFieldAPI(api)
qeAPI := NewQuadraticExtensionAPI(fieldAPI, commonCircuitData.DegreeBits)
hashAPI := NewHashAPI(fieldAPI)
poseidonChip := NewPoseidonChip(api, fieldAPI)
plonkChip := NewPlonkChip(api, qeAPI, commonCircuitData)
friChip := NewFriChip(api, fieldAPI, qeAPI, hashAPI, poseidonChip, &commonCircuitData.FriParams)
verifierChip := VerifierChip{
api: api,
fieldAPI: fieldAPI,
qeAPI: qeAPI,
poseidonChip: poseidonChip,
plonkChip: plonkChip,
friChip: friChip,
}
verifierChip.Verify(proofWithPis, verfierOnlyCircuitData, commonCircuitData)
return nil
}
func TestDummyVerifier(t *testing.T) {
assert := test.NewAssert(t)
testCase := func() {
circuit := TestVerifierCircuit{
proofWithPIsFilename: "./data/dummy_2^14_gates/proof_with_public_inputs.json",
commonCircuitDataFilename: "./data/dummy_2^14_gates/common_circuit_data.json",
verifierOnlyCircuitDataFilename: "./data/dummy_2^14_gates/verifier_only_circuit_data.json",
}
witness := TestVerifierCircuit{}
err := test.IsSolved(&circuit, &witness, TEST_CURVE.ScalarField())
assert.NoError(err)
}
testCase()
}

Loading…
Cancel
Save