consensus/clique: Proof of Authority (#3753)

This PR is a prototype implementation of plugable consensus engines and the
Clique PoA protocol ethereum/EIPs#225
This commit is contained in:
Péter Szilágyi
2017-04-10 13:24:12 +03:00
committed by Felix Lange
parent bfe5eb7f8c
commit feeccdf4ec
12 changed files with 1576 additions and 124 deletions

View File

@ -55,10 +55,6 @@ type NodeConfig struct {
// decide if remote peers should be accepted or not.
EthereumNetworkID int
// EthereumChainConfig is the default parameters of the blockchain to use. If no
// configuration is specified, it defaults to the main network.
EthereumChainConfig *ChainConfig
// EthereumGenesis is the genesis JSON to use to seed the blockchain with. An
// empty genesis state is equivalent to using the mainnet's state.
EthereumGenesis string
@ -84,7 +80,6 @@ var defaultNodeConfig = &NodeConfig{
MaxPeers: 25,
EthereumEnabled: true,
EthereumNetworkID: 1,
EthereumChainConfig: MainnetChainConfig(),
EthereumDatabaseCache: 16,
}
@ -94,18 +89,6 @@ func NewNodeConfig() *NodeConfig {
return &config
}
// SetMainnet sets up the node for use on the Ethereum mainnet.
func (cfg *NodeConfig) SetMainnet() {
cfg.EthereumGenesis = ""
cfg.EthereumChainConfig = MainnetChainConfig()
}
// SetTestnet sets up the node for use on the Ethereum testnet.
func (cfg *NodeConfig) SetTestnet() {
cfg.EthereumGenesis = TestnetGenesis()
cfg.EthereumChainConfig = TestnetChainConfig()
}
// Node represents a Geth Ethereum node instance.
type Node struct {
node *node.Node
@ -144,27 +127,19 @@ func NewNode(datadir string, config *NodeConfig) (stack *Node, _ error) {
var genesis *core.Genesis
if config.EthereumGenesis != "" {
// Parse the user supplied genesis spec if not mainnet
genesis = new(core.Genesis)
if err := json.Unmarshal([]byte(config.EthereumGenesis), genesis); err != nil {
return nil, fmt.Errorf("invalid EthereumGenesis: %v", err)
return nil, fmt.Errorf("invalid genesis spec: %v", err)
}
// If we have the testnet, hard code the chain configs too
if config.EthereumGenesis == TestnetGenesis() {
genesis.Config = params.TestnetChainConfig
if config.EthereumNetworkID == 1 {
config.EthereumNetworkID = 3
}
}
}
if config.EthereumChainConfig != nil {
if genesis == nil {
genesis = core.DefaultGenesisBlock()
}
genesis.Config = &params.ChainConfig{
ChainId: big.NewInt(config.EthereumChainConfig.ChainID),
HomesteadBlock: big.NewInt(config.EthereumChainConfig.HomesteadBlock),
DAOForkBlock: big.NewInt(config.EthereumChainConfig.DAOForkBlock),
DAOForkSupport: config.EthereumChainConfig.DAOForkSupport,
EIP150Block: big.NewInt(config.EthereumChainConfig.EIP150Block),
EIP150Hash: config.EthereumChainConfig.EIP150Hash.hash,
EIP155Block: big.NewInt(config.EthereumChainConfig.EIP155Block),
EIP158Block: big.NewInt(config.EthereumChainConfig.EIP158Block),
}
}
// Register the Ethereum protocol if requested
if config.EthereumEnabled {
ethConf := &eth.Config{
@ -173,7 +148,7 @@ func NewNode(datadir string, config *NodeConfig) (stack *Node, _ error) {
DatabaseCache: config.EthereumDatabaseCache,
NetworkId: config.EthereumNetworkID,
GasPrice: new(big.Int).SetUint64(20 * params.Shannon),
GpoBlocks: 5,
GpoBlocks: 10,
GpoPercentile: 50,
EthashCacheDir: "ethash",
EthashCachesInMem: 2,

View File

@ -26,40 +26,12 @@ import (
"github.com/ethereum/go-ethereum/params"
)
// MainnetChainConfig returns the chain configurations for the main Ethereum network.
func MainnetChainConfig() *ChainConfig {
return &ChainConfig{
ChainID: params.MainNetChainID.Int64(),
HomesteadBlock: params.MainNetHomesteadBlock.Int64(),
DAOForkBlock: params.MainNetDAOForkBlock.Int64(),
DAOForkSupport: true,
EIP150Block: params.MainNetHomesteadGasRepriceBlock.Int64(),
EIP150Hash: Hash{params.MainNetHomesteadGasRepriceHash},
EIP155Block: params.MainNetSpuriousDragon.Int64(),
EIP158Block: params.MainNetSpuriousDragon.Int64(),
}
}
// MainnetGenesis returns the JSON spec to use for the main Ethereum network. It
// is actually empty since that defaults to the hard coded binary genesis block.
func MainnetGenesis() string {
return ""
}
// TestnetChainConfig returns the chain configurations for the Ethereum test network.
func TestnetChainConfig() *ChainConfig {
return &ChainConfig{
ChainID: params.TestNetChainID.Int64(),
HomesteadBlock: params.TestNetHomesteadBlock.Int64(),
DAOForkBlock: 0,
DAOForkSupport: false,
EIP150Block: params.TestNetHomesteadGasRepriceBlock.Int64(),
EIP150Hash: Hash{params.TestNetHomesteadGasRepriceHash},
EIP155Block: params.TestNetSpuriousDragon.Int64(),
EIP158Block: params.TestNetSpuriousDragon.Int64(),
}
}
// TestnetGenesis returns the JSON spec to use for the Ethereum test network.
func TestnetGenesis() string {
enc, err := json.Marshal(core.DefaultTestnetGenesisBlock())
@ -69,24 +41,6 @@ func TestnetGenesis() string {
return string(enc)
}
// ChainConfig is the core config which determines the blockchain settings.
type ChainConfig struct {
ChainID int64 // Chain ID for replay protection
HomesteadBlock int64 // Homestead switch block
DAOForkBlock int64 // TheDAO hard-fork switch block
DAOForkSupport bool // Whether the nodes supports or opposes the DAO hard-fork
EIP150Block int64 // Homestead gas reprice switch block
EIP150Hash Hash // Homestead gas reprice switch block hash
EIP155Block int64 // Replay protection switch block
EIP158Block int64 // Empty account pruning switch block
}
// NewChainConfig creates a new chain configuration that transitions immediately
// to homestead and has no notion of the DAO fork (ideal for a private network).
func NewChainConfig() *ChainConfig {
return new(ChainConfig)
}
// FoundationBootnodes returns the enode URLs of the P2P bootstrap nodes operated
// by the foundation running the V5 discovery protocol.
func FoundationBootnodes() *Enodes {