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

ETC Atlantis fork #179

Merged
merged 18 commits into from
Nov 15, 2019
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 @@ -113,6 +113,18 @@ public interface GenesisConfigOptions {
*/
OptionalLong getDefuseDifficultyBombBlockNumber();

/**
* Block number for Atlantis fork on Classic network Note, this fork happen after Defuse
* Difficulty Bomb fork and before Agharta fork ECIP-1054: Atlantis EVM and Protocol Upgrades
* Enable the outstanding Ethereum Foundation Spurious Dragon and Byzantium network protocol
* upgrades for the Ethereum Classic network.
*
* @see <a
* href="https://ecips.ethereumclassic.org/ECIPs/ecip-1054">https://ecips.ethereumclassic.org/ECIPs/ecip-1054</a>
* @return block number for Atlantis fork on Classic network
*/
OptionalLong getAtlantisBlockNumber();

Optional<BigInteger> getChainId();

OptionalInt getContractSizeLimit();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -220,6 +220,11 @@ public OptionalLong getDefuseDifficultyBombBlockNumber() {
return getOptionalLong("ecip1041block");
}

@Override
public OptionalLong getAtlantisBlockNumber() {
return getOptionalLong("atlantisblock");
}

@Override
public Optional<BigInteger> getChainId() {
return getOptionalBigInteger("chainid");
Expand Down
1 change: 1 addition & 0 deletions config/src/main/resources/classic.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
"diehardBlock": 3000000,
"gothamBlock": 5000001,
"ecip1041Block": 5900000,
"atlantisBlock": 8772000,
"ethash": {

}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ public class StubGenesisConfigOptions implements GenesisConfigOptions {
private OptionalLong diehardBlockNumber = OptionalLong.empty();
private OptionalLong gothamBlockNumber = OptionalLong.empty();
private OptionalLong defuseDifficultyBombBlockNumber = OptionalLong.empty();
private OptionalLong atlantisBlockNumber = OptionalLong.empty();
private Optional<BigInteger> chainId = Optional.empty();
private OptionalInt contractSizeLimit = OptionalInt.empty();
private OptionalInt stackSizeLimit = OptionalInt.empty();
Expand Down Expand Up @@ -151,6 +152,11 @@ public OptionalLong getDefuseDifficultyBombBlockNumber() {
return defuseDifficultyBombBlockNumber;
}

@Override
public OptionalLong getAtlantisBlockNumber() {
return atlantisBlockNumber;
}

@Override
public OptionalInt getContractSizeLimit() {
return contractSizeLimit;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import org.hyperledger.besu.ethereum.core.ProcessableBlockHeader;
import org.hyperledger.besu.ethereum.core.Wei;
import org.hyperledger.besu.ethereum.core.WorldUpdater;
import org.hyperledger.besu.ethereum.mainnet.AbstractBlockProcessor.TransactionReceiptFactory;

import java.math.BigInteger;
import java.util.List;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
*/
package org.hyperledger.besu.ethereum.mainnet;

import org.hyperledger.besu.ethereum.core.Hash;
import org.hyperledger.besu.util.uint.UInt256;

import java.math.BigInteger;
Expand Down Expand Up @@ -64,6 +65,29 @@ public abstract class ClassicDifficultyCalculators {
return difficulty;
};

public static DifficultyCalculator<Void> EIP100 =
(time, parent, protocolContext) -> {
final BigInteger parentDifficulty = difficulty(parent.getDifficulty());
final boolean hasOmmers = !parent.getOmmersHash().equals(Hash.EMPTY_LIST_HASH);
final BigInteger difficulty =
ensureMinimumDifficulty(
BigInteger.valueOf(byzantiumX(time, parent.getTimestamp(), hasOmmers))
.multiply(parentDifficulty.divide(DIFFICULTY_BOUND_DIVISOR))
.add(parentDifficulty));
return difficulty;
};

private static long byzantiumX(
final long blockTime, final long parentTime, final boolean hasOmmers) {
long x = (blockTime - parentTime) / 9L;
if (hasOmmers) {
x = 2 - x;
} else {
x = 1 - x;
}
return Math.max(x, -99L);
}

private static BigInteger adjustForDifficultyDelay(
final long periodCount, final BigInteger difficulty) {
return difficulty.add(BIGINT_2.pow(Ints.checkedCast(periodCount - DELAY - 2)));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,15 @@
*/
package org.hyperledger.besu.ethereum.mainnet;

import org.hyperledger.besu.ethereum.core.Account;
import org.hyperledger.besu.ethereum.core.TransactionReceipt;
import org.hyperledger.besu.ethereum.core.Wei;
import org.hyperledger.besu.ethereum.core.WorldState;
import org.hyperledger.besu.ethereum.mainnet.contractvalidation.MaxCodeSizeRule;
import org.hyperledger.besu.ethereum.vm.MessageFrame;

import java.math.BigInteger;
import java.util.Collections;
import java.util.Optional;
import java.util.OptionalInt;

Expand Down Expand Up @@ -83,4 +89,61 @@ public static ProtocolSpecBuilder<Void> defuseDifficultyBombDefinition(
gasCalculator -> new MainnetTransactionValidator(gasCalculator, true, chainId))
.name("DefuseDifficultyBomb");
}

public static ProtocolSpecBuilder<Void> atlantisDefinition(
final Optional<BigInteger> chainId,
final OptionalInt configContractSizeLimit,
final OptionalInt configStackSizeLimit,
final boolean enableRevertReason) {
final int contractSizeLimit =
configContractSizeLimit.orElse(MainnetProtocolSpecs.SPURIOUS_DRAGON_CONTRACT_SIZE_LIMIT);
final int stackSizeLimit = configStackSizeLimit.orElse(MessageFrame.DEFAULT_MAX_STACK_SIZE);
return gothamDefinition(chainId, configContractSizeLimit, configStackSizeLimit)
.evmBuilder(MainnetEvmRegistries::byzantium)
.gasCalculator(SpuriousDragonGasCalculator::new)
.skipZeroBlockRewards(true)
.messageCallProcessorBuilder(
(evm, precompileContractRegistry) ->
new MainnetMessageCallProcessor(evm, precompileContractRegistry))
.precompileContractRegistryBuilder(MainnetPrecompiledContractRegistries::byzantium)
.difficultyCalculator(ClassicDifficultyCalculators.EIP100)
.transactionReceiptFactory(
enableRevertReason
? ClassicProtocolSpecs::byzantiumTransactionReceiptFactoryWithReasonEnabled
: ClassicProtocolSpecs::byzantiumTransactionReceiptFactory)
.contractCreationProcessorBuilder(
(gasCalculator, evm) ->
new MainnetContractCreationProcessor(
gasCalculator,
evm,
true,
Collections.singletonList(MaxCodeSizeRule.of(contractSizeLimit)),
1))
.transactionProcessorBuilder(
(gasCalculator,
transactionValidator,
contractCreationProcessor,
messageCallProcessor) ->
new MainnetTransactionProcessor(
gasCalculator,
transactionValidator,
contractCreationProcessor,
messageCallProcessor,
true,
stackSizeLimit,
Account.DEFAULT_VERSION))
.name("Atlantis");
}

private static TransactionReceipt byzantiumTransactionReceiptFactory(
final TransactionProcessor.Result result, final WorldState worldState, final long gasUsed) {
return new TransactionReceipt(
result.isSuccessful() ? 1 : 0, gasUsed, result.getLogs(), Optional.empty());
}

private static TransactionReceipt byzantiumTransactionReceiptFactoryWithReasonEnabled(
final TransactionProcessor.Result result, final WorldState worldState, final long gasUsed) {
return new TransactionReceipt(
result.isSuccessful() ? 1 : 0, gasUsed, result.getLogs(), result.getRevertReason());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,14 @@ public ProtocolSchedule<C> createProtocolSchedule() {
config.getDefuseDifficultyBombBlockNumber(),
ClassicProtocolSpecs.defuseDifficultyBombDefinition(
chainId, config.getContractSizeLimit(), config.getEvmStackSize()));
addProtocolSpec(
protocolSchedule,
config.getAtlantisBlockNumber(),
ClassicProtocolSpecs.atlantisDefinition(
chainId,
config.getContractSizeLimit(),
config.getEvmStackSize(),
isRevertReasonEnabled));

LOG.info("Protocol schedule created with milestones: {}", protocolSchedule.listMilestones());
return protocolSchedule;
Expand Down Expand Up @@ -221,6 +229,14 @@ private long validateForkOrder(
}

private void validateForkOrdering() {
if (config.getDaoForkBlock().isEmpty()) {
validateClassicForkOrdering();
} else {
validateEthereumForkOrdering();
}
}

private void validateEthereumForkOrdering() {
long lastForkBlock = 0;
lastForkBlock = validateForkOrder("Homestead", config.getHomesteadBlockNumber(), lastForkBlock);
lastForkBlock = validateForkOrder("DaoFork", config.getDaoForkBlock(), lastForkBlock);
Expand All @@ -238,4 +254,19 @@ private void validateForkOrdering() {
lastForkBlock = validateForkOrder("Istanbul", config.getIstanbulBlockNumber(), lastForkBlock);
assert (lastForkBlock >= 0);
}

private void validateClassicForkOrdering() {
long lastForkBlock = 0;
lastForkBlock = validateForkOrder("Homestead", config.getHomesteadBlockNumber(), lastForkBlock);
lastForkBlock =
validateForkOrder(
"ClassicTangerineWhistle", config.getEcip1015BlockNumber(), lastForkBlock);
lastForkBlock = validateForkOrder("DieHard", config.getDieHardBlockNumber(), lastForkBlock);
lastForkBlock = validateForkOrder("Gotham", config.getGothamBlockNumber(), lastForkBlock);
lastForkBlock =
validateForkOrder(
"DefuseDifficultyBomb", config.getDefuseDifficultyBombBlockNumber(), lastForkBlock);
lastForkBlock = validateForkOrder("Atlantis", config.getAtlantisBlockNumber(), lastForkBlock);
assert (lastForkBlock >= 0);
}
}