Skip to content

Commit

Permalink
Prover: all the fixes for beta-v1.a (#90)
Browse files Browse the repository at this point in the history
* feat(limits): unhardcode the keccak limits
* limits(shomei): double the state limits
* fix(rlpaddr): uses the right stamp column for rlpaddr
* fix(ecpair): fix 1 invalid constraints and a bug in the assignment
* log(plonk): logs which circuit is failing in plonk-in-wizard
* log(projection): print a more informative message when a projection query fails
* feat(csv): adds more options to FmtCSV
* fix(mimc): removes a non-necessary constraint for mimc padding
* fix(mimc): address the edge-case where the mimc data size is a multiple of 31
* fix(sha2): uses the correct selectors to extract the sha2 hashes
* chores(makefile): dont recreate the zkevm.bin when linting or running the checker
* chore(make): adds the bin/checker in the .PHONY
* chores(cs): bump the constraints to rc7
* fix(arithmetization): fix invalid casting into a variable
  • Loading branch information
AlexandreBelling authored Sep 25, 2024
1 parent 5256e04 commit bba9677
Show file tree
Hide file tree
Showing 17 changed files with 128 additions and 43 deletions.
2 changes: 1 addition & 1 deletion constraints
5 changes: 3 additions & 2 deletions prover/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ CORSET := PATH="${CORSET_ROOT}/target/release":$$PATH
lib/compressor-and-shnarf-calculator-local \
docker \
bin/prover \
bin/checker \
corset \
testdata \

Expand Down Expand Up @@ -102,7 +103,7 @@ bin/compression-aggregation-sample:
##
## corset-checker
##
bin/checker: zkevm/arithmetization/zkevm.bin
bin/checker:
mkdir -p bin
rm -f $@
go build -o $@ ./cmd/dev-tools/corset-checker
Expand Down Expand Up @@ -140,7 +141,7 @@ test:
##
## Run the CI linting
##
ci-lint: zkevm/arithmetization/zkevm.bin
ci-lint:
golangci-lint run --timeout 5m

##
Expand Down
7 changes: 7 additions & 0 deletions prover/config/config_default.go
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,11 @@ func setDefaultTracesLimit() {
viper.SetDefault("traces_limits.SHF_REFERENCE_TABLE", 4096)
viper.SetDefault("traces_limits.INSTRUCTION_DECODER", 512)

// Shomei limits
viper.SetDefault("traces_limits.SHOMEI_MERKLE_PROOFS", 16384)

// Large Limits

// Arithmetization modules
viper.SetDefault("traces_limits_large.ADD", 1048576)
viper.SetDefault("traces_limits_large.BIN", 524288)
Expand Down Expand Up @@ -152,4 +156,7 @@ func setDefaultTracesLimit() {
viper.SetDefault("traces_limits_large.SHF_REFERENCE_TABLE", 4096)
viper.SetDefault("traces_limits_large.INSTRUCTION_DECODER", 512)

// Shomei limits
viper.SetDefault("traces_limits_large.SHOMEI_MERKLE_PROOFS", 32768)

}
2 changes: 2 additions & 0 deletions prover/config/traces_limit.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,8 @@ type TracesLimits struct {
BlockL1Size int `mapstructure:"BLOCK_L1_SIZE"`
BlockL2L1Logs int `mapstructure:"BLOCK_L2_L1_LOGS"`
BlockTransactions int `mapstructure:"BLOCK_TRANSACTIONS"`

ShomeiMerkleProofs int `mapstructure:"SHOMEI_MERKLE_PROOFS"`
}

func (tl *TracesLimits) Checksum() string {
Expand Down
2 changes: 1 addition & 1 deletion prover/protocol/dedicated/plonk/prover_commit.go
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ func (ctx compilationCtx) runGnarkPlonkProver(
)

if err != nil {
utils.Panic("Error in the solver: %v", err)
utils.Panic("Error in the solver: circ=%v err=%v", ctx.name, err)
}

// Once the solver has finished, return the solution
Expand Down
20 changes: 18 additions & 2 deletions prover/protocol/dedicated/projection/projection.go
Original file line number Diff line number Diff line change
Expand Up @@ -289,8 +289,24 @@ func (pa projectionProverAction) Run(run *wizard.ProverRuntime) {
cntB++
}

for i := range rowsA {
fmt.Printf("row=%v %v %v\n", i, strings.Join(rowsA[i], " "), strings.Join(rowsB[i], " "))
larger := max(len(rowsA), len(rowsB))

for i := 0; i < larger; i++ {

var (
fa = "* * * * * *"
fb = "* * * * * *"
)

if i < len(rowsA) {
fa = strings.Join(rowsA[i], " ")
}

if i < len(rowsB) {
fb = strings.Join(rowsB[i], " ")
}

fmt.Printf("row=%v %v %v\n", i, fa, fb)
}

logrus.Errorf("projection query %v failed", pa.Name)
Expand Down
58 changes: 52 additions & 6 deletions prover/utils/csvtraces/csvtraces.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,9 @@ import (

type cfg struct {
// The number of rows in the trace
nbRows int
nbRows int
skipPrePaddingZero bool
filterOn ifaces.Column
}

type Option func(*cfg) error
Expand All @@ -30,6 +32,21 @@ func WithNbRows(nbRows int) Option {
}
}

// SkipPrepaddingZero skips the zeroes at the beginning of the file
func SkipPrepaddingZero(c *cfg) error {
c.skipPrePaddingZero = true
return nil
}

// FilterOn sets the CSV printer to ignore rows where the provided filter
// column is zero.
func FilterOn(col ifaces.Column) Option {
return func(c *cfg) error {
c.filterOn = col
return nil
}
}

type CsvTrace struct {
mapped map[string][]field.Element

Expand All @@ -54,25 +71,44 @@ func MustOpenCsvFile(fName string) *CsvTrace {

// FmtCsv is a utility function that can be used in order to print a set of column
// in a csv format so that debugging and testcase generation are simpler.
func FmtCsv(w io.Writer, run *wizard.ProverRuntime, cols []ifaces.Column) error {
func FmtCsv(w io.Writer, run *wizard.ProverRuntime, cols []ifaces.Column, options []Option) error {

var (
header = []string{}
assignment = [][]field.Element{}
header = []string{}
assignment = [][]field.Element{}
cfg = cfg{}
foundNonZero = false
filterCol []field.Element
)

for _, op := range options {
op(&cfg)
}

for i := range cols {
header = append(header, string(cols[i].GetColID()))
assignment = append(assignment, cols[i].GetColAssignment(run).IntoRegVecSaveAlloc())
}

fmt.Fprintf(w, "%v\n", strings.Join(header, ","))

if cfg.filterOn != nil {
filterCol = cfg.filterOn.GetColAssignment(run).IntoRegVecSaveAlloc()
}

for r := range assignment[0] {

fmtVals := []string{}
var (
fmtVals = []string{}
allZeroes = true
)

for c := range assignment {

if !assignment[c][r].IsZero() {
allZeroes = false
}

if assignment[c][r].IsUint64() {
fmtVals = append(fmtVals, assignment[c][r].String())
continue
Expand All @@ -81,7 +117,17 @@ func FmtCsv(w io.Writer, run *wizard.ProverRuntime, cols []ifaces.Column) error
fmtVals = append(fmtVals, "0x"+assignment[c][r].Text(16))
}

fmt.Fprintf(w, "%v\n", strings.Join(fmtVals, ","))
if !allZeroes {
foundNonZero = true
}

if filterCol != nil && filterCol[r].IsZero() {
continue
}

if !cfg.skipPrePaddingZero || !allZeroes || foundNonZero {
fmt.Fprintf(w, "%v\n", strings.Join(fmtVals, ","))
}
}

return nil
Expand Down
2 changes: 1 addition & 1 deletion prover/zkevm/arithmetization/definition.go
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ func (s *schemaScanner) addConstraintInComp(name string, corsetCS schema.Constra
wExpr = wExpr.ReconstructBottomUp(
func(e *symbolic.Expression, children []*symbolic.Expression) (new *symbolic.Expression) {

v, isV := e.Operator.(*symbolic.Variable)
v, isV := e.Operator.(symbolic.Variable)
if !isV {
return e.SameWithNewChildren(children)
}
Expand Down
2 changes: 1 addition & 1 deletion prover/zkevm/arithmetization/zkevm.bin

Large diffs are not rendered by default.

14 changes: 2 additions & 12 deletions prover/zkevm/full.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,16 +24,6 @@ import (
"github.com/consensys/linea-monorepo/prover/zkevm/prover/statemanager/accumulator"
)

const (
// @TODO: the keccak limits are hardcoded currently, in the future we should
// instead take the limits from the trace limit file. Note, neither of these
// limits are actually enforced by the prover as the keccak module is not
// connected to the rest of the arithmetization. Thus, it is easy to just
// ignore the overflowing keccaks and the state merkle-proofs.
keccakLimit = 1 << 13
merkleProofLimit = 1 << 13
)

var (
fullZkEvm *ZkEvm
fullZkEvmCheckOnly *ZkEvm
Expand Down Expand Up @@ -141,7 +131,7 @@ func fullZKEVMWithSuite(tl *config.TracesLimits, suite compilationSuite) *ZkEvm
},
Statemanager: statemanager.Settings{
AccSettings: accumulator.Settings{
MaxNumProofs: merkleProofLimit,
MaxNumProofs: tl.ShomeiMerkleProofs,
Name: "SM_ACCUMULATOR",
MerkleTreeDepth: 40,
},
Expand All @@ -152,7 +142,7 @@ func fullZKEVMWithSuite(tl *config.TracesLimits, suite compilationSuite) *ZkEvm
Version: "beta-v1",
},
Keccak: keccak.Settings{
MaxNumKeccakf: keccakLimit,
MaxNumKeccakf: tl.BlockKeccak,
},
Ecdsa: ecdsa.Settings{
MaxNbEcRecover: tl.PrecompileEcrecoverEffectiveCalls,
Expand Down
2 changes: 2 additions & 0 deletions prover/zkevm/prover/ecpair/ecpair.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,8 @@ type ECPair struct {
*UnalignedPairingData
*UnalignedG2MembershipData

CptPrevEqualCurrID wizard.ProverAction

AlignedG2MembershipData *plonk.Alignment
AlignedMillerLoopCircuit *plonk.Alignment
AlignedFinalExpCircuit *plonk.Alignment
Expand Down
9 changes: 5 additions & 4 deletions prover/zkevm/prover/ecpair/ecpair_assignment.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,10 +10,14 @@ import (

// Assign assigns the data to the circuit
func (ec *ECPair) Assign(run *wizard.ProverRuntime) {

// assign data to the pairing check part
ec.assignPairingData(run)
// assign data to the membership check part
ec.assignMembershipData(run)
// assign the column telling wether the previous and the current row have
// the same id.
ec.CptPrevEqualCurrID.Run(run)

// general assignments
var (
Expand All @@ -22,6 +26,7 @@ func (ec *ECPair) Assign(run *wizard.ProverRuntime) {
srcIsPairingPulling = ec.UnalignedPairingData.IsPulling.GetColAssignment(run).IntoRegVecSaveAlloc()
srcIsPairingComputed = ec.UnalignedPairingData.IsComputed.GetColAssignment(run).IntoRegVecSaveAlloc()
)

if len(srcIsG2Pulling) != len(srcIsG2Computed) || len(srcIsG2Pulling) != len(srcIsPairingPulling) || len(srcIsG2Pulling) != len(srcIsPairingComputed) {
utils.Panic("ECPair: input length mismatch")
}
Expand Down Expand Up @@ -95,10 +100,6 @@ func (ec *ECPair) assignPairingData(run *wizard.ProverRuntime) {
// inputs.
nbInputs := 1 // we start with 1 because we always have at least one pairing input
for {
// first we do a sanity check - we should expect to see IsResult but if the input is shorter then panic
if currPos+nbInputs*(nbG1Limbs+nbG2Limbs+2) >= len(srcLimbs) {
utils.Panic("ECPair: not enough data for pairing at pos %d", currPos)
}
if srcIsRes[currPos+nbInputs*(nbG1Limbs+nbG2Limbs)].IsOne() {
break
}
Expand Down
16 changes: 15 additions & 1 deletion prover/zkevm/prover/ecpair/ecpair_constraints.go
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
package ecpair

import (
"github.com/consensys/linea-monorepo/prover/maths/field"
"github.com/consensys/linea-monorepo/prover/protocol/column"
"github.com/consensys/linea-monorepo/prover/protocol/column/verifiercol"
"github.com/consensys/linea-monorepo/prover/protocol/dedicated"
"github.com/consensys/linea-monorepo/prover/protocol/dedicated/projection"
"github.com/consensys/linea-monorepo/prover/protocol/ifaces"
"github.com/consensys/linea-monorepo/prover/protocol/wizard"
Expand Down Expand Up @@ -94,16 +97,27 @@ func (ec *ECPair) csConstantWhenIsComputing(comp *wizard.CompiledIOP) {
func (ec *ECPair) csInstanceIDChangeWhenNewInstance(comp *wizard.CompiledIOP) {
// when we are at the first line of the new instance then the instance ID
// should change
prevEqualCurrID, cptPrevEqualCurrID := dedicated.IsZero(
comp,
sym.Sub(
ec.UnalignedPairingData.InstanceID,
column.Shift(ec.UnalignedPairingData.InstanceID, -1),
),
)

ec.CptPrevEqualCurrID = cptPrevEqualCurrID

// IF IS_ACTIVE AND FIRST_LINE AND INSTANCE_ID != 0 => INSTANCE_ID_{i} = INSTANCE_ID_{i-1} + 1
// And the constraint does not apply on the first row.
comp.InsertGlobal(
roundNr,
ifaces.QueryIDf("%v_INSTANCE_ID_CHANGE", nameECPair),
sym.Mul(
column.Shift(verifiercol.NewConstantCol(field.One(), ec.IsActive.Size()), -1), // this "useless" line helps cancelling the constraint on the first row
ec.IsActive,
ec.UnalignedPairingData.IsFirstLineOfInstance,
ec.UnalignedPairingData.InstanceID,
sym.Sub(ec.UnalignedPairingData.InstanceID, column.Shift(ec.UnalignedPairingData.InstanceID, -1), 1),
prevEqualCurrID,
),
)
}
Expand Down
18 changes: 10 additions & 8 deletions prover/zkevm/prover/hash/importpad/import_pad.go
Original file line number Diff line number Diff line change
Expand Up @@ -149,14 +149,16 @@ func ImportAndPad(comp *wizard.CompiledIOP, inp ImportAndPadInputs, numRows int)
sym.Sub(res.IsNewHash, sym.Mul(res.IsInserted, column.Shift(res.IsPadded, -1))),
)

// before IsActive transits to 0, there should be a padding zone.
// IsActive[i] * (1-IsActive[i+1]) * (1-IsPadded[i]) =0
comp.InsertGlobal(0, ifaces.QueryIDf("%v_LAST_HASH_HAS_PADDING", inp.Name),
sym.Mul(res.IsActive,
sym.Sub(1, column.Shift(res.IsActive, 1)),
sym.Sub(1, res.IsPadded),
),
)
if inp.PaddingStrategy != generic.MiMCUsecase {
// before IsActive transits to 0, there should be a padding zone.
// IsActive[i] * (1-IsActive[i+1]) * (1-IsPadded[i]) =0
comp.InsertGlobal(0, ifaces.QueryIDf("%v_LAST_HASH_HAS_PADDING", inp.Name),
sym.Mul(res.IsActive,
sym.Sub(1, column.Shift(res.IsActive, 1)),
sym.Sub(1, res.IsPadded),
),
)
}

// to handle the above constraint for the case where isActive[i] = 1 for all i .
// IsPadded[last-row]= isActive[last-row]
Expand Down
4 changes: 4 additions & 0 deletions prover/zkevm/prover/hash/importpad/padding_mimc.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,10 @@ func (sp mimcPadder) pushPaddingRows(byteStringSize int, ipad *importationAssign
accPaddedBytes = 0
)

if remainToPad == blocksize {
remainToPad = 0
}

for remainToPad > 0 {
currNbBytes := utils.Min(remainToPad, 16)
accPaddedBytes += currNbBytes
Expand Down
4 changes: 2 additions & 2 deletions prover/zkevm/prover/hash/keccak/keccak_zkevm.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,14 +105,14 @@ func getShakiraArithmetization(comp *wizard.CompiledIOP) generic.GenericByteModu
func getRlpAddArithmetization(comp *wizard.CompiledIOP) generic.GenericByteModule {
return generic.GenericByteModule{
Data: generic.GenDataModule{
HashNum: comp.Columns.GetHandle("rlpaddr.COUNTER"),
HashNum: comp.Columns.GetHandle("rlpaddr.STAMP"),
Index: comp.Columns.GetHandle("rlpaddr.INDEX"),
Limb: comp.Columns.GetHandle("rlpaddr.LIMB"),
NBytes: comp.Columns.GetHandle("rlpaddr.nBYTES"),
ToHash: comp.Columns.GetHandle("rlpaddr.LC"),
},
Info: generic.GenInfoModule{
HashNum: comp.Columns.GetHandle("rlpaddr.COUNTER"),
HashNum: comp.Columns.GetHandle("rlpaddr.STAMP"),
HashLo: comp.Columns.GetHandle("rlpaddr.DEP_ADDR_LO"),
HashHi: comp.Columns.GetHandle("rlpaddr.RAW_ADDR_HI"),
IsHashLo: comp.Columns.GetHandle("rlpaddr.SELECTOR_KECCAK_RES"),
Expand Down
4 changes: 2 additions & 2 deletions prover/zkevm/prover/hash/sha2/sha2.go
Original file line number Diff line number Diff line change
Expand Up @@ -115,13 +115,13 @@ func newSha2SingleProvider(comp *wizard.CompiledIOP, inp Sha2SingleProviderInput
projection.InsertProjection(comp, "SHA2_RES_HI",
[]ifaces.Column{cSha2.HashHi},
[]ifaces.Column{inp.Provider.Info.HashHi},
cSha2.IsActive,
cSha2.IsEffFirstLaneOfNewHash,
inp.Provider.Info.IsHashHi,
)
projection.InsertProjection(comp, "SHA2_RES_LO",
[]ifaces.Column{cSha2.HashLo},
[]ifaces.Column{inp.Provider.Info.HashLo},
cSha2.IsActive,
cSha2.IsEffFirstLaneOfNewHash,
inp.Provider.Info.IsHashLo,
)

Expand Down

0 comments on commit bba9677

Please sign in to comment.