nim-groth16/groth16/math/domain.nim
Dmitriy Ryajov f3042c4e00
wip
2025-03-08 11:53:20 -06:00

61 lines
1.9 KiB
Nim

#
# power-of-two sized multiplicative FFT domains in the scalar field
#
import pkg/constantine/math/arithmetic
import pkg/constantine/math/io/io_fields
import pkg/constantine/named/properties_fields
import pkg/constantine/math/extension_fields/towers
import groth16/bn128
import groth16/misc
#-------------------------------------------------------------------------------
type
Domain* = object
domainSize* : int # `N = 2^n`
logDomainSize* : int # `n = log2(N)`
domainGen* : Fr[BN254Snarks] # `g`
invDomainGen* : Fr[BN254Snarks] # `g^-1`
invDomainSize* : Fr[BN254Snarks] # `1/n`
#-------------------------------------------------------------------------------
# the generator of the multiplicative subgroup with size `2^28`
const gen28 = fromHex( Fr[BN254Snarks], "0x2a3c09f0a58a7e8500e0a7eb8ef62abc402d111e41112ed49bd61b6e725b19f0" )
func createDomain*(size: int): Domain =
let log2 = ceilingLog2(size)
assert( (1 shl log2) == size , "domain must have a power-of-two size" )
let expo = 1'u shl (28 - log2)
let gen = smallPowFr(gen28, expo)
let halfSize = size div 2
let a = smallPowFr(gen, size )
let b = smallPowFr(gen, halfSize)
assert( bool(a == oneFr) , "domain generator sanity check /A" )
assert( not bool(b == oneFr) , "domain generator sanity check /B" )
return Domain( domainSize: size
, logDomainSize: log2
, domainGen: gen
, invDomainGen: invFr(gen)
, invDomainSize: invFr(intToFr(size))
)
#-------------------------------------------------------------------------------
func enumerateDomain*(D: Domain): seq[Fr[BN254Snarks]] =
var xs = newSeq[Fr[BN254Snarks]](D.domainSize)
var g = oneFr
for i in 0..<D.domainSize:
xs[i] = g
g *= D.domainGen
return xs
#-------------------------------------------------------------------------------