mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-08-18 18:02:24 +00:00
Merge pull request #5 from TeamEGEM/expEGEMdiff
Exp egem diff and era transitions.
This commit is contained in:
commit
0e38fa83b7
3 changed files with 160 additions and 171 deletions
|
|
@ -36,10 +36,24 @@ import (
|
||||||
|
|
||||||
// Ethash proof-of-work protocol constants.
|
// Ethash proof-of-work protocol constants.
|
||||||
var (
|
var (
|
||||||
FrontierBlockReward *big.Int = big.NewInt(9000000000000000000) // Block reward in wei for successfully mining a block
|
|
||||||
ByzantiumBlockReward *big.Int = big.NewInt(3e+18) // Block reward in wei for successfully mining a block upward from Byzantium
|
|
||||||
maxUncles = 2 // Maximum number of uncles allowed in a single block
|
maxUncles = 2 // Maximum number of uncles allowed in a single block
|
||||||
allowedFutureBlockTime = 15 * time.Second // Max time from current time allowed for blocks, before they're considered future blocks
|
allowedFutureBlockTime = 15 * time.Second // Max time from current time allowed for blocks, before they're considered future blocks
|
||||||
|
FrontierBlockReward *big.Int = big.NewInt(5e+18) // Not used will be removed in furture EGEM update.
|
||||||
|
ByzantiumBlockReward *big.Int = big.NewInt(3e+18) // Not used will be removed in furture EGEM update.
|
||||||
|
)
|
||||||
|
|
||||||
|
// EGEM Variables
|
||||||
|
var (
|
||||||
|
egem0BlockReward *big.Int = big.NewInt(8e+18) // 8 EGEM Block reward in wei for successfully mining a block.
|
||||||
|
egem1BlockReward *big.Int = big.NewInt(4e+18) // 4 EGEM Block reward in wei for successfully mining a block.
|
||||||
|
egem2BlockReward *big.Int = big.NewInt(2e+18) // 2 EGEM Block reward in wei for successfully mining a block.
|
||||||
|
egem0DevReward *big.Int = big.NewInt(1e+18) // Era0 Dev reward 1 EGEM per block.
|
||||||
|
egem1DevReward *big.Int = big.NewInt(500000000000000000) // Era1 Dev reward 0.5 EGEM per block.
|
||||||
|
egem2DevReward *big.Int = big.NewInt(100000000000000000) // Era2 Dev reward 0.1 EGEM per block.
|
||||||
|
egemRewardSwitchBlockEra0 *big.Int = big.NewInt(5000) //5K Block era transition
|
||||||
|
egemRewardSwitchBlockEra1 *big.Int = big.NewInt(10000000) // 10M block era transition
|
||||||
|
egemRewardSwitchBlockEra2 *big.Int = big.NewInt(20000000) // 20M block era transtiton
|
||||||
|
devFund = common.HexToAddress("0xc393659c2918a64cdfb44d463de9c747aa4ce3f7") //r
|
||||||
)
|
)
|
||||||
|
|
||||||
// Various error messages to mark blocks invalid. These should be private to
|
// Various error messages to mark blocks invalid. These should be private to
|
||||||
|
|
@ -298,11 +312,11 @@ func CalcDifficulty(config *params.ChainConfig, time uint64, parent *types.Heade
|
||||||
next := new(big.Int).Add(parent.Number, big1)
|
next := new(big.Int).Add(parent.Number, big1)
|
||||||
switch {
|
switch {
|
||||||
case config.IsByzantium(next):
|
case config.IsByzantium(next):
|
||||||
return calcDifficultyByzantium(time, parent)
|
return calcDifficultyEGEM(time, parent)
|
||||||
case config.IsHomestead(next):
|
case config.IsHomestead(next):
|
||||||
return calcDifficultyHomestead(time, parent)
|
return calcDifficultyEGEM(time, parent)
|
||||||
default:
|
default:
|
||||||
return calcDifficultyFrontier(time, parent)
|
return calcDifficultyEGEM(time, parent)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -313,149 +327,78 @@ var (
|
||||||
big2 = big.NewInt(2)
|
big2 = big.NewInt(2)
|
||||||
big9 = big.NewInt(9)
|
big9 = big.NewInt(9)
|
||||||
big10 = big.NewInt(10)
|
big10 = big.NewInt(10)
|
||||||
|
big15 = big.NewInt(15)
|
||||||
|
big20 = big.NewInt(20)
|
||||||
|
big50 = big.NewInt(50)
|
||||||
bigMinus99 = big.NewInt(-99)
|
bigMinus99 = big.NewInt(-99)
|
||||||
big2999999 = big.NewInt(2999999)
|
big2999999 = big.NewInt(2999999)
|
||||||
)
|
)
|
||||||
|
|
||||||
// calcDifficultyByzantium is the difficulty adjustment algorithm. It returns
|
// EGEM Era Difficulty Algo
|
||||||
// the difficulty that a new block should have when created at time given the
|
//
|
||||||
// parent block's time and difficulty. The calculation uses the Byzantium rules.
|
// Launch 0 - 5000 50% Difficulty*
|
||||||
func calcDifficultyByzantium(time uint64, parent *types.Header) *big.Int {
|
// Requiem Era0 5001 - 10,000,000 20% Difficulty**
|
||||||
// https://github.com/ethereum/EIPs/issues/100.
|
// Solstice Era1 10,000,001 - 20,000,000 15% Difficulty*
|
||||||
// algorithm:
|
// Oblivion Era2 20,000,001 + 10% Difficulty*
|
||||||
// diff = (parent_diff +
|
//
|
||||||
// (parent_diff / 2048 * max((2 if len(parent.uncles) else 1) - ((timestamp - parent.timestamp) // 9), -99))
|
// * +/- adjustment per block
|
||||||
// ) + 2^(periodCount - 2)
|
// ** Dev fee is enabled at this Era start.
|
||||||
|
//
|
||||||
|
|
||||||
bigTime := new(big.Int).SetUint64(time)
|
func calcDifficultyEGEM(time uint64, parent *types.Header) *big.Int {
|
||||||
bigParentTime := new(big.Int).Set(parent.Time)
|
|
||||||
|
|
||||||
// holds intermediate values to make the algo easier to read & audit
|
|
||||||
x := new(big.Int)
|
|
||||||
y := new(big.Int)
|
|
||||||
|
|
||||||
// (2 if len(parent_uncles) else 1) - (block_timestamp - parent_timestamp) // 9
|
|
||||||
x.Sub(bigTime, bigParentTime)
|
|
||||||
x.Div(x, big9)
|
|
||||||
if parent.UncleHash == types.EmptyUncleHash {
|
|
||||||
x.Sub(big1, x)
|
|
||||||
} else {
|
|
||||||
x.Sub(big2, x)
|
|
||||||
}
|
|
||||||
// max((2 if len(parent_uncles) else 1) - (block_timestamp - parent_timestamp) // 9, -99)
|
|
||||||
if x.Cmp(bigMinus99) < 0 {
|
|
||||||
x.Set(bigMinus99)
|
|
||||||
}
|
|
||||||
// parent_diff + (parent_diff / 2048 * max((2 if len(parent.uncles) else 1) - ((timestamp - parent.timestamp) // 9), -99))
|
|
||||||
y.Div(parent.Difficulty, params.DifficultyBoundDivisor)
|
|
||||||
x.Mul(y, x)
|
|
||||||
x.Add(parent.Difficulty, x)
|
|
||||||
|
|
||||||
// minimum difficulty can ever be (before exponential factor)
|
|
||||||
if x.Cmp(params.MinimumDifficulty) < 0 {
|
|
||||||
x.Set(params.MinimumDifficulty)
|
|
||||||
}
|
|
||||||
// calculate a fake block number for the ice-age delay:
|
|
||||||
// https://github.com/ethereum/EIPs/pull/669
|
|
||||||
// fake_block_number = min(0, block.number - 3_000_000
|
|
||||||
fakeBlockNumber := new(big.Int)
|
|
||||||
if parent.Number.Cmp(big2999999) >= 0 {
|
|
||||||
fakeBlockNumber = fakeBlockNumber.Sub(parent.Number, big2999999) // Note, parent is 1 less than the actual block number
|
|
||||||
}
|
|
||||||
// for the exponential factor
|
|
||||||
periodCount := fakeBlockNumber
|
|
||||||
periodCount.Div(periodCount, expDiffPeriod)
|
|
||||||
|
|
||||||
// the exponential factor, commonly referred to as "the bomb"
|
|
||||||
// diff = diff + 2^(periodCount - 2)
|
|
||||||
if periodCount.Cmp(big1) > 0 {
|
|
||||||
y.Sub(periodCount, big2)
|
|
||||||
y.Exp(big2, y, nil)
|
|
||||||
x.Add(x, y)
|
|
||||||
}
|
|
||||||
return x
|
|
||||||
}
|
|
||||||
|
|
||||||
// calcDifficultyHomestead is the difficulty adjustment algorithm. It returns
|
|
||||||
// the difficulty that a new block should have when created at time given the
|
|
||||||
// parent block's time and difficulty. The calculation uses the Homestead rules.
|
|
||||||
func calcDifficultyHomestead(time uint64, parent *types.Header) *big.Int {
|
|
||||||
// https://github.com/ethereum/EIPs/blob/master/EIPS/eip-2.md
|
|
||||||
// algorithm:
|
|
||||||
// diff = (parent_diff +
|
|
||||||
// (parent_diff / 2048 * max(1 - (block_timestamp - parent_timestamp) // 10, -99))
|
|
||||||
// ) + 2^(periodCount - 2)
|
|
||||||
|
|
||||||
bigTime := new(big.Int).SetUint64(time)
|
|
||||||
bigParentTime := new(big.Int).Set(parent.Time)
|
|
||||||
|
|
||||||
// holds intermediate values to make the algo easier to read & audit
|
|
||||||
x := new(big.Int)
|
|
||||||
y := new(big.Int)
|
|
||||||
|
|
||||||
// 1 - (block_timestamp - parent_timestamp) // 10
|
|
||||||
x.Sub(bigTime, bigParentTime)
|
|
||||||
x.Div(x, big10)
|
|
||||||
x.Sub(big1, x)
|
|
||||||
|
|
||||||
// max(1 - (block_timestamp - parent_timestamp) // 10, -99)
|
|
||||||
if x.Cmp(bigMinus99) < 0 {
|
|
||||||
x.Set(bigMinus99)
|
|
||||||
}
|
|
||||||
// (parent_diff + parent_diff // 2048 * max(1 - (block_timestamp - parent_timestamp) // 10, -99))
|
|
||||||
y.Div(parent.Difficulty, params.DifficultyBoundDivisor)
|
|
||||||
x.Mul(y, x)
|
|
||||||
x.Add(parent.Difficulty, x)
|
|
||||||
|
|
||||||
// minimum difficulty can ever be (before exponential factor)
|
|
||||||
if x.Cmp(params.MinimumDifficulty) < 0 {
|
|
||||||
x.Set(params.MinimumDifficulty)
|
|
||||||
}
|
|
||||||
// for the exponential factor
|
|
||||||
periodCount := new(big.Int).Add(parent.Number, big1)
|
|
||||||
periodCount.Div(periodCount, expDiffPeriod)
|
|
||||||
|
|
||||||
// the exponential factor, commonly referred to as "the bomb"
|
|
||||||
// diff = diff + 2^(periodCount - 2)
|
|
||||||
if periodCount.Cmp(big1) > 0 {
|
|
||||||
y.Sub(periodCount, big2)
|
|
||||||
y.Exp(big2, y, nil)
|
|
||||||
x.Add(x, y)
|
|
||||||
}
|
|
||||||
return x
|
|
||||||
}
|
|
||||||
|
|
||||||
// calcDifficultyFrontier is the difficulty adjustment algorithm. It returns the
|
|
||||||
// difficulty that a new block should have when created at time given the parent
|
|
||||||
// block's time and difficulty. The calculation uses the Frontier rules.
|
|
||||||
func calcDifficultyFrontier(time uint64, parent *types.Header) *big.Int {
|
|
||||||
diff := new(big.Int)
|
diff := new(big.Int)
|
||||||
adjust := new(big.Int).Div(parent.Difficulty, params.DifficultyBoundDivisor)
|
adjust0 := new(big.Int).Div(parent.Difficulty, big10)
|
||||||
|
adjust1 := new(big.Int).Div(parent.Difficulty, big15)
|
||||||
|
adjust2 := new(big.Int).Div(parent.Difficulty, big20)
|
||||||
|
adjust3 := new(big.Int).Div(parent.Difficulty, big50)
|
||||||
|
|
||||||
bigTime := new(big.Int)
|
bigTime := new(big.Int)
|
||||||
bigParentTime := new(big.Int)
|
bigParentTime := new(big.Int)
|
||||||
|
|
||||||
bigTime.SetUint64(time)
|
bigTime.SetUint64(time)
|
||||||
bigParentTime.Set(parent.Time)
|
bigParentTime.Set(parent.Time)
|
||||||
|
|
||||||
|
if (parent.Number.Cmp(egemRewardSwitchBlockEra2) == 1) {
|
||||||
if bigTime.Sub(bigTime, bigParentTime).Cmp(params.DurationLimit) < 0 {
|
if bigTime.Sub(bigTime, bigParentTime).Cmp(params.DurationLimit) < 0 {
|
||||||
diff.Add(parent.Difficulty, adjust)
|
diff.Add(parent.Difficulty, adjust0)
|
||||||
} else {
|
} else {
|
||||||
diff.Sub(parent.Difficulty, adjust)
|
diff.Sub(parent.Difficulty, adjust0)
|
||||||
}
|
}
|
||||||
if diff.Cmp(params.MinimumDifficulty) < 0 {
|
if diff.Cmp(params.MinimumDifficulty) < 0 {
|
||||||
diff.Set(params.MinimumDifficulty)
|
diff.Set(params.MinimumDifficulty)
|
||||||
}
|
}
|
||||||
|
return diff
|
||||||
periodCount := new(big.Int).Add(parent.Number, big1)
|
} else if (parent.Number.Cmp(egemRewardSwitchBlockEra1) == 1) {
|
||||||
periodCount.Div(periodCount, expDiffPeriod)
|
if bigTime.Sub(bigTime, bigParentTime).Cmp(params.DurationLimit) < 0 {
|
||||||
if periodCount.Cmp(big1) > 0 {
|
diff.Add(parent.Difficulty, adjust1)
|
||||||
// diff = diff + 2^(periodCount - 2)
|
} else {
|
||||||
expDiff := periodCount.Sub(periodCount, big2)
|
diff.Sub(parent.Difficulty, adjust1)
|
||||||
expDiff.Exp(big2, expDiff, nil)
|
}
|
||||||
diff.Add(diff, expDiff)
|
if diff.Cmp(params.MinimumDifficulty) < 0 {
|
||||||
diff = math.BigMax(diff, params.MinimumDifficulty)
|
diff.Set(params.MinimumDifficulty)
|
||||||
}
|
}
|
||||||
return diff
|
return diff
|
||||||
|
} else if (parent.Number.Cmp(egemRewardSwitchBlockEra0) == 1) {
|
||||||
|
if bigTime.Sub(bigTime, bigParentTime).Cmp(params.DurationLimit) < 0 {
|
||||||
|
diff.Add(parent.Difficulty, adjust2)
|
||||||
|
} else {
|
||||||
|
diff.Sub(parent.Difficulty, adjust2)
|
||||||
|
}
|
||||||
|
if diff.Cmp(params.MinimumDifficulty) < 0 {
|
||||||
|
diff.Set(params.MinimumDifficulty)
|
||||||
|
}
|
||||||
|
return diff
|
||||||
|
} else {
|
||||||
|
if bigTime.Sub(bigTime, bigParentTime).Cmp(params.DurationLimit) < 0 {
|
||||||
|
diff.Add(parent.Difficulty, adjust3)
|
||||||
|
} else {
|
||||||
|
diff.Sub(parent.Difficulty, adjust3)
|
||||||
|
}
|
||||||
|
if diff.Cmp(params.MinimumDifficulty) < 0 {
|
||||||
|
diff.Set(params.MinimumDifficulty)
|
||||||
|
}
|
||||||
|
return diff
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// VerifySeal implements consensus.Engine, checking whether the given block satisfies
|
// VerifySeal implements consensus.Engine, checking whether the given block satisfies
|
||||||
|
|
@ -532,23 +475,86 @@ var (
|
||||||
// reward. The total reward consists of the static block reward and rewards for
|
// reward. The total reward consists of the static block reward and rewards for
|
||||||
// included uncles. The coinbase of each uncle block is also rewarded.
|
// included uncles. The coinbase of each uncle block is also rewarded.
|
||||||
func accumulateRewards(config *params.ChainConfig, state *state.StateDB, header *types.Header, uncles []*types.Header) {
|
func accumulateRewards(config *params.ChainConfig, state *state.StateDB, header *types.Header, uncles []*types.Header) {
|
||||||
|
|
||||||
// Select the correct block reward based on chain progression
|
// Select the correct block reward based on chain progression
|
||||||
blockReward := FrontierBlockReward
|
block0Reward := egem0BlockReward
|
||||||
if config.IsByzantium(header.Number) {
|
block1Reward := egem1BlockReward
|
||||||
blockReward = ByzantiumBlockReward
|
block2Reward := egem2BlockReward
|
||||||
}
|
d0Reward := egem0DevReward
|
||||||
|
d1Reward := egem1DevReward
|
||||||
|
d2Reward := egem2DevReward
|
||||||
|
|
||||||
// Accumulate the rewards for the miner and any included uncles
|
// Accumulate the rewards for the miner and any included uncles
|
||||||
reward := new(big.Int).Set(blockReward)
|
|
||||||
|
// Final form of rewards and blocks 2/0.1. 10% Difficulty adjustment per block
|
||||||
|
if (header.Number.Cmp(egemRewardSwitchBlockEra2) == 1) {
|
||||||
|
reward := new(big.Int).Set(block2Reward)
|
||||||
r := new(big.Int)
|
r := new(big.Int)
|
||||||
for _, uncle := range uncles {
|
for _, uncle := range uncles {
|
||||||
r.Add(uncle.Number, big8)
|
r.Add(uncle.Number, big8)
|
||||||
r.Sub(r, header.Number)
|
r.Sub(r, header.Number)
|
||||||
r.Mul(r, blockReward)
|
r.Mul(r, reward)
|
||||||
r.Div(r, big8)
|
r.Div(r, big8)
|
||||||
state.AddBalance(uncle.Coinbase, r)
|
|
||||||
|
|
||||||
r.Div(blockReward, big32)
|
r.Div(reward, big32)
|
||||||
reward.Add(reward, r)
|
reward.Add(reward, r)
|
||||||
}
|
}
|
||||||
state.AddBalance(header.Coinbase, reward)
|
state.AddBalance(header.Coinbase, reward)
|
||||||
|
|
||||||
|
//dev rewards
|
||||||
|
state.AddBalance(devFund, d2Reward) //ridz
|
||||||
|
|
||||||
|
//Era1 Reward scheme Block and dev reward halving 4/0.5. 15% Difficulty adjustment per block
|
||||||
|
} else if (header.Number.Cmp(egemRewardSwitchBlockEra1) == 1) {
|
||||||
|
reward := new(big.Int).Set(block1Reward)
|
||||||
|
r := new(big.Int)
|
||||||
|
for _, uncle := range uncles {
|
||||||
|
r.Add(uncle.Number, big8)
|
||||||
|
r.Sub(r, header.Number)
|
||||||
|
r.Mul(r, reward)
|
||||||
|
r.Div(r, big8)
|
||||||
|
|
||||||
|
r.Div(reward, big32)
|
||||||
|
reward.Add(reward, r)
|
||||||
|
}
|
||||||
|
state.AddBalance(header.Coinbase, reward)
|
||||||
|
|
||||||
|
//dev rewards
|
||||||
|
state.AddBalance(devFund, d1Reward) //ridz
|
||||||
|
|
||||||
|
//Era0 Reward of block and dev reward 8/1 EGEM. 20% Difficulty adjustment per block
|
||||||
|
} else if (header.Number.Cmp(egemRewardSwitchBlockEra0) == 1) {
|
||||||
|
reward := new(big.Int).Set(block0Reward)
|
||||||
|
r := new(big.Int)
|
||||||
|
for _, uncle := range uncles {
|
||||||
|
r.Add(uncle.Number, big8)
|
||||||
|
r.Sub(r, header.Number)
|
||||||
|
r.Mul(r, reward)
|
||||||
|
r.Div(r, big8)
|
||||||
|
|
||||||
|
r.Div(reward, big32)
|
||||||
|
reward.Add(reward, r)
|
||||||
|
}
|
||||||
|
state.AddBalance(header.Coinbase, reward)
|
||||||
|
|
||||||
|
//dev rewards
|
||||||
|
state.AddBalance(devFund, d0Reward) //ridz
|
||||||
|
|
||||||
|
// Launch upto block 5000 with a 50% Difficulty adjustment per block, 8 EGEM reward.
|
||||||
|
} else {
|
||||||
|
reward := new(big.Int).Set(block0Reward)
|
||||||
|
r := new(big.Int)
|
||||||
|
for _, uncle := range uncles {
|
||||||
|
r.Add(uncle.Number, big8)
|
||||||
|
r.Sub(r, header.Number)
|
||||||
|
r.Mul(r, reward)
|
||||||
|
r.Div(r, big8)
|
||||||
|
|
||||||
|
r.Div(reward, big32)
|
||||||
|
reward.Add(reward, r)
|
||||||
|
}
|
||||||
|
|
||||||
|
state.AddBalance(header.Coinbase, reward)
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -145,26 +145,9 @@ func (c *CliqueConfig) String() string {
|
||||||
|
|
||||||
// String implements the fmt.Stringer interface.
|
// String implements the fmt.Stringer interface.
|
||||||
func (c *ChainConfig) String() string {
|
func (c *ChainConfig) String() string {
|
||||||
var engine interface{}
|
|
||||||
switch {
|
return fmt.Sprintf("{ChainID: %v EGEM Geth}",
|
||||||
case c.Ethash != nil:
|
|
||||||
engine = c.Ethash
|
|
||||||
case c.Clique != nil:
|
|
||||||
engine = c.Clique
|
|
||||||
default:
|
|
||||||
engine = "unknown"
|
|
||||||
}
|
|
||||||
return fmt.Sprintf("{ChainID: %v Homestead: %v DAO: %v DAOSupport: %v EIP150: %v EIP155: %v EIP158: %v Byzantium: %v Constantinople: %v Engine: %v}",
|
|
||||||
c.ChainId,
|
c.ChainId,
|
||||||
c.HomesteadBlock,
|
|
||||||
c.DAOForkBlock,
|
|
||||||
c.DAOForkSupport,
|
|
||||||
c.EIP150Block,
|
|
||||||
c.EIP155Block,
|
|
||||||
c.EIP158Block,
|
|
||||||
c.ByzantiumBlock,
|
|
||||||
c.ConstantinopleBlock,
|
|
||||||
engine,
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -24,7 +24,7 @@ const (
|
||||||
VersionMajor = 1 // Major version component of the current release
|
VersionMajor = 1 // Major version component of the current release
|
||||||
VersionMinor = 0 // Minor version component of the current release
|
VersionMinor = 0 // Minor version component of the current release
|
||||||
VersionPatch = 0 // Patch version component of the current release
|
VersionPatch = 0 // Patch version component of the current release
|
||||||
VersionMeta = "usable" // Version metadata to append to the version string
|
VersionMeta = "fresco" // Version metadata to append to the version string
|
||||||
)
|
)
|
||||||
|
|
||||||
// Version holds the textual version string.
|
// Version holds the textual version string.
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue