mirror of
https://github.com/logos-storage/gnark-plonky2-verifier.git
synced 2026-01-09 00:23:10 +00:00
added the function friCombineInitial
This commit is contained in:
parent
8e9591c964
commit
393059b51d
@ -12,26 +12,6 @@ import (
|
||||
"github.com/consensys/gnark/frontend"
|
||||
)
|
||||
|
||||
type FriOpeningBatch struct {
|
||||
values []QuadraticExtension
|
||||
}
|
||||
|
||||
type FriOpenings struct {
|
||||
Batches []FriOpeningBatch
|
||||
}
|
||||
|
||||
func (c *OpeningSet) ToFriOpenings() FriOpenings {
|
||||
values := c.Constants
|
||||
values = append(values, c.PlonkSigmas...)
|
||||
values = append(values, c.Wires...)
|
||||
values = append(values, c.PlonkZs...)
|
||||
values = append(values, c.PartialProducts...)
|
||||
values = append(values, c.QuotientPolys...)
|
||||
zetaBatch := FriOpeningBatch{values: values}
|
||||
zetaNextBatch := FriOpeningBatch{values: c.PlonkZsNext}
|
||||
return FriOpenings{Batches: []FriOpeningBatch{zetaBatch, zetaNextBatch}}
|
||||
}
|
||||
|
||||
type FriChip struct {
|
||||
api frontend.API
|
||||
fieldAPI frontend.API
|
||||
@ -190,22 +170,10 @@ func (f *FriChip) assertNoncanonicalIndicesOK() {
|
||||
}
|
||||
}
|
||||
|
||||
func (f *FriChip) verifyQueryRound(
|
||||
challenges *FriChallenges,
|
||||
precomputedReducedEval []QuadraticExtension,
|
||||
initialMerkleCaps []MerkleCap,
|
||||
proof *FriProof,
|
||||
xIndex F,
|
||||
n uint64,
|
||||
func (f *FriChip) calculateSubgroupX(
|
||||
xIndexBits []frontend.Variable,
|
||||
nLog uint64,
|
||||
roundProof *FriQueryRound,
|
||||
) {
|
||||
f.assertNoncanonicalIndicesOK()
|
||||
xIndexBits := f.fieldAPI.ToBinary(xIndex, int(nLog))
|
||||
capIndexBits := xIndexBits[len(xIndexBits)-int(f.friParams.Config.CapHeight):]
|
||||
|
||||
f.verifyInitialProof(xIndexBits, &roundProof.InitialTreesProof, initialMerkleCaps, capIndexBits)
|
||||
|
||||
) F {
|
||||
// Compute x from its index
|
||||
// `subgroup_x` is `subgroup[x_index]`, i.e., the actual field element in the domain.
|
||||
// TODO - Make these as global values
|
||||
@ -240,10 +208,105 @@ func (f *FriChip) verifyQueryRound(
|
||||
).(F)
|
||||
}
|
||||
|
||||
subgroupX := f.fieldAPI.Mul(g, product).(F)
|
||||
return f.fieldAPI.Mul(g, product).(F)
|
||||
}
|
||||
|
||||
func (f *FriChip) friCombineInitial(
|
||||
instance FriInstanceInfo,
|
||||
proof FriInitialTreeProof,
|
||||
friAlpha QuadraticExtension,
|
||||
subgroupX_QE QuadraticExtension,
|
||||
precomputedReducedEval []QuadraticExtension,
|
||||
) QuadraticExtension {
|
||||
sum := f.qeAPI.ZERO_QE
|
||||
|
||||
if len(instance.Batches) != len(precomputedReducedEval) {
|
||||
panic("len(openings) != len(precomputedReducedEval)")
|
||||
}
|
||||
|
||||
for i := 0; i < len(instance.Batches); i++ {
|
||||
batch := instance.Batches[i]
|
||||
reducedOpenings := precomputedReducedEval[i]
|
||||
|
||||
point := batch.Point
|
||||
evals := make([]QuadraticExtension, 0)
|
||||
for _, polynomial := range batch.Polynomials {
|
||||
evals = append(
|
||||
evals,
|
||||
QuadraticExtension{proof.EvalsProofs[polynomial.OracleIndex].Elements[polynomial.PolynomialInfo], field.ZERO_F},
|
||||
)
|
||||
}
|
||||
|
||||
reducedEvals := reduceWithPowers(f.qeAPI, evals, friAlpha)
|
||||
numerator := f.qeAPI.SubExtension(reducedEvals, reducedOpenings)
|
||||
denominator := f.qeAPI.SubExtension(subgroupX_QE, point)
|
||||
sum = f.qeAPI.MulExtension(f.qeAPI.ExpU64Extension(friAlpha, uint64(len(evals))), sum)
|
||||
sum = f.qeAPI.AddExtension(
|
||||
f.qeAPI.DivExtension(
|
||||
numerator,
|
||||
denominator,
|
||||
),
|
||||
sum,
|
||||
)
|
||||
}
|
||||
|
||||
return f.qeAPI.MulExtension(sum, subgroupX_QE)
|
||||
}
|
||||
|
||||
func (f *FriChip) finalPolyEval(finalPoly PolynomialCoeffs, point QuadraticExtension) QuadraticExtension {
|
||||
ret := f.qeAPI.ZERO_QE
|
||||
for i := len(finalPoly.Coeffs) - 1; i >= 0; i-- {
|
||||
ret = f.qeAPI.AddExtension(
|
||||
f.qeAPI.MulExtension(
|
||||
ret,
|
||||
point,
|
||||
),
|
||||
finalPoly.Coeffs[i],
|
||||
)
|
||||
}
|
||||
return ret
|
||||
}
|
||||
|
||||
func (f *FriChip) verifyQueryRound(
|
||||
instance FriInstanceInfo,
|
||||
challenges *FriChallenges,
|
||||
precomputedReducedEval []QuadraticExtension,
|
||||
initialMerkleCaps []MerkleCap,
|
||||
proof *FriProof,
|
||||
xIndex F,
|
||||
n uint64,
|
||||
nLog uint64,
|
||||
roundProof *FriQueryRound,
|
||||
) {
|
||||
f.assertNoncanonicalIndicesOK()
|
||||
xIndexBits := f.fieldAPI.ToBinary(xIndex, int(nLog))
|
||||
capIndexBits := xIndexBits[len(xIndexBits)-int(f.friParams.Config.CapHeight):]
|
||||
|
||||
f.verifyInitialProof(xIndexBits, &roundProof.InitialTreesProof, initialMerkleCaps, capIndexBits)
|
||||
|
||||
subgroupX := f.calculateSubgroupX(
|
||||
xIndexBits,
|
||||
nLog,
|
||||
)
|
||||
|
||||
subgroupX_QE := QuadraticExtension{subgroupX, field.ZERO_F}
|
||||
|
||||
oldEval := f.friCombineInitial(
|
||||
instance,
|
||||
roundProof.InitialTreesProof,
|
||||
challenges.FriAlpha,
|
||||
subgroupX_QE,
|
||||
precomputedReducedEval,
|
||||
)
|
||||
|
||||
finalPolyEval := f.finalPolyEval(proof.FinalPoly, subgroupX_QE)
|
||||
|
||||
f.fieldAPI.AssertIsEqual(oldEval[0], finalPolyEval[0])
|
||||
f.fieldAPI.AssertIsEqual(oldEval[1], finalPolyEval[1])
|
||||
}
|
||||
|
||||
func (f *FriChip) VerifyFriProof(
|
||||
instance FriInstanceInfo,
|
||||
openings FriOpenings,
|
||||
friChallenges *FriChallenges,
|
||||
initialMerkleCaps []MerkleCap,
|
||||
@ -281,6 +344,7 @@ func (f *FriChip) VerifyFriProof(
|
||||
roundProof := friProof.QueryRoundProofs[idx]
|
||||
|
||||
f.verifyQueryRound(
|
||||
instance,
|
||||
friChallenges,
|
||||
precomputedReducedEvals,
|
||||
initialMerkleCaps,
|
||||
|
||||
@ -68,6 +68,7 @@ func (circuit *TestFriCircuit) Define(api frontend.API) error {
|
||||
}
|
||||
|
||||
friChip.VerifyFriProof(
|
||||
commonCircuitData.GetFriInstance(),
|
||||
proofWithPis.Proof.Openings.ToFriOpenings(),
|
||||
&friChallenges,
|
||||
initialMerkleCaps,
|
||||
|
||||
@ -2,7 +2,9 @@ package plonky2_verifier
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"gnark-ed25519/field"
|
||||
. "gnark-ed25519/field"
|
||||
"math/bits"
|
||||
|
||||
"github.com/consensys/gnark/frontend"
|
||||
)
|
||||
@ -12,7 +14,6 @@ type QuadraticExtensionAPI struct {
|
||||
|
||||
W F
|
||||
DTH_ROOT F
|
||||
ZERO_F F
|
||||
|
||||
ONE QuadraticExtension
|
||||
ZERO_QE QuadraticExtension
|
||||
@ -66,7 +67,7 @@ func (c *QuadraticExtensionAPI) InverseExtension(a QuadraticExtension) Quadratic
|
||||
a1_is_zero := c.fieldAPI.IsZero(a[1])
|
||||
|
||||
// assert that a0_is_zero OR a1_is_zero == false
|
||||
c.fieldAPI.AssertIsEqual(c.fieldAPI.Mul(a0_is_zero, a1_is_zero).(F), c.ZERO_F)
|
||||
c.fieldAPI.AssertIsEqual(c.fieldAPI.Mul(a0_is_zero, a1_is_zero).(F), field.ZERO_F)
|
||||
|
||||
a_pow_r_minus_1 := QuadraticExtension{a[0], c.fieldAPI.Mul(a[1], c.DTH_ROOT).(F)}
|
||||
a_pow_r := c.MulExtension(a_pow_r_minus_1, a)
|
||||
@ -78,7 +79,35 @@ func (c *QuadraticExtensionAPI) ScalarMulExtension(a QuadraticExtension, scalar
|
||||
}
|
||||
|
||||
func (c *QuadraticExtensionAPI) FieldToQE(a F) QuadraticExtension {
|
||||
return QuadraticExtension{a, c.ZERO_F}
|
||||
return QuadraticExtension{a, field.ZERO_F}
|
||||
}
|
||||
|
||||
// / Exponentiate `base` to the power of a known `exponent`.
|
||||
func (c *QuadraticExtensionAPI) ExpU64Extension(a QuadraticExtension, exponent uint64) QuadraticExtension {
|
||||
switch exponent {
|
||||
case 0:
|
||||
return c.ONE
|
||||
case 1:
|
||||
return a
|
||||
case 2:
|
||||
return c.SquareExtension(a)
|
||||
default:
|
||||
}
|
||||
|
||||
current := a
|
||||
product := c.ONE
|
||||
|
||||
for i := 0; i < bits.Len64(exponent); i++ {
|
||||
if i != 0 {
|
||||
current = c.SquareExtension(current)
|
||||
}
|
||||
|
||||
if (exponent >> i & 1) != 0 {
|
||||
product = c.MulExtension(product, current)
|
||||
}
|
||||
}
|
||||
|
||||
return product
|
||||
}
|
||||
|
||||
func (c *QuadraticExtensionAPI) Println(a QuadraticExtension) {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user