github.com/SmartMeshFoundation/Spectrum@v0.0.0-20220621030607-452a266fee1e/params/config.go (about)

     1  // Copyright 2016 The Spectrum Authors
     2  // This file is part of the Spectrum library.
     3  //
     4  // The Spectrum library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The Spectrum library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the Spectrum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package params
    18  
    19  import (
    20  	"fmt"
    21  	"math/big"
    22  
    23  	"github.com/SmartMeshFoundation/Spectrum/common"
    24  )
    25  
    26  var (
    27  	MainnetGenesisHash = common.HexToHash("0xa8ab5ecb308dd061e6baa8c8a04a62b3e35fae7aae1393921f8d52deac2c5712") // enforce below configs on
    28  	TestnetGenesisHash = common.HexToHash("0x464dfae7a2e140e76376f732c6be542880064d0a9b8350ceb2259b811827e7c6") // Testnet genesis hash to enforce below configs on
    29  	DevnetGenesisHash  = common.HexToHash("0xe11f21ee330cfb50c3f31d9b792df2fb5e196739d562e642416974f339aa4304")
    30  )
    31  
    32  var (
    33  	// MainnetChainConfig is the chain parameters to run a node on the main network.
    34  	MainnetChainConfig = &ChainConfig{
    35  		ChainId:        big.NewInt(20180430),
    36  		HomesteadBlock: big.NewInt(0),
    37  		DAOForkBlock:   nil,
    38  		DAOForkSupport: false,
    39  		EIP150Block:    big.NewInt(0),
    40  		EIP150Hash:     common.Hash{},
    41  		EIP155Block:    big.NewInt(0),
    42  		EIP158Block:    big.NewInt(0),
    43  		ByzantiumBlock: big.NewInt(0),
    44  		// add by liangc : change default consensus for dev
    45  		// if skip this vsn please set 0 or nil to block and set common.Address{} to address
    46  		// 0.0.5 : ready for release
    47  		Chief005Block:   big.NewInt(2),
    48  		Chief005Address: common.HexToAddress("0xf0d2ad4e0d25cfea98e9640329993bbc52396abd"),
    49  		// 0.0.6 : ready for release
    50  		Chief006Block:   big.NewInt(595888),
    51  		Chief006Address: common.HexToAddress("0xba7f507d5aab3e931312512c234fbeb85cbd9dce"),
    52  
    53  		Meshbox001Block:   big.NewInt(1870333),
    54  		Meshbox001Address: common.HexToAddress("0xf0ced0b1ce8738eeac06fdca51e0ff398328634b"),
    55  
    56  		Anmap001Block:   big.NewInt(2686801),
    57  		Anmap001Address: common.HexToAddress("0x23fb7fa0f6f88ce56b70ac3d671315f5baf84bb9"),
    58  
    59  		SIP001Block: big.NewInt(0), // new rules for chief.tx of gaspool
    60  		SIP002Block: big.NewInt(588888),
    61  		SIP003Block: big.NewInt(808888),
    62  
    63  		ChiefBaseAddress: common.HexToAddress("0xe1c749f45ee14180853e552d3349cc58972cd082"),
    64  		// PocBlock must less than Chief100Block
    65  		PocAddress: common.HexToAddress("0xb9b4ece952c8005f009801e5ec78e116f528c1d0"),
    66  
    67  		Chief100Block:   big.NewInt(2823366),
    68  		Chief100Address: common.HexToAddress("0x890eb8566550e7337c7788ff971a3996860c51b5"),
    69  		Tribe:           &TribeConfig{},
    70  
    71  		Sip004Block: big.NewInt(8654321),
    72  	}
    73  
    74  	// TestnetChainConfig contains the chain parameters to run a node on the Ropsten test network.
    75  	TestnetChainConfig = &ChainConfig{
    76  		ChainId:        big.NewInt(2022),
    77  		HomesteadBlock: big.NewInt(0),
    78  		DAOForkBlock:   nil,
    79  		DAOForkSupport: true,
    80  		EIP150Block:    big.NewInt(0),
    81  		EIP150Hash:     common.Hash{},
    82  		EIP155Block:    big.NewInt(0),
    83  		EIP158Block:    big.NewInt(0),
    84  		ByzantiumBlock: big.NewInt(0),
    85  		//ByzantiumBlock: big.NewInt(1700000),
    86  		//Clique: &CliqueConfig{ Period: 15, Epoch:  30000}, //Ethash: new(EthashConfig),
    87  		// if skip this vsn please set 0 or nil to block and set common.Address{} to address
    88  		// 0.0.2
    89  		Chief002Block:   big.NewInt(2),
    90  		Chief002Address: common.HexToAddress("0x75f7D812142c6f4BB39ad2c70424CF27869EAB33"),
    91  		// 0.0.3
    92  		//Chief003Block:   big.NewInt(113772), //hard fork testnet
    93  		//Chief003Address: common.HexToAddress("0xac28e532b3fac82554fc7b0b8b62549deeeb33a9"),
    94  		// 0.0.4 : fix bug redeploy
    95  		//Chief004Block:   big.NewInt(120305), //hard fork testnet : fix bugs and debug chief
    96  		//Chief004Address: common.HexToAddress("0xe242e2bcf5b0da6518320210fab0a27458bc0674"),
    97  		// 0.0.5 : ready for release
    98  		//Chief005Block:   big.NewInt(176244),
    99  		//Chief005Address: common.HexToAddress("0xe90da8175922925dfb40e6505b508f1042e807aa"),
   100  		// 0.0.6 : ready for release
   101  		//Chief006Block:   big.NewInt(595710),
   102  		//Chief006Address: common.HexToAddress("0x53cb83888e6d28cf7ec168308c65172001f441aa"),
   103  
   104  		//Meshbox001Block: big.NewInt(1976666),
   105  		//Meshbox001Address: common.HexToAddress("0x0f15e1e44322b2946215705d2ed60cba899f0b38"),
   106  		// Note that : meshbox002 must is superset of meshbox001
   107  
   108  		//Anmap001Block:   big.NewInt(1310056),
   109  		//Anmap001Address: common.HexToAddress("0x7449931e38dd938d2e8558eda9fe225acf4d14e6"),
   110  
   111  		// new rules for chief.tx of gaspool
   112  		SIP001Block: big.NewInt(24),
   113  		SIP002Block: big.NewInt(24),
   114  		SIP003Block: big.NewInt(24),
   115  		Sip004Block: big.NewInt(27),
   116  
   117  		// base block link to Chief100Block
   118  		ChiefBaseAddress: common.HexToAddress("0xa44B4ff09825f8c21fc4ad7FAA125a0d6238d0fd"),
   119  		//ChiefBaseAddress: common.HexToAddress("0xeb97d5201a79717675c03e80ef3ed0c00ec777fc"),
   120  
   121  		// PocBlock must less than Chief100Block
   122  		PocAddress: common.HexToAddress("0x32bcF7d3b48A7Ceaa1b45199CB94098d0b3b3112"),
   123  		//PocAddress: common.HexToAddress("0xe3d5627f6f854481b23da37cea623411bf090881"),
   124  
   125  		Chief100Block:   big.NewInt(26),
   126  		Chief100Address: common.HexToAddress("0x754FF9bDC93C66ff235b7AaaDcaeECdD63442657"),
   127  		//Chief100Address: common.HexToAddress("0x695249d987d10bcccda9bcaa3090db8565c317d1"),
   128  
   129  		Tribe: &TribeConfig{},
   130  	}
   131  
   132  	// DevnetChainConfig contains the chain parameters to run a node on the Ropsten test network.
   133  	DevnetChainConfig = &ChainConfig{
   134  		ChainId:        big.NewInt(4),
   135  		HomesteadBlock: big.NewInt(0),
   136  		DAOForkBlock:   nil,
   137  		DAOForkSupport: false,
   138  		EIP150Block:    big.NewInt(0),
   139  		EIP150Hash:     common.Hash{},
   140  		EIP155Block:    big.NewInt(0),
   141  		EIP158Block:    big.NewInt(0),
   142  		ByzantiumBlock: big.NewInt(0),
   143  
   144  		// if skip this vsn please set 0 or nil to block and set common.Address{} to address
   145  		// 0.0.6 : ready for release
   146  		// before block 2 gas used : 2631756
   147  		// after gas used : 2892524
   148  		Chief007Block:   big.NewInt(3),
   149  		Chief007Address: common.HexToAddress("0x57d2bcd8d702999daf240793919675c90b12a17a"),
   150  
   151  		// ############
   152  		// # DEBUG >>>>
   153  		// ############
   154  
   155  		// Note that : meshbox002 must is superset of meshbox001
   156  		Meshbox002Block:   big.NewInt(6),
   157  		Meshbox002Address: common.HexToAddress("0x7880adce4504fd39645aabb3efb53824d9b0c21b"),
   158  
   159  		Anmap001Block:   big.NewInt(6),
   160  		Anmap001Address: common.HexToAddress("0x143084accd6472ad502b59c3197f9ed5f797b966"),
   161  
   162  		// base block link to Chief100Block
   163  		//ChiefBaseAddress: common.HexToAddress("0xad61f1201f592fbf13d2645f9c59d8d5f82a1837"), //liang
   164  		ChiefBaseAddress: common.HexToAddress("0xf096d7f8ae3cd0a85e593accac5e7bc38a756111"),
   165  
   166  		// PocBlock must less than Chief100Block
   167  		//PocBlock: big.NewInt(35),
   168  		//PocAddress: common.HexToAddress("0x901c0636c4fc83f353bca2db85e2ace886a9416d"), //liang
   169  		PocAddress: common.HexToAddress("0x48e0f07faf58bc6e713d5c6373ce4f2a8b5c359a"),
   170  
   171  		Chief100Block: big.NewInt(63),
   172  		//Chief100Address: common.HexToAddress("0x"),
   173  		//Chief100Address: common.HexToAddress("0x6d05f6aa4e19e20cd781fa3def97bbfd0b980534"), // liang
   174  		Chief100Address: common.HexToAddress("0x21c5dc409138205291d6a7ef2dbb1701ac02ff96"),
   175  
   176  		/*
   177  			Meshbox002Block:   big.NewInt(6),
   178  			Meshbox002Address: common.HexToAddress("0xc4a2d182fe92f0eadffbddea9a0977d5b95b31a5"),
   179  
   180  			Anmap001Block:   big.NewInt(6),
   181  			Anmap001Address: common.HexToAddress("0x57d2bcd8d702999daf240793919675c90b12a17a"),
   182  
   183  			// base block link to Chief100Block
   184  			ChiefBaseAddress: common.HexToAddress("0x7880adce4504fd39645aabb3efb53824d9b0c21b"),
   185  
   186  			// PocBlock must less than Chief100Block
   187  			PocBlock:   big.NewInt(20),
   188  			PocAddress: common.HexToAddress("0xad61f1201f592fbf13d2645f9c59d8d5f82a1837"),
   189  
   190  			Chief100Block:   big.NewInt(22),
   191  			Chief100Address: common.HexToAddress("0x0f91c3f2e10a0b53d6b3b4d6c7b41ab77c7d0674"),
   192  
   193  		*/
   194  		// ############
   195  		// # DEBUG <<<<
   196  		// ############
   197  
   198  		// new rules for chief.tx of gaspool
   199  		SIP001Block: big.NewInt(0),
   200  		SIP002Block: big.NewInt(1),
   201  		SIP003Block: big.NewInt(3),
   202  
   203  		Tribe:       &TribeConfig{Period: 3},
   204  		Sip004Block: big.NewInt(4),
   205  	}
   206  
   207  	// AllEthashProtocolChanges contains every protocol change (EIPs) introduced
   208  	// and accepted by the Ethereum core developers into the Ethash consensus.
   209  	//
   210  	// This configuration is intentionally not using keyed fields to force anyone
   211  	// adding flags to the config to also have to set these fields.
   212  	AllEthashProtocolChanges = &ChainConfig{
   213  		ChainId:        big.NewInt(1337),
   214  		HomesteadBlock: big.NewInt(0),
   215  		DAOForkBlock:   nil,
   216  		DAOForkSupport: false,
   217  		EIP150Block:    big.NewInt(0),
   218  		EIP150Hash:     common.Hash{},
   219  		EIP155Block:    big.NewInt(0),
   220  		EIP158Block:    big.NewInt(0),
   221  		ByzantiumBlock: big.NewInt(0),
   222  		Ethash:         new(EthashConfig),
   223  		Clique:         nil,
   224  		Tribe:          nil,
   225  	}
   226  
   227  	// AllCliqueProtocolChanges contains every protocol change (EIPs) introduced
   228  	// and accepted by the Ethereum core developers into the Clique consensus.
   229  	//
   230  	// This configuration is intentionally not using keyed fields to force anyone
   231  	// adding flags to the config to also have to set these fields.
   232  	AllCliqueProtocolChanges = &ChainConfig{
   233  		ChainId:        big.NewInt(1337),
   234  		HomesteadBlock: big.NewInt(0),
   235  		DAOForkBlock:   nil,
   236  		DAOForkSupport: false,
   237  		EIP150Block:    big.NewInt(0),
   238  		EIP150Hash:     common.Hash{},
   239  		EIP155Block:    big.NewInt(0),
   240  		EIP158Block:    big.NewInt(0),
   241  		ByzantiumBlock: big.NewInt(0),
   242  		Ethash:         nil,
   243  		Clique:         &CliqueConfig{Period: 0, Epoch: 30000},
   244  		Tribe:          nil,
   245  	}
   246  	TestChainConfig = &ChainConfig{
   247  		ChainId:        big.NewInt(1),
   248  		HomesteadBlock: big.NewInt(0),
   249  		DAOForkBlock:   nil,
   250  		DAOForkSupport: false,
   251  		EIP150Block:    big.NewInt(0),
   252  		EIP150Hash:     common.Hash{},
   253  		EIP155Block:    big.NewInt(0),
   254  		EIP158Block:    big.NewInt(0),
   255  		ByzantiumBlock: big.NewInt(0),
   256  		Ethash:         new(EthashConfig),
   257  		Clique:         nil,
   258  		Tribe:          nil,
   259  	}
   260  	TestRules = TestChainConfig.Rules(new(big.Int))
   261  )
   262  
   263  // ChainConfig is the core config which determines the blockchain settings.
   264  //
   265  // ChainConfig is stored in the database on a per block basis. This means
   266  // that any network, identified by its genesis block, can have its own
   267  // set of configuration options.
   268  type ChainConfig struct {
   269  	ChainId *big.Int `json:"chainId"` // Chain id identifies the current chain and is used for replay protection
   270  
   271  	HomesteadBlock *big.Int `json:"homesteadBlock,omitempty"` // Homestead switch block (nil = no fork, 0 = already homestead)
   272  
   273  	DAOForkBlock   *big.Int `json:"daoForkBlock,omitempty"`   // TheDAO hard-fork switch block (nil = no fork)
   274  	DAOForkSupport bool     `json:"daoForkSupport,omitempty"` // Whether the nodes supports or opposes the DAO hard-fork
   275  
   276  	// EIP150 implements the Gas price changes (https://github.com/ethereum/EIPs/issues/150)
   277  	EIP150Block *big.Int    `json:"eip150Block,omitempty"` // EIP150 HF block (nil = no fork)
   278  	EIP150Hash  common.Hash `json:"eip150Hash,omitempty"`  // EIP150 HF hash (needed for header only clients as only gas pricing changed)
   279  
   280  	EIP155Block *big.Int `json:"eip155Block,omitempty"` // EIP155 HF block
   281  	EIP158Block *big.Int `json:"eip158Block,omitempty"` // EIP158 HF block
   282  
   283  	ByzantiumBlock *big.Int `json:"byzantiumBlock,omitempty"` // Byzantium switch block (nil = no fork, 0 = already on byzantium)
   284  
   285  	// Various consensus engines
   286  	Ethash *EthashConfig `json:"ethash,omitempty"`
   287  	Clique *CliqueConfig `json:"clique,omitempty"`
   288  	Tribe  *TribeConfig  `json:"tribe,omitempty"` // add by liangc
   289  
   290  	// >>> add by liangc : set chief start number >>>
   291  	// chief.sol vsn 0.0.2
   292  	Chief002Block   *big.Int       `json:"chief002Block,omitempty"`
   293  	Chief002Address common.Address `json:"chief002Address,omitempty"`
   294  	// chief.sol vsn 0.0.3
   295  	Chief003Block   *big.Int       `json:"chief003Block,omitempty"`
   296  	Chief003Address common.Address `json:"chief003Address,omitempty"`
   297  	// chief.sol vsn 0.0.4
   298  	Chief004Block   *big.Int       `json:"chief004Block,omitempty"`
   299  	Chief004Address common.Address `json:"chief004Address,omitempty"`
   300  	// chief.sol vsn 0.0.5
   301  	Chief005Block   *big.Int       `json:"chief005Block,omitempty"`
   302  	Chief005Address common.Address `json:"chief005Address,omitempty"`
   303  	// chief.sol vsn 0.0.6
   304  	Chief006Block   *big.Int       `json:"chief006Block,omitempty"`
   305  	Chief006Address common.Address `json:"chief006Address,omitempty"`
   306  
   307  	// extends 0.0.6 only for dev and test
   308  	Chief007Block   *big.Int       `json:"chief007Block,omitempty"`
   309  	Chief007Address common.Address `json:"chief007Address,omitempty"`
   310  	// https://github.com/SmartMeshFoundation/Spectrum/wiki/%5BChinese%5D-v1.0.0-Standard
   311  	Chief100Block   *big.Int       `json:"chief100Block,omitempty"`
   312  	Chief100Address common.Address `json:"chief100Address,omitempty"`
   313  
   314  	ChiefBaseAddress common.Address `json:"chiefBaseAddress,omitempty"`
   315  
   316  	//PocBlock   *big.Int       `json:"PocBlock,omitempty"`
   317  	PocAddress common.Address `json:"PocAddress,omitempty"`
   318  
   319  	// <<< add by liangc : set chief start number <<<
   320  	// add by liangc : new rules for chief.tx of gaspool
   321  	SIP001Block *big.Int `json:"sip001Block,omitempty"` // SIP001 HF block
   322  	// add by liangc : new rules for block period
   323  	SIP002Block *big.Int `json:"sip002Block,omitempty"` // SIP002 HF block
   324  	// add by liangc : 18-09-13 : incompatible HomesteadSigner begin at this number
   325  	SIP003Block *big.Int `json:"sip003Block,omitempty"`
   326  
   327  	Meshbox001Block   *big.Int       `json:"meshbox001Block,omitempty"`
   328  	Meshbox001Address common.Address `json:"meshbox001Address,omitempty"`
   329  	// Note that : meshbox002 must is superset of meshbox001
   330  	Meshbox002Block   *big.Int       `json:"meshbox002Block,omitempty"`
   331  	Meshbox002Address common.Address `json:"meshbox002Address,omitempty"`
   332  
   333  	Anmap001Block   *big.Int       `json:"anmap001Block,omitempty"`
   334  	Anmap001Address common.Address `json:"anmap001Address,omitempty"`
   335  
   336  	Sip004Block *big.Int `json:"sip004Block,omitempty"`
   337  }
   338  
   339  // EthashConfig is the consensus engine configs for proof-of-work based sealing.
   340  type EthashConfig struct{}
   341  
   342  // String implements the stringer interface, returning the consensus engine details.
   343  func (c *EthashConfig) String() string {
   344  	return "ethash"
   345  }
   346  
   347  // CliqueConfig is the consensus engine configs for proof-of-authority based sealing.
   348  type CliqueConfig struct {
   349  	Period uint64 `json:"period"` // Number of seconds between blocks to enforce
   350  	Epoch  uint64 `json:"epoch"`  // Epoch length to reset votes and checkpoint
   351  }
   352  
   353  // String implements the stringer interface, returning the consensus engine details.
   354  func (c *CliqueConfig) String() string {
   355  	return "clique"
   356  }
   357  
   358  // TribeConfig is the consensus engine configs.
   359  type TribeConfig struct {
   360  	Period uint64 `json:"period"` // Number of seconds between blocks to enforce
   361  }
   362  
   363  // String implements the stringer interface, returning the consensus engine details.
   364  func (c *TribeConfig) String() string {
   365  	return "tribe"
   366  }
   367  
   368  // String implements the fmt.Stringer interface.
   369  func (c *ChainConfig) String() string {
   370  	var engine interface{}
   371  	switch {
   372  	case c.Ethash != nil:
   373  		engine = c.Ethash
   374  	case c.Clique != nil:
   375  		engine = c.Clique
   376  	case c.Tribe != nil:
   377  		engine = c.Tribe
   378  	default:
   379  		engine = "unknown"
   380  	}
   381  	return fmt.Sprintf("{ChainID: %v Homestead: %v DAO: %v DAOSupport: %v EIP150: %v EIP155: %v EIP158: %v Byzantium: %v Engine: %v}",
   382  		c.ChainId,
   383  		c.HomesteadBlock,
   384  		c.DAOForkBlock,
   385  		c.DAOForkSupport,
   386  		c.EIP150Block,
   387  		c.EIP155Block,
   388  		c.EIP158Block,
   389  		c.ByzantiumBlock,
   390  		engine,
   391  	)
   392  }
   393  
   394  // IsHomestead returns whether num is either equal to the homestead block or greater.
   395  func (c *ChainConfig) IsHomestead(num *big.Int) bool {
   396  	return isForked(c.HomesteadBlock, num)
   397  }
   398  
   399  // IsDAO returns whether num is either equal to the DAO fork block or greater.
   400  func (c *ChainConfig) IsDAOFork(num *big.Int) bool {
   401  	return isForked(c.DAOForkBlock, num)
   402  }
   403  
   404  func (c *ChainConfig) IsEIP150(num *big.Int) bool {
   405  	return isForked(c.EIP150Block, num)
   406  }
   407  
   408  func (c *ChainConfig) IsEIP155(num *big.Int) bool {
   409  	return isForked(c.EIP155Block, num)
   410  }
   411  
   412  func (c *ChainConfig) IsEIP158(num *big.Int) bool {
   413  	return isForked(c.EIP158Block, num)
   414  }
   415  
   416  func (c *ChainConfig) IsByzantium(num *big.Int) bool {
   417  	// add by liangc : set default byzantium
   418  	return isForked(c.ByzantiumBlock, num)
   419  }
   420  func (c *ChainConfig) IsSip004(num *big.Int) bool {
   421  	// add by liangc : set default byzantium
   422  	return isForked(c.Sip004Block, num)
   423  }
   424  
   425  // GasTable returns the gas table corresponding to the current phase (homestead or homestead reprice).
   426  //
   427  // The returned GasTable's fields shouldn't, under any circumstances, be changed.
   428  func (c *ChainConfig) GasTable(num *big.Int) GasTable {
   429  	if num == nil {
   430  		return GasTableHomestead
   431  	}
   432  	switch {
   433  	case c.IsEIP158(num):
   434  		return GasTableEIP158
   435  	case c.IsEIP150(num):
   436  		return GasTableEIP150
   437  	default:
   438  		return GasTableHomestead
   439  	}
   440  }
   441  
   442  // CheckCompatible checks whether scheduled fork transitions have been imported
   443  // with a mismatching chain configuration.
   444  func (c *ChainConfig) CheckCompatible(newcfg *ChainConfig, height uint64) *ConfigCompatError {
   445  	bhead := new(big.Int).SetUint64(height)
   446  
   447  	// Iterate checkCompatible to find the lowest conflict.
   448  	var lasterr *ConfigCompatError
   449  	for {
   450  		err := c.checkCompatible(newcfg, bhead)
   451  		if err == nil || (lasterr != nil && err.RewindTo == lasterr.RewindTo) {
   452  			break
   453  		}
   454  		lasterr = err
   455  		bhead.SetUint64(err.RewindTo)
   456  	}
   457  	return lasterr
   458  }
   459  
   460  func (c *ChainConfig) checkCompatible(newcfg *ChainConfig, head *big.Int) *ConfigCompatError {
   461  	if isForkIncompatible(c.HomesteadBlock, newcfg.HomesteadBlock, head) {
   462  		return newCompatError("Homestead fork block", c.HomesteadBlock, newcfg.HomesteadBlock)
   463  	}
   464  	if isForkIncompatible(c.DAOForkBlock, newcfg.DAOForkBlock, head) {
   465  		return newCompatError("DAO fork block", c.DAOForkBlock, newcfg.DAOForkBlock)
   466  	}
   467  	if c.IsDAOFork(head) && c.DAOForkSupport != newcfg.DAOForkSupport {
   468  		return newCompatError("DAO fork support flag", c.DAOForkBlock, newcfg.DAOForkBlock)
   469  	}
   470  	if isForkIncompatible(c.EIP150Block, newcfg.EIP150Block, head) {
   471  		return newCompatError("EIP150 fork block", c.EIP150Block, newcfg.EIP150Block)
   472  	}
   473  	if isForkIncompatible(c.EIP155Block, newcfg.EIP155Block, head) {
   474  		return newCompatError("EIP155 fork block", c.EIP155Block, newcfg.EIP155Block)
   475  	}
   476  	if isForkIncompatible(c.EIP158Block, newcfg.EIP158Block, head) {
   477  		return newCompatError("EIP158 fork block", c.EIP158Block, newcfg.EIP158Block)
   478  	}
   479  	if c.IsEIP158(head) && !configNumEqual(c.ChainId, newcfg.ChainId) {
   480  		return newCompatError("EIP158 chain ID", c.EIP158Block, newcfg.EIP158Block)
   481  	}
   482  	if isForkIncompatible(c.ByzantiumBlock, newcfg.ByzantiumBlock, head) {
   483  		return newCompatError("Byzantium fork block", c.ByzantiumBlock, newcfg.ByzantiumBlock)
   484  	}
   485  	return nil
   486  }
   487  
   488  // isForkIncompatible returns true if a fork scheduled at s1 cannot be rescheduled to
   489  // block s2 because head is already past the fork.
   490  func isForkIncompatible(s1, s2, head *big.Int) bool {
   491  	return (isForked(s1, head) || isForked(s2, head)) && !configNumEqual(s1, s2)
   492  }
   493  
   494  // isForked returns whether a fork scheduled at block s is active at the given head block.
   495  func isForked(s, head *big.Int) bool {
   496  	if s == nil || head == nil {
   497  		return false
   498  	}
   499  	return s.Cmp(head) <= 0
   500  }
   501  
   502  func configNumEqual(x, y *big.Int) bool {
   503  	if x == nil {
   504  		return y == nil
   505  	}
   506  	if y == nil {
   507  		return x == nil
   508  	}
   509  	return x.Cmp(y) == 0
   510  }
   511  
   512  // ConfigCompatError is raised if the locally-stored blockchain is initialised with a
   513  // ChainConfig that would alter the past.
   514  type ConfigCompatError struct {
   515  	What string
   516  	// block numbers of the stored and new configurations
   517  	StoredConfig, NewConfig *big.Int
   518  	// the block number to which the local chain must be rewound to correct the error
   519  	RewindTo uint64
   520  }
   521  
   522  func newCompatError(what string, storedblock, newblock *big.Int) *ConfigCompatError {
   523  	var rew *big.Int
   524  	switch {
   525  	case storedblock == nil:
   526  		rew = newblock
   527  	case newblock == nil || storedblock.Cmp(newblock) < 0:
   528  		rew = storedblock
   529  	default:
   530  		rew = newblock
   531  	}
   532  	err := &ConfigCompatError{what, storedblock, newblock, 0}
   533  	if rew != nil && rew.Sign() > 0 {
   534  		err.RewindTo = rew.Uint64() - 1
   535  	}
   536  	return err
   537  }
   538  
   539  func (err *ConfigCompatError) Error() string {
   540  	return fmt.Sprintf("mismatching %s in database (have %d, want %d, rewindto %d)", err.What, err.StoredConfig, err.NewConfig, err.RewindTo)
   541  }
   542  
   543  // Rules wraps ChainConfig and is merely syntatic sugar or can be used for functions
   544  // that do not have or require information about the block.
   545  //
   546  // Rules is a one time interface meaning that it shouldn't be used in between transition
   547  // phases.
   548  type Rules struct {
   549  	ChainId                                   *big.Int
   550  	IsHomestead, IsEIP150, IsEIP155, IsEIP158 bool
   551  	IsByzantium                               bool
   552  	IsSip004                                  bool
   553  }
   554  
   555  func (c *ChainConfig) Rules(num *big.Int) Rules {
   556  	chainId := c.ChainId
   557  	if chainId == nil {
   558  		chainId = new(big.Int)
   559  	}
   560  	return Rules{ChainId: new(big.Int).Set(chainId), IsHomestead: c.IsHomestead(num), IsEIP150: c.IsEIP150(num), IsEIP155: c.IsEIP155(num), IsEIP158: c.IsEIP158(num), IsByzantium: c.IsByzantium(num), IsSip004: c.IsSip004(num)}
   561  }