获取区块奖励过程

来源:互联网 发布:mysql建索引优化 编辑:程序博客网 时间:2024/05/22 02:07

区块奖励入口代码:go-ethereum\core\chain_makers.go  line:182


ethash.AccumulateRewards(config, statedb, header , uncles)

其中config:
config *params.ChainConfig //链配置
statedb = state.New(parent.Root(), state.NewDatabase(db))//状态DB建立
header为该块头,可以根据配置、父块组合出来 header := makeHeader(config, parent, statedb),实际使用时,只用到header.Number和header.coinBase
parent为*types.Block实例,父块
db即ethdb.Database实例
uncles:叔节点,实际使用时,只用到header.Number和header.coinBase


makeHeader函数:
func makeHeader(config *params.ChainConfig, parent *types.Block, state *state.StateDB) *types.Header {
var time *big.Int
if parent.Time() == nil {
time = big.NewInt(10)
} else {
time = new(big.Int).Add(parent.Time(), big.NewInt(10)) // block time is fixed at 10 seconds
}


return &types.Header{
Root:       state.IntermediateRoot(config.IsEIP158(parent.Number())),
ParentHash: parent.Hash(),
Coinbase:   parent.Coinbase(),
Difficulty: ethash.CalcDifficulty(config, time.Uint64(), &types.Header{
Number:     parent.Number(),
Time:       new(big.Int).Sub(time, big.NewInt(10)),
Difficulty: parent.Difficulty(),
UncleHash:  parent.UncleHash(),
}),
GasLimit: CalcGasLimit(parent),
GasUsed:  new(big.Int),
Number:   new(big.Int).Add(parent.Number(), common.Big1),
Time:     time,
}
}


计算奖励:
func AccumulateRewards(config *params.ChainConfig, state *state.StateDB, header *types.Header, uncles []*types.Header) {
// Select the correct block reward based on chain progression
blockReward := frontierBlockReward
if config.IsByzantium(header.Number) {
blockReward = byzantiumBlockReward
}
// Accumulate the rewards for the miner and any included uncles
reward := new(big.Int).Set(blockReward)
r := new(big.Int)
for _, uncle := range uncles {//叔块奖励
r.Add(uncle.Number, big8)
r.Sub(r, header.Number)
r.Mul(r, blockReward)
r.Div(r, big8)
state.AddBalance(uncle.Coinbase, r)//给叔块建立者奖励


r.Div(blockReward, big32)
reward.Add(reward, r)
}
//reward为最终奖励额度
state.AddBalance(header.Coinbase, reward)
}