fix for fast sync regression on post-merge networks (#4224)

* use attached/detached rule difference to prevent PoW rules from influencing fast sync around TTD

Signed-off-by: garyschulte <garyschulte@gmail.com>
pull/4241/head
garyschulte 2 years ago committed by GitHub
parent f43b9ade7e
commit bd9b98c002
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 47
      ethereum/core/src/main/java/org/hyperledger/besu/ethereum/mainnet/MainnetBlockHeaderValidator.java
  2. 46
      ethereum/core/src/main/java/org/hyperledger/besu/ethereum/mainnet/headervalidationrules/AttachedProofOfWorkValidationRule.java
  3. 5
      ethereum/core/src/main/java/org/hyperledger/besu/ethereum/mainnet/headervalidationrules/CalculatedDifficultyValidationRule.java
  4. 7
      ethereum/core/src/main/java/org/hyperledger/besu/ethereum/mainnet/headervalidationrules/ProofOfWorkValidationRule.java
  5. 4
      ethereum/core/src/main/java/org/hyperledger/besu/ethereum/mainnet/headervalidationrules/TimestampMoreRecentThanParent.java

@ -14,9 +14,11 @@
*/ */
package org.hyperledger.besu.ethereum.mainnet; package org.hyperledger.besu.ethereum.mainnet;
import org.hyperledger.besu.config.MergeConfigOptions;
import org.hyperledger.besu.ethereum.core.BlockHeader; import org.hyperledger.besu.ethereum.core.BlockHeader;
import org.hyperledger.besu.ethereum.mainnet.feemarket.BaseFeeMarket; import org.hyperledger.besu.ethereum.mainnet.feemarket.BaseFeeMarket;
import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.AncestryValidationRule; import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.AncestryValidationRule;
import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.AttachedProofOfWorkValidationRule;
import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.BaseFeeMarketBlockHeaderGasPriceValidationRule; import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.BaseFeeMarketBlockHeaderGasPriceValidationRule;
import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.CalculatedDifficultyValidationRule; import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.CalculatedDifficultyValidationRule;
import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.ConstantFieldValidationRule; import org.hyperledger.besu.ethereum.mainnet.headervalidationrules.ConstantFieldValidationRule;
@ -122,22 +124,35 @@ public final class MainnetBlockHeaderValidator {
public static BlockHeaderValidator.Builder createBaseFeeMarketValidator( public static BlockHeaderValidator.Builder createBaseFeeMarketValidator(
final BaseFeeMarket baseFeeMarket) { final BaseFeeMarket baseFeeMarket) {
return new BlockHeaderValidator.Builder() var builder =
.addRule(CalculatedDifficultyValidationRule::new) new BlockHeaderValidator.Builder()
.addRule(new AncestryValidationRule()) .addRule(CalculatedDifficultyValidationRule::new)
.addRule(new GasUsageValidationRule()) .addRule(new AncestryValidationRule())
.addRule( .addRule(new GasUsageValidationRule())
new GasLimitRangeAndDeltaValidationRule( .addRule(
MIN_GAS_LIMIT, Long.MAX_VALUE, Optional.of(baseFeeMarket))) new GasLimitRangeAndDeltaValidationRule(
.addRule(new TimestampMoreRecentThanParent(MINIMUM_SECONDS_SINCE_PARENT)) MIN_GAS_LIMIT, Long.MAX_VALUE, Optional.of(baseFeeMarket)))
.addRule(new TimestampBoundedByFutureParameter(TIMESTAMP_TOLERANCE_S)) .addRule(new TimestampMoreRecentThanParent(MINIMUM_SECONDS_SINCE_PARENT))
.addRule(new ExtraDataMaxLengthValidationRule(BlockHeader.MAX_EXTRA_DATA_BYTES)) .addRule(new TimestampBoundedByFutureParameter(TIMESTAMP_TOLERANCE_S))
.addRule( .addRule(new ExtraDataMaxLengthValidationRule(BlockHeader.MAX_EXTRA_DATA_BYTES))
new ProofOfWorkValidationRule( .addRule((new BaseFeeMarketBlockHeaderGasPriceValidationRule(baseFeeMarket)));
new EpochCalculator.DefaultEpochCalculator(),
PoWHasher.ETHASH_LIGHT, // if merge is enabled, use the attached version of the proof of work validation rule
Optional.of(baseFeeMarket))) if (MergeConfigOptions.isMergeEnabled()) {
.addRule((new BaseFeeMarketBlockHeaderGasPriceValidationRule(baseFeeMarket))); builder.addRule(
new AttachedProofOfWorkValidationRule(
new EpochCalculator.DefaultEpochCalculator(),
PoWHasher.ETHASH_LIGHT,
Optional.of(baseFeeMarket)));
} else {
builder.addRule(
new ProofOfWorkValidationRule(
new EpochCalculator.DefaultEpochCalculator(),
PoWHasher.ETHASH_LIGHT,
Optional.of(baseFeeMarket)));
}
return builder;
} }
static BlockHeaderValidator.Builder createBaseFeeMarketOmmerValidator( static BlockHeaderValidator.Builder createBaseFeeMarketOmmerValidator(

@ -0,0 +1,46 @@
/*
* Copyright Hyperledger Besu Contributors
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
* an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
* specific language governing permissions and limitations under the License.
*
* SPDX-License-Identifier: Apache-2.0
*/
package org.hyperledger.besu.ethereum.mainnet.headervalidationrules;
import org.hyperledger.besu.ethereum.ProtocolContext;
import org.hyperledger.besu.ethereum.core.BlockHeader;
import org.hyperledger.besu.ethereum.mainnet.AttachedBlockHeaderValidationRule;
import org.hyperledger.besu.ethereum.mainnet.EpochCalculator;
import org.hyperledger.besu.ethereum.mainnet.PoWHasher;
import org.hyperledger.besu.ethereum.mainnet.feemarket.FeeMarket;
import java.util.Optional;
/**
* An attached proof of work validation rule that wraps the detached version of the same. Suitable
* for use in block validator stacks supporting the merge.
*/
public class AttachedProofOfWorkValidationRule implements AttachedBlockHeaderValidationRule {
private final ProofOfWorkValidationRule detachedRule;
public AttachedProofOfWorkValidationRule(
final EpochCalculator epochCalculator,
final PoWHasher hasher,
final Optional<FeeMarket> feeMarket) {
this.detachedRule = new ProofOfWorkValidationRule(epochCalculator, hasher, feeMarket);
}
@Override
public boolean validate(
final BlockHeader header, final BlockHeader parent, final ProtocolContext protocolContext) {
return detachedRule.validate(header, parent);
}
}

@ -14,7 +14,6 @@
*/ */
package org.hyperledger.besu.ethereum.mainnet.headervalidationrules; package org.hyperledger.besu.ethereum.mainnet.headervalidationrules;
import org.hyperledger.besu.config.MergeConfigOptions;
import org.hyperledger.besu.ethereum.ProtocolContext; import org.hyperledger.besu.ethereum.ProtocolContext;
import org.hyperledger.besu.ethereum.core.BlockHeader; import org.hyperledger.besu.ethereum.core.BlockHeader;
import org.hyperledger.besu.ethereum.mainnet.AttachedBlockHeaderValidationRule; import org.hyperledger.besu.ethereum.mainnet.AttachedBlockHeaderValidationRule;
@ -37,9 +36,7 @@ public class CalculatedDifficultyValidationRule implements AttachedBlockHeaderVa
@Override @Override
public boolean validate( public boolean validate(
final BlockHeader header, final BlockHeader parent, final ProtocolContext context) { final BlockHeader header, final BlockHeader parent, final ProtocolContext context) {
if (MergeConfigOptions.isMergeEnabled()) {
return true;
}
final BigInteger actualDifficulty = new BigInteger(1, header.getDifficulty().toArray()); final BigInteger actualDifficulty = new BigInteger(1, header.getDifficulty().toArray());
final BigInteger expectedDifficulty = final BigInteger expectedDifficulty =
difficultyCalculator.nextDifficulty(header.getTimestamp(), parent, context); difficultyCalculator.nextDifficulty(header.getTimestamp(), parent, context);

@ -16,7 +16,6 @@ package org.hyperledger.besu.ethereum.mainnet.headervalidationrules;
import static java.lang.Boolean.FALSE; import static java.lang.Boolean.FALSE;
import org.hyperledger.besu.config.MergeConfigOptions;
import org.hyperledger.besu.datatypes.Hash; import org.hyperledger.besu.datatypes.Hash;
import org.hyperledger.besu.ethereum.core.BlockHeader; import org.hyperledger.besu.ethereum.core.BlockHeader;
import org.hyperledger.besu.ethereum.mainnet.DetachedBlockHeaderValidationRule; import org.hyperledger.besu.ethereum.mainnet.DetachedBlockHeaderValidationRule;
@ -70,12 +69,6 @@ public final class ProofOfWorkValidationRule implements DetachedBlockHeaderValid
return false; return false;
} }
// TODO: remove this rule bypass, use post-merge headervalidation rules
// https://github.com/hyperledger/besu/issues/2898
if (MergeConfigOptions.isMergeEnabled()) {
return true;
}
final Hash headerHash = hashHeader(header); final Hash headerHash = hashHeader(header);
PoWSolution solution = PoWSolution solution =
hasher.hash(header.getNonce(), header.getNumber(), epochCalculator, headerHash); hasher.hash(header.getNonce(), header.getNumber(), epochCalculator, headerHash);

@ -16,7 +16,6 @@ package org.hyperledger.besu.ethereum.mainnet.headervalidationrules;
import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkArgument;
import org.hyperledger.besu.config.MergeConfigOptions;
import org.hyperledger.besu.ethereum.core.BlockHeader; import org.hyperledger.besu.ethereum.core.BlockHeader;
import org.hyperledger.besu.ethereum.mainnet.DetachedBlockHeaderValidationRule; import org.hyperledger.besu.ethereum.mainnet.DetachedBlockHeaderValidationRule;
@ -36,9 +35,6 @@ public class TimestampMoreRecentThanParent implements DetachedBlockHeaderValidat
@Override @Override
public boolean validate(final BlockHeader header, final BlockHeader parent) { public boolean validate(final BlockHeader header, final BlockHeader parent) {
if (MergeConfigOptions.isMergeEnabled()) {
return true;
}
return validateTimestamp(header.getTimestamp(), parent.getTimestamp()); return validateTimestamp(header.getTimestamp(), parent.getTimestamp());
} }

Loading…
Cancel
Save