Skip to content

Commit

Permalink
fork implementation for root calculation
Browse files Browse the repository at this point in the history
  • Loading branch information
igorcrevar committed Jul 11, 2023
1 parent 95fabc6 commit 6021c59
Show file tree
Hide file tree
Showing 7 changed files with 88 additions and 6 deletions.
2 changes: 1 addition & 1 deletion blockchain/blockchain.go
Original file line number Diff line number Diff line change
Expand Up @@ -705,7 +705,7 @@ func (b *Blockchain) verifyBlockBody(block *types.Block) ([]*types.Receipt, erro
}

// Make sure the transactions root matches up
if hash := buildroot.CalculateTransactionsRoot(block.Transactions); hash != block.Header.TxRoot {
if hash := buildroot.CalculateTransactionsRoot(block.Transactions, block.Number()); hash != block.Header.TxRoot {
b.logger.Error(fmt.Sprintf(
"transaction root hash mismatch: have %s, want %s",
hash,
Expand Down
8 changes: 7 additions & 1 deletion chain/params.go
Original file line number Diff line number Diff line change
Expand Up @@ -87,8 +87,11 @@ const (
EIP150 = "EIP150"
EIP158 = "EIP158"
EIP155 = "EIP155"
TxHashWithType = "txHashWithType"
)

const TxHashHandler = "txHash"

// Forks is map which contains all forks and their starting blocks from genesis
type Forks map[string]Fork

Expand Down Expand Up @@ -120,6 +123,7 @@ func (f *Forks) At(block uint64) ForksInTime {
EIP150: f.IsActive(EIP150, block),
EIP158: f.IsActive(EIP158, block),
EIP155: f.IsActive(EIP155, block),
TxHashWithType: f.IsActive(TxHashWithType, block),
}
}

Expand Down Expand Up @@ -164,7 +168,8 @@ type ForksInTime struct {
London,
EIP150,
EIP158,
EIP155 bool
EIP155,
TxHashWithType bool
}

// AllForksEnabled should contain all supported forks by current edge version
Expand All @@ -178,4 +183,5 @@ var AllForksEnabled = &Forks{
Petersburg: NewFork(0),
Istanbul: NewFork(0),
London: NewFork(0),
TxHashWithType: NewFork(0),
}
4 changes: 4 additions & 0 deletions consensus/polybft/blockchain_wrapper.go
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,10 @@ func (p *blockchainWrapper) ProcessBlock(parent *types.Header, block *types.Bloc
Receipts: transition.Receipts(),
})

if builtBlock.Header.TxRoot != block.Header.TxRoot {
return nil, fmt.Errorf("incorrect tx root: (%s, %s)", builtBlock.Header.TxRoot, block.Header.TxRoot)
}

return &types.FullBlock{
Block: builtBlock,
Receipts: transition.Receipts(),
Expand Down
2 changes: 1 addition & 1 deletion consensus/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ func BuildBlock(params BuildBlockParams) *types.Block {
if len(txs) == 0 {
header.TxRoot = types.EmptyRootHash
} else {
header.TxRoot = buildroot.CalculateTransactionsRoot(txs)
header.TxRoot = buildroot.CalculateTransactionsRoot(txs, header.Number)
}

if len(params.Receipts) == 0 {
Expand Down
18 changes: 17 additions & 1 deletion server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -291,7 +291,23 @@ func NewServer(config *Config) (*Server, error) {

if err := forkmanager.ForkManagerInit(
initialParams,
forkManagerFactory[ConsensusType(engineName)],
func(forks *chain.Forks) error {
if err := forkmanager.GetInstance().RegisterHandler(
forkmanager.InitialFork, chain.TxHashHandler, &types.TransactionHashForkV1{}); err != nil {
return err
}

if err := forkmanager.GetInstance().RegisterHandler(
chain.TxHashWithType, chain.TxHashHandler, &types.TransactionHashForkV2{}); err != nil {
return err
}

if fc := forkManagerFactory[ConsensusType(engineName)]; fc != nil {
return fc(forks)
}

return nil
},
config.Chain.Params.Forks); err != nil {
return nil, err
}
Expand Down
16 changes: 14 additions & 2 deletions types/buildroot/buildroot.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
package buildroot

import (
"github.com/0xPolygon/polygon-edge/chain"
"github.com/0xPolygon/polygon-edge/forkmanager"
"github.com/0xPolygon/polygon-edge/helper/keccak"
itrie "github.com/0xPolygon/polygon-edge/state/immutable-trie"
"github.com/0xPolygon/polygon-edge/types"
Expand All @@ -25,9 +27,19 @@ func CalculateReceiptsRoot(receipts []*types.Receipt) types.Hash {
}

// CalculateTransactionsRoot calculates the root of a list of transactions
func CalculateTransactionsRoot(transactions []*types.Transaction) types.Hash {
func CalculateTransactionsRoot(transactions []*types.Transaction, blockNumber uint64) types.Hash {
var handler types.TransactionHashFork

if h := forkmanager.GetInstance().GetHandler(chain.TxHashHandler, blockNumber); h != nil {
//nolint:forcetypeassert
handler = h.(types.TransactionHashFork)
} else {
// because of tests
handler = &types.TransactionHashForkV1{}
}

return CalculateRoot(len(transactions), func(indx int) []byte {
return transactions[indx].MarshalRLPTo(nil)
return handler.SerializeForRootCalculation(transactions[indx], &arenaPool)
})
}

Expand Down
44 changes: 44 additions & 0 deletions types/transaction_fork_hash.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
package types

import (
"math/big"

"github.com/umbracle/fastrlp"
)

const TransactionHashHandler = "TxHash"

type TransactionHashFork interface {
SerializeForRootCalculation(*Transaction, *fastrlp.ArenaPool) []byte
}

var (
_ TransactionHashFork = (*TransactionHashForkV1)(nil)
_ TransactionHashFork = (*TransactionHashForkV2)(nil)
)

type TransactionHashForkV1 struct {
}

func (th *TransactionHashForkV1) SerializeForRootCalculation(t *Transaction, ap *fastrlp.ArenaPool) []byte {
ar := ap.Get()
chainID := t.ChainID
t.ChainID = big.NewInt(0)

defer func() {
ap.Put(ar)

t.ChainID = chainID
}()

ar.Reset()

return t.MarshalRLPWith(ar).MarshalTo(nil)
}

type TransactionHashForkV2 struct {
}

func (th *TransactionHashForkV2) SerializeForRootCalculation(t *Transaction, _ *fastrlp.ArenaPool) []byte {
return t.MarshalRLPTo(nil)
}

0 comments on commit 6021c59

Please sign in to comment.