gnark-plonky2-verifier/goldilocks/quadratic_extension_algebra.go
John Guibas b670530e7f
Use optimized goldilocks in codebase (#26)
* 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>

* fix: resolve kevin's confusion

---------

Co-authored-by: Kevin Jue <kjue235@gmail.com>
2023-07-24 16:08:17 -07:00

126 lines
3.6 KiB
Go

package goldilocks
import "github.com/consensys/gnark-crypto/field/goldilocks"
const D = 2
type QuadraticExtensionAlgebraVariable = [D]QuadraticExtensionVariable
func NewQuadraticExtensionAlgebraVariable(
a QuadraticExtensionVariable,
b QuadraticExtensionVariable,
) QuadraticExtensionAlgebraVariable {
return QuadraticExtensionAlgebraVariable{a, b}
}
func (p QuadraticExtensionVariable) ToQuadraticExtensionAlgebra() QuadraticExtensionAlgebraVariable {
return [2]QuadraticExtensionVariable{p, ZeroExtension()}
}
func ZeroExtensionAlgebra() QuadraticExtensionAlgebraVariable {
return ZeroExtension().ToQuadraticExtensionAlgebra()
}
func OneExtensionAlgebra() QuadraticExtensionAlgebraVariable {
return OneExtension().ToQuadraticExtensionAlgebra()
}
func (p *Chip) AddExtensionAlgebra(
a QuadraticExtensionAlgebraVariable,
b QuadraticExtensionAlgebraVariable,
) QuadraticExtensionAlgebraVariable {
var sum QuadraticExtensionAlgebraVariable
for i := 0; i < D; i++ {
sum[i] = p.AddExtension(a[i], b[i])
}
return sum
}
func (p *Chip) SubExtensionAlgebra(
a QuadraticExtensionAlgebraVariable,
b QuadraticExtensionAlgebraVariable,
) QuadraticExtensionAlgebraVariable {
var diff QuadraticExtensionAlgebraVariable
for i := 0; i < D; i++ {
diff[i] = p.SubExtension(a[i], b[i])
}
return diff
}
func (p Chip) MulExtensionAlgebra(
a QuadraticExtensionAlgebraVariable,
b QuadraticExtensionAlgebraVariable,
) QuadraticExtensionAlgebraVariable {
var inner [D][]QuadraticExtensionAlgebraVariable
var innerW [D][]QuadraticExtensionAlgebraVariable
for i := 0; i < D; i++ {
for j := 0; j < D-i; j++ {
idx := (i + j) % D
inner[idx] = append(inner[idx], QuadraticExtensionAlgebraVariable{a[i], b[j]})
}
for j := D - i; j < D; j++ {
idx := (i + j) % D
innerW[idx] = append(innerW[idx], QuadraticExtensionAlgebraVariable{a[i], b[j]})
}
}
var product QuadraticExtensionAlgebraVariable
for i := 0; i < D; i++ {
acc := p.InnerProductExtension(NewVariable(W), ZeroExtension(), innerW[i])
product[i] = p.InnerProductExtension(One(), acc, inner[i])
}
return product
}
func (p *Chip) ScalarMulExtensionAlgebra(
a QuadraticExtensionVariable,
b QuadraticExtensionAlgebraVariable,
) QuadraticExtensionAlgebraVariable {
var product QuadraticExtensionAlgebraVariable
for i := 0; i < D; i++ {
product[i] = p.MulExtension(a, b[i])
}
return product
}
func (p *Chip) PartialInterpolateExtAlgebra(
domain []goldilocks.Element,
values []QuadraticExtensionAlgebraVariable,
barycentricWeights []goldilocks.Element,
point QuadraticExtensionAlgebraVariable,
initialEval QuadraticExtensionAlgebraVariable,
initialPartialProd QuadraticExtensionAlgebraVariable,
) (QuadraticExtensionAlgebraVariable, QuadraticExtensionAlgebraVariable) {
n := len(values)
if n == 0 {
panic("Cannot interpolate with no values")
}
if n != len(domain) {
panic("Domain and values must have the same length")
}
if n != len(barycentricWeights) {
panic("Domain and barycentric weights must have the same length")
}
newEval := initialEval
newPartialProd := initialPartialProd
for i := 0; i < n; i++ {
val := values[i]
x := domain[i]
xField := NewVariable(x)
xQE := xField.ToQuadraticExtension()
xQEAlgebra := xQE.ToQuadraticExtensionAlgebra()
weight := NewVariable(barycentricWeights[i].Uint64()).ToQuadraticExtension()
term := p.SubExtensionAlgebra(point, xQEAlgebra)
weightedVal := p.ScalarMulExtensionAlgebra(weight, val)
newEval = p.MulExtensionAlgebra(newEval, term)
tmp := p.MulExtensionAlgebra(weightedVal, newPartialProd)
newEval = p.AddExtensionAlgebra(newEval, tmp)
newPartialProd = p.MulExtensionAlgebra(newPartialProd, term)
}
return newEval, newPartialProd
}