get masternodes set from latest checkpoint block header instead of fr… …

This commit is contained in:
MestryOmkar 2018-10-10 14:15:15 +05:30
parent 5b26898ad5
commit f814908442
5 changed files with 64 additions and 30 deletions

View file

@ -377,13 +377,16 @@ func startNode(ctx *cli.Context, stack *node.Node) {
if err != nil {
log.Warn("Can't get cap of a masternode candidate. Will ignore him", "address", candidate, "error", err)
}
ms = append(ms, clique.Masternode{Address: candidate, Stake: v.Int64()})
ms = append(ms, clique.Masternode{Address: candidate, Stake: v.String()})
}
//// order by cap
//sort.Slice(ms, func(i, j int) bool {
// return ms[i].Stake > ms[j].Stake
//})
log.Info("Ordered list of masternode candidates")
for _, m := range ms {
fmt.Printf("address: %s, stake: %s\n", m.Address.String(), m.Stake)
}
// order by cap
sort.Slice(ms, func(i, j int) bool {
return ms[i].Stake > ms[j].Stake
})
log.Info("Ordered list of masternode candidates", "candidates", ms)
if len(ms) == 0 {
log.Info("No masternode candidates found. Keep the current masternodes set for the next epoch")
} else {
@ -399,4 +402,4 @@ func startNode(ctx *cli.Context, stack *node.Node) {
}
}()
}
}
}

View file

@ -25,6 +25,7 @@ import (
"sync"
"time"
"fmt"
"github.com/ethereum/go-ethereum/accounts"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil"
@ -52,7 +53,7 @@ const (
type Masternode struct {
Address common.Address
Stake int64
Stake string
}
// Clique proof-of-authority protocol constants.
@ -394,7 +395,7 @@ func position(list []common.Address, x common.Address) int {
return -1
}
func YourTurn(snap *Snapshot, header *types.Header, cur common.Address) (bool, error) {
func YourTurn(masternodes []common.Address, snap *Snapshot, header *types.Header, cur common.Address) (bool, error) {
if header.Number.Uint64() == 0 {
// Not check signer for genesis block.
return true, nil
@ -404,10 +405,21 @@ func YourTurn(snap *Snapshot, header *types.Header, cur common.Address) (bool, e
if err != nil {
return false, err
}
preIndex := position(snap.signers(), pre)
curIndex := position(snap.signers(), cur)
log.Info("Debugging info", "number of masternodes", len(snap.signers()), "previous", pre, "position", preIndex, "current", cur, "position", curIndex)
return (preIndex+1)%len(snap.signers()) == curIndex, nil
preIndex := position(masternodes, pre)
curIndex := position(masternodes, cur)
log.Info("Debugging info", "number of masternodes", len(masternodes), "previous", pre, "position", preIndex, "current", cur, "position", curIndex)
for i, s := range masternodes {
fmt.Printf("%d - %s\n", i, s.String())
}
return (preIndex+1)%len(masternodes) == curIndex, nil
}
func GetExtraVanity() int {
return extraVanity
}
func GetExtraSeal() int {
return extraSeal
}
// snapshot retrieves the authorization snapshot at a given point in time.
@ -610,6 +622,29 @@ func (c *Clique) Prepare(chain consensus.ChainReader, header *types.Header) erro
return nil
}
func (c *Clique) UpdateMasternodes(chain consensus.ChainReader, header *types.Header, ms []Masternode) error {
number := header.Number.Uint64()
log.Trace("take snapshot", "number", number, "hash", header.Hash())
snap, err := c.snapshot(chain, number, header.Hash(), nil)
if err != nil {
return err
}
currentSigners := snap.signers()
proposedSigners := make(map[common.Address]struct{})
// count all addresses in ms to be masternode
for _, m := range ms {
proposedSigners[m.Address] = struct{}{}
c.proposals[m.Address] = true
}
// deactivate current masternodes which aren't in ms
for _, s := range currentSigners {
if _, ok := proposedSigners[s]; !ok {
c.proposals[s] = false
}
}
return nil
}
// Finalize implements consensus.Engine, ensuring no uncles are set, nor block
// rewards given, and returns the final block.
func (c *Clique) Finalize(chain consensus.ChainReader, header *types.Header, state *state.StateDB, txs []*types.Transaction, uncles []*types.Header, receipts []*types.Receipt) (*types.Block, error) {

View file

@ -62,7 +62,7 @@ const (
// BlockChainVersion ensures that an incompatible database forces a resync from scratch.
BlockChainVersion = 3
M1Gap = 10
M1Gap = 3
)
// CacheConfig contains the configuration values for the trie caching/pruning

View file

@ -238,7 +238,7 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
}
}
}
return nil
return nil
}
}
@ -428,23 +428,10 @@ func (s *Ethereum) UpdateMasternodes(ms []clique.Masternode) error {
return errors.New("not clique")
}
c := s.engine.(*clique.Clique)
snap, err := c.GetSnapshot(s.blockchain, s.blockchain.CurrentHeader())
err := c.UpdateMasternodes(s.blockchain, s.blockchain.CurrentHeader(), ms)
if err != nil {
return err
}
snap.Signers = make(map[common.Address]struct{})
for i, m := range ms {
if i == NumOfMasternodes {
break
}
snap.Signers[m.Address] = struct{}{}
}
err = c.StoreSnapshot(snap)
if err != nil {
return err
}
log.Trace("Stored masternodes snapshot to db", "number", snap.Number, "hash", snap.Hash)
return nil
}

View file

@ -421,13 +421,22 @@ func (self *worker) commitNewWork() {
// check if we are right after parent's coinbase in the list
// only go with Clique
if self.config.Clique != nil {
// get masternodes set from latest checkpoint
lastCheckpointNumber := parent.NumberU64() - (parent.NumberU64() % self.config.Clique.Epoch)
preCheckpointHeader := self.chain.GetHeaderByNumber(lastCheckpointNumber)
extraVanity := clique.GetExtraVanity()
extraSeal := clique.GetExtraSeal()
masternodes := make([]common.Address, (len(preCheckpointHeader.Extra)-extraVanity-extraSeal)/common.AddressLength)
for i := 0; i < len(masternodes); i++ {
copy(masternodes[i][:], preCheckpointHeader.Extra[extraVanity+i*common.AddressLength:])
}
c := self.engine.(*clique.Clique)
snap, err := c.GetSnapshot(self.chain, parent.Header())
if err != nil {
log.Error("Failed when trying to commit new work", "err", err)
return
}
ok, err := clique.YourTurn(snap, parent.Header(), self.coinbase)
ok, err := clique.YourTurn(masternodes, snap, parent.Header(), self.coinbase)
if err != nil {
log.Error("Failed when trying to commit new work", "err", err)
return