Skip to content
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
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
package org.hyperledger.besu.consensus.merge.blockcreation;

import static java.util.stream.Collectors.joining;
import static org.hyperledger.besu.consensus.merge.TransitionUtils.isTerminalProofOfWorkBlock;
import static org.hyperledger.besu.consensus.merge.blockcreation.MergeMiningCoordinator.ForkchoiceResult.Status.INVALID;

import org.hyperledger.besu.consensus.merge.MergeContext;
Expand Down Expand Up @@ -667,96 +666,6 @@ private boolean moveWorldStateTo(final BlockHeader newHead) {
return newWorldState.isPresent();
}

@Override
public boolean latestValidAncestorDescendsFromTerminal(final BlockHeader blockHeader) {
if (blockHeader.getNumber() <= 1L) {
// parent is a genesis block, check for merge-at-genesis
var blockchain = protocolContext.getBlockchain();

return blockchain
.getTotalDifficultyByHash(blockHeader.getBlockHash())
.map(Optional::of)
.orElse(blockchain.getTotalDifficultyByHash(blockHeader.getParentHash()))
.filter(
currDiff -> currDiff.greaterOrEqualThan(mergeContext.getTerminalTotalDifficulty()))
.isPresent();
}

Optional<Hash> validAncestorHash = this.getLatestValidAncestor(blockHeader);
if (validAncestorHash.isPresent()) {
final Optional<BlockHeader> maybeFinalized = mergeContext.getFinalized();
if (maybeFinalized.isPresent()) {
return isDescendantOf(maybeFinalized.get(), blockHeader);
} else {
Optional<BlockHeader> terminalBlockHeader = mergeContext.getTerminalPoWBlock();
if (terminalBlockHeader.isPresent()) {
return isDescendantOf(terminalBlockHeader.get(), blockHeader);
} else {
if (isTerminalProofOfWorkBlock(blockHeader, protocolContext)
|| ancestorIsValidTerminalProofOfWork(blockHeader)) {
Comment thread
fab-10 marked this conversation as resolved.
return true;
} else {
LOG.warn("Couldn't find terminal block, no blocks will be valid");
return false;
}
}
}
} else {
return false;
}
}

/**
* Ancestor is valid terminal proof of work boolean.
*
* @param blockheader the blockheader
* @return the boolean
*/
// package visibility for testing
boolean ancestorIsValidTerminalProofOfWork(final BlockHeader blockheader) {
// this should only happen very close to the transition from PoW to PoS, prior to a finalized
// block. For example, after a full sync of an already-merged chain which does not have
// terminal block info in the genesis config.

// check a 'cached' block which was determined to descend from terminal to short circuit
// in the case of a long period of non-finality
if (Optional.ofNullable(latestDescendsFromTerminal.get())
.map(latestDescendant -> isDescendantOf(latestDescendant, blockheader))
.orElse(Boolean.FALSE)) {
latestDescendsFromTerminal.set(blockheader);
return true;
}

var blockchain = protocolContext.getBlockchain();
Optional<BlockHeader> parent = blockchain.getBlockHeader(blockheader.getParentHash());
do {
LOG.debug(
"checking ancestor {} is valid terminal PoW for {}",
parent.map(BlockHeader::toLogString).orElse("empty"),
blockheader.toLogString());

if (parent.isPresent()) {
if (!parent.get().getDifficulty().equals(Difficulty.ZERO)) {
break;
}
parent = blockchain.getBlockHeader(parent.get().getParentHash());
}

} while (parent.isPresent());

boolean resp =
parent.filter(header -> isTerminalProofOfWorkBlock(header, protocolContext)).isPresent();
LOG.debug(
"checking ancestor {} is valid terminal PoW for {}\n {}",
parent.map(BlockHeader::toLogString).orElse("empty"),
blockheader.toLogString(),
resp);
if (resp) {
latestDescendsFromTerminal.set(blockheader);
}
return resp;
}

@Override
public Optional<Hash> getLatestValidAncestor(final Hash blockHash) {
final var chain = protocolContext.getBlockchain();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,19 +101,11 @@ ForkchoiceResult updateForkChoice(
Optional<Hash> getLatestValidAncestor(BlockHeader blockheader);

/**
* Check if latest valid ancestor descends from terminal.
*
* @param blockHeader the block header
* @return the boolean
*/
boolean latestValidAncestorDescendsFromTerminal(final BlockHeader blockHeader);

/**
* Is descendant of.
* Checks if a block descends from another
*
* @param ancestorBlock the ancestor block
* @param newBlock the new block
* @return the boolean
* @param newBlock the block we want to check if it is descendant
* @return true if newBlock is a descendant of ancestorBlock
*/
boolean isDescendantOf(final BlockHeader ancestorBlock, final BlockHeader newBlock);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -179,12 +179,6 @@ public Optional<Hash> getLatestValidAncestor(final BlockHeader blockHeader) {
return mergeCoordinator.getLatestValidAncestor(blockHeader);
}

@Override
public boolean latestValidAncestorDescendsFromTerminal(final BlockHeader blockHeader) {
// this is nonsensical pre-merge, but should be fine to delegate
return mergeCoordinator.latestValidAncestorDescendsFromTerminal(blockHeader);
}

@Override
public boolean isBackwardSyncing() {
return mergeCoordinator.isBackwardSyncing();
Expand Down
Loading