From a2994a25b127c9b362bedaa9e49bd24affb8b90f Mon Sep 17 00:00:00 2001 From: buddh0 Date: Tue, 17 Oct 2023 16:38:07 +0800 Subject: [PATCH] consensus/parlia: fix nextForkHash in Extra filed of block header --- consensus/parlia/parlia.go | 4 ++-- core/forkid/forkid.go | 26 ++++++++++++++++++++++++++ 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/consensus/parlia/parlia.go b/consensus/parlia/parlia.go index 8f8fd18cc1..17c77a3123 100644 --- a/consensus/parlia/parlia.go +++ b/consensus/parlia/parlia.go @@ -950,7 +950,7 @@ func (p *Parlia) Prepare(chain consensus.ChainHeaderReader, header *types.Header } header.Extra = header.Extra[:extraVanity-nextForkHashSize] - nextForkHash := forkid.NewID(p.chainConfig, p.genesisHash, number, header.Time).Hash + nextForkHash := forkid.NextForkHash(p.chainConfig, p.genesisHash, number, header.Time) header.Extra = append(header.Extra, nextForkHash[:]...) if err := p.prepareValidators(header); err != nil { @@ -1084,7 +1084,7 @@ func (p *Parlia) Finalize(chain consensus.ChainHeaderReader, header *types.Heade if err != nil { return err } - nextForkHash := forkid.NewID(p.chainConfig, p.genesisHash, number, header.Time).Hash + nextForkHash := forkid.NextForkHash(p.chainConfig, p.genesisHash, number, header.Time) if !snap.isMajorityFork(hex.EncodeToString(nextForkHash[:])) { log.Debug("there is a possible fork, and your client is not the majority. Please check...", "nextForkHash", hex.EncodeToString(nextForkHash[:])) } diff --git a/core/forkid/forkid.go b/core/forkid/forkid.go index 8964558845..85b0daa96b 100644 --- a/core/forkid/forkid.go +++ b/core/forkid/forkid.go @@ -98,6 +98,32 @@ func NewID(config *params.ChainConfig, genesis common.Hash, head, time uint64) I return ID{Hash: checksumToBytes(hash), Next: 0} } +// NextForkHash calculates the forkHash from genesis to the next fork block number or time +func NextForkHash(config *params.ChainConfig, genesis common.Hash, head uint64, time uint64) [4]byte { + // Calculate the starting checksum from the genesis hash + hash := crc32.ChecksumIEEE(genesis[:]) + + // Calculate the next fork checksum + forksByBlock, forksByTime := gatherForks(config) + for _, fork := range forksByBlock { + if fork > head { + // Checksum the previous hash and nextFork number and return + return checksumToBytes(checksumUpdate(hash, fork)) + } + // Fork already passed, checksum the previous hash and the fork number + hash = checksumUpdate(hash, fork) + } + for _, fork := range forksByTime { + if fork > time { + // Checksum the previous hash and nextFork time and return + return checksumToBytes(checksumUpdate(hash, fork)) + } + // Fork already passed, checksum the previous hash and the fork time + hash = checksumUpdate(hash, fork) + } + return checksumToBytes(hash) +} + // NewIDWithChain calculates the Ethereum fork ID from an existing chain instance. func NewIDWithChain(chain Blockchain) ID { head := chain.CurrentHeader()