Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add validium functions for acc input hash calculations #1311

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
165 changes: 157 additions & 8 deletions zk/syncer/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,26 +11,48 @@ import (
"github.com/ledgerwatch/erigon/zk/utils"
)

const (
sequenceBatchesMethodName = "sequenceBatches"
sequenceBatchesValidiumMethodName = "sequenceBatchesValidium"
)

func GetAccInputDataCalcFunction(l1InfoRoot common.Hash, decodedSequenceInteerface interface{}) (accInputHashCalcFn func(prevAccInputHash common.Hash, index int) *common.Hash, totalSequenceBatches int, err error) {
switch decodedSequence := decodedSequenceInteerface.(type) {
case *SequenceBatchesCalldataPreEtrog:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculatePreEtrogAccInputHash(prevAccInputHash, decodedSequence.Batches[index].Transactions, decodedSequence.Batches[index].GlobalExitRoot, decodedSequence.Batches[index].Timestamp, decodedSequence.L2Coinbase)
}
return accInputHashCalcFn, len(decodedSequence.Batches), nil
totalSequenceBatches = len(decodedSequence.Batches)
case *SequenceBatchesCalldataEtrog:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculateEtrogAccInputHash(prevAccInputHash, decodedSequence.Batches[index].Transactions, l1InfoRoot, decodedSequence.Batches[index].ForcedTimestamp, decodedSequence.L2Coinbase, decodedSequence.Batches[index].ForcedBlockHashL1)
}
return accInputHashCalcFn, len(decodedSequence.Batches), nil
totalSequenceBatches = len(decodedSequence.Batches)
case *SequenceBatchesCalldataElderberry:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculateEtrogAccInputHash(prevAccInputHash, decodedSequence.Batches[index].Transactions, l1InfoRoot, decodedSequence.MaxSequenceTimestamp, decodedSequence.L2Coinbase, decodedSequence.Batches[index].ForcedBlockHashL1)
}
return accInputHashCalcFn, len(decodedSequence.Batches), nil
totalSequenceBatches = len(decodedSequence.Batches)
case *SequenceBatchesCalldataValidiumPreEtrog:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculatePreEtrogValidiumAccInputHash(prevAccInputHash, decodedSequence.Batches[index].TransactionsHash, decodedSequence.Batches[index].GlobalExitRoot, decodedSequence.Batches[index].Timestamp, decodedSequence.L2Coinbase)
}
totalSequenceBatches = len(decodedSequence.Batches)
case *SequenceBatchesCalldataValidiumEtrog:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculateEtrogValidiumAccInputHash(prevAccInputHash, decodedSequence.Batches[index].TransactionsHash, l1InfoRoot, decodedSequence.Batches[index].ForcedTimestamp, decodedSequence.L2Coinbase, decodedSequence.Batches[index].ForcedBlockHashL1)
}
totalSequenceBatches = len(decodedSequence.Batches)
case *SequenceBatchesCalldataValidiumElderberry:
accInputHashCalcFn = func(prevAccInputHash common.Hash, index int) *common.Hash {
return utils.CalculateEtrogValidiumAccInputHash(prevAccInputHash, decodedSequence.Batches[index].TransactionsHash, l1InfoRoot, decodedSequence.MaxSequenceTimestamp, decodedSequence.L2Coinbase, decodedSequence.Batches[index].ForcedBlockHashL1)
}
totalSequenceBatches = len(decodedSequence.Batches)
default:
return nil, 0, fmt.Errorf("unexpected type of decoded sequence calldata: %T", decodedSequenceInteerface)
}

return accInputHashCalcFn, totalSequenceBatches, nil
}

func DecodeSequenceBatchesCalldata(data []byte) (calldata interface{}, err error) {
Expand All @@ -51,8 +73,8 @@ func DecodeSequenceBatchesCalldata(data []byte) (calldata interface{}, err error
}

//sanitycheck
if method.Name != "sequenceBatches" {
return nil, fmt.Errorf("method name is not sequenceBatches, got: %s", method.Name)
if method.Name != sequenceBatchesMethodName && method.Name != sequenceBatchesValidiumMethodName {
return nil, fmt.Errorf("method name is not expected, got: %s", method.Name)
}

unpackedCalldata := make(map[string]interface{})
Expand All @@ -62,11 +84,23 @@ func DecodeSequenceBatchesCalldata(data []byte) (calldata interface{}, err error

switch methodSig {
case contracts.SequenceBatchesPreEtrog:
return decodePreEtrogSequenceBatchesCallData(unpackedCalldata), nil
if method.Name == sequenceBatchesMethodName {
return decodePreEtrogSequenceBatchesCallData(unpackedCalldata), nil
} else {
return decodePreEtrogSequenceBatchesValidiumCallData(unpackedCalldata), nil
}
case contracts.SequenceBatchesIdv5_0:
return decodeEtrogSequenceBatchesCallData(unpackedCalldata), nil
if method.Name == sequenceBatchesMethodName {
return decodeEtrogSequenceBatchesCallData(unpackedCalldata), nil
} else {
return decodeEtrogSequenceBatchesValidiumCallData(unpackedCalldata), nil
}
case contracts.SequenceBatchesIdv6_6:
return decodeElderberryBatchesCallData(unpackedCalldata), nil
if method.Name == sequenceBatchesMethodName {
return decodeElderberryBatchesCallData(unpackedCalldata), nil
} else {
return decodeElderberryBatchesValidiumCallData(unpackedCalldata), nil
}
default:
return nil, fmt.Errorf("no decoder found for method signature: %s", methodSig)
}
Expand Down Expand Up @@ -113,6 +147,47 @@ func decodeElderberryBatchesCallData(unpackedCalldata map[string]interface{}) *S
return calldata
}

type SequencedBatchValidiumElderberry struct {
TransactionsHash common.Hash
ForcedGlobalExitRoot common.Hash
ForcedTimestamp uint64
ForcedBlockHashL1 common.Hash
}

type SequenceBatchesCalldataValidiumElderberry struct {
Batches []SequencedBatchValidiumElderberry
InitSequencedBatch uint64
L2Coinbase common.Address
MaxSequenceTimestamp uint64
}

func decodeElderberryBatchesValidiumCallData(unpackedCalldata map[string]interface{}) *SequenceBatchesCalldataValidiumElderberry {
unpackedbatches := unpackedCalldata["batches"].([]struct {
TransactionsHash [32]uint8 `json:"transactionsHash"`
ForcedGlobalExitRoot [32]uint8 `json:"forcedGlobalExitRoot"`
ForcedTimestamp uint64 `json:"forcedTimestamp"`
ForcedBlockHashL1 [32]uint8 `json:"forcedBlockHashL1"`
})

calldata := &SequenceBatchesCalldataValidiumElderberry{
Batches: make([]SequencedBatchValidiumElderberry, len(unpackedbatches)),
InitSequencedBatch: unpackedCalldata["initSequencedBatch"].(uint64),
L2Coinbase: unpackedCalldata["l2Coinbase"].(common.Address),
MaxSequenceTimestamp: unpackedCalldata["maxSequenceTimestamp"].(uint64),
}

for i, batch := range unpackedbatches {
calldata.Batches[i] = SequencedBatchValidiumElderberry{
TransactionsHash: common.BytesToHash(batch.TransactionsHash[:]),
ForcedGlobalExitRoot: common.BytesToHash(batch.ForcedGlobalExitRoot[:]),
ForcedTimestamp: batch.ForcedTimestamp,
ForcedBlockHashL1: common.BytesToHash(batch.ForcedBlockHashL1[:]),
}
}

return calldata
}

type SequencedBatchEtrog struct {
Transactions []uint8
ForcedGlobalExitRoot common.Hash
Expand Down Expand Up @@ -150,6 +225,43 @@ func decodeEtrogSequenceBatchesCallData(unpackedCalldata map[string]interface{})
return calldata
}

type SequencedBatchValidiumEtrog struct {
TransactionsHash common.Hash
ForcedGlobalExitRoot common.Hash
ForcedTimestamp uint64
ForcedBlockHashL1 common.Hash
}

type SequenceBatchesCalldataValidiumEtrog struct {
Batches []SequencedBatchValidiumEtrog
L2Coinbase common.Address
}

func decodeEtrogSequenceBatchesValidiumCallData(unpackedCalldata map[string]interface{}) *SequenceBatchesCalldataValidiumEtrog {
unpackedbatches := unpackedCalldata["batches"].([]struct {
TransactionsHash [32]uint8 `json:"transactionsHash"`
ForcedGlobalExitRoot [32]uint8 `json:"forcedGlobalExitRoot"`
ForcedTimestamp uint64 `json:"forcedTimestamp"`
ForcedBlockHashL1 [32]uint8 `json:"forcedBlockHashL1"`
})

calldata := &SequenceBatchesCalldataValidiumEtrog{
Batches: make([]SequencedBatchValidiumEtrog, len(unpackedbatches)),
L2Coinbase: unpackedCalldata["l2Coinbase"].(common.Address),
}

for i, batch := range unpackedbatches {
calldata.Batches[i] = SequencedBatchValidiumEtrog{
TransactionsHash: common.BytesToHash(batch.TransactionsHash[:]),
ForcedGlobalExitRoot: common.BytesToHash(batch.ForcedGlobalExitRoot[:]),
ForcedTimestamp: batch.ForcedTimestamp,
ForcedBlockHashL1: batch.ForcedBlockHashL1,
}
}

return calldata
}

type SequencedBatchPreEtrog struct {
Transactions []uint8
GlobalExitRoot common.Hash
Expand Down Expand Up @@ -186,3 +298,40 @@ func decodePreEtrogSequenceBatchesCallData(unpackedCalldata map[string]interface

return calldata
}

type SequencedBatchValidiumPreEtrog struct {
TransactionsHash common.Hash
GlobalExitRoot common.Hash
Timestamp uint64
MinForcedTimestamp uint64
}

type SequenceBatchesCalldataValidiumPreEtrog struct {
Batches []SequencedBatchValidiumPreEtrog
L2Coinbase common.Address
}

func decodePreEtrogSequenceBatchesValidiumCallData(unpackedCalldata map[string]interface{}) *SequenceBatchesCalldataValidiumPreEtrog {
unpackedbatches := unpackedCalldata["batches"].([]struct {
TransactionsHash [32]uint8 `json:"transactionsHash"`
GlobalExitRoot [32]uint8 `json:"globalExitRoot"`
Timestamp uint64 `json:"timestamp"`
MinForcedTimestamp uint64 `json:"minForcedTimestamp"`
})

calldata := &SequenceBatchesCalldataValidiumPreEtrog{
Batches: make([]SequencedBatchValidiumPreEtrog, len(unpackedbatches)),
L2Coinbase: unpackedCalldata["l2Coinbase"].(common.Address),
}

for i, batch := range unpackedbatches {
calldata.Batches[i] = SequencedBatchValidiumPreEtrog{
TransactionsHash: common.BytesToHash(batch.TransactionsHash[:]),
GlobalExitRoot: common.BytesToHash(batch.GlobalExitRoot[:]),
Timestamp: batch.Timestamp,
MinForcedTimestamp: batch.MinForcedTimestamp,
}
}

return calldata
}
82 changes: 76 additions & 6 deletions zk/utils/acc_input_hash.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,27 @@ import (
"github.com/ledgerwatch/erigon/crypto"
)

// calculates the new accInputHash based on the old one and data frem one new batch
// this returns the accInputHash for the current batch
// oldAccInputHash - the accInputHash from the previous batch
func CalculateEtrogValidiumAccInputHash(
oldAccInputHash common.Hash,
batchTransactionData common.Hash,
l1InfoRoot common.Hash,
limitTimestamp uint64,
sequencerAddress common.Address,
forcedBlockHashL1 common.Hash,
) *common.Hash {
return calculateEtrogAccInputHash(
oldAccInputHash,
batchTransactionData.Bytes(),
l1InfoRoot,
limitTimestamp,
sequencerAddress,
forcedBlockHashL1,
)
}

// calculates the new accInputHash based on the old one and data frem one new batch
// this returns the accInputHash for the current batch
// oldAccInputHash - the accInputHash from the previous batch
Expand All @@ -19,9 +40,26 @@ func CalculateEtrogAccInputHash(
sequencerAddress common.Address,
forcedBlockHashL1 common.Hash,
) *common.Hash {
batchHashData := CalculateBatchHashData(batchTransactionData)
return calculateEtrogAccInputHash(
oldAccInputHash,
CalculateBatchHashData(batchTransactionData),
l1InfoRoot,
limitTimestamp,
sequencerAddress,
forcedBlockHashL1,
)
}

func calculateEtrogAccInputHash(
oldAccInputHash common.Hash,
batchDataHash []byte,
l1InfoRoot common.Hash,
limitTimestamp uint64,
sequencerAddress common.Address,
forcedBlockHashL1 common.Hash,
) *common.Hash {
v1 := oldAccInputHash.Bytes()
v2 := batchHashData
v2 := batchDataHash
v3 := l1InfoRoot.Bytes()
v4 := big.NewInt(0).SetUint64(limitTimestamp).Bytes()
v5 := sequencerAddress.Bytes()
Expand Down Expand Up @@ -49,9 +87,22 @@ func CalculateEtrogAccInputHash(
return &hash
}

// calculates the new accInputHash based on the old one and data frem one new batch
// this returns the accInputHash for the current batch
// oldAccInputHash - the accInputHash from the previous batch
func CalculatePreEtrogValidiumAccInputHash(
oldAccInputHash common.Hash,
batchHashData common.Hash,
globalExitRoot common.Hash,
timestamp uint64,
sequencerAddress common.Address,
) *common.Hash {
return calculatePreEtrogAccInputHash(
oldAccInputHash,
batchHashData.Bytes(),
globalExitRoot,
timestamp,
sequencerAddress,
)
}

func CalculatePreEtrogAccInputHash(
oldAccInputHash common.Hash,
batchTransactionData []byte,
Expand All @@ -60,8 +111,27 @@ func CalculatePreEtrogAccInputHash(
sequencerAddress common.Address,
) *common.Hash {
batchHashData := CalculateBatchHashData(batchTransactionData)
return calculatePreEtrogAccInputHash(
oldAccInputHash,
batchHashData,
globalExitRoot,
timestamp,
sequencerAddress,
)
}

// calculates the new accInputHash based on the old one and data frem one new batch
// this returns the accInputHash for the current batch
// oldAccInputHash - the accInputHash from the previous batch
func calculatePreEtrogAccInputHash(
oldAccInputHash common.Hash,
batchTransactionHash []byte,
globalExitRoot common.Hash,
timestamp uint64,
sequencerAddress common.Address,
) *common.Hash {
v1 := oldAccInputHash.Bytes()
v2 := batchHashData
v2 := batchTransactionHash
v3 := globalExitRoot.Bytes()
v4 := big.NewInt(0).SetUint64(timestamp).Bytes()
v5 := sequencerAddress.Bytes()
Expand Down
Loading