github.com/reapchain/go-reapchain@v0.2.15-0.20210609012950-9735c110c705/params/config.go (about) 1 package params 2 3 4 5 // Copyright 2016 The go-ethereum Authors 6 // This file is part of the go-ethereum library. 7 // 8 // The go-ethereum library is free software: you can redistribute it and/or modify 9 // it under the terms of the GNU Lesser General Public License as published by 10 // the Free Software Foundation, either version 3 of the License, or 11 // (at your option) any later version. 12 // 13 // The go-ethereum library is distributed in the hope that it will be useful, 14 // but WITHOUT ANY WARRANTY; without even the implied warranty of 15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 // GNU Lesser General Public License for more details. 17 // 18 // You should have received a copy of the GNU Lesser General Public License 19 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 20 21 import ( 22 "fmt" 23 "math/big" 24 "errors" 25 "github.com/ethereum/go-ethereum/common" 26 ) 27 28 var ( 29 // MainnetChainConfig is the chain parameters to run a node on the main network. 30 MainnetChainConfig = &ChainConfig{ 31 ChainId: MainNetChainID, 32 HomesteadBlock: MainNetHomesteadBlock, 33 DAOForkBlock: MainNetDAOForkBlock, 34 DAOForkSupport: true, 35 EIP150Block: MainNetHomesteadGasRepriceBlock, 36 EIP150Hash: MainNetHomesteadGasRepriceHash, 37 EIP155Block: MainNetSpuriousDragon, 38 EIP158Block: MainNetSpuriousDragon, 39 MetropolisBlock: MainNetMetropolisBlock, 40 41 Ethash: new(EthashConfig), 42 } 43 44 //MainnetChainConfig = &ChainConfig{ 45 // ChainId: big.NewInt(2017), 46 // HomesteadBlock: big.NewInt(1), 47 // DAOForkBlock: nil, 48 // DAOForkSupport: true, 49 // EIP150Block: big.NewInt(2), 50 // EIP150Hash: common.HexToHash("0x9b095b36c15eaf13044373aef8ee0bd3a382a5abb92e402afa44b8249c3a90e9"), 51 // EIP155Block: big.NewInt(3), 52 // EIP158Block: big.NewInt(3), 53 // MetropolisBlock: TestNetMetropolisBlock, 54 // 55 // /*Istanbul: &IstanbulConfig{ 56 // Epoch: 30000, 57 // ProposerPolicy: 0, 58 // }, */ 59 //// PoDC: &PoDCConfig{ 60 //// Epoch: 30000, 61 //// ProposerPolicy: 0, 62 //// }, 63 ////} 64 65 // TestnetChainConfig contains the chain parameters to run a node on the Ropsten test network. 66 TestnetChainConfig = &ChainConfig{ 67 ChainId: big.NewInt(3), 68 HomesteadBlock: big.NewInt(0), 69 DAOForkBlock: nil, 70 DAOForkSupport: true, 71 EIP150Block: big.NewInt(0), 72 EIP150Hash: common.HexToHash("0x41941023680923e0fe4d74a34bdac8141f2540e3ae90623718e47d66d1ca4a2d"), 73 EIP155Block: big.NewInt(10), 74 EIP158Block: big.NewInt(10), 75 MetropolisBlock: TestNetMetropolisBlock, 76 77 Ethash: new(EthashConfig), 78 } 79 80 // RinkebyChainConfig contains the chain parameters to run a node on the Rinkeby test network. 81 RinkebyChainConfig = &ChainConfig{ 82 ChainId: big.NewInt(4), 83 HomesteadBlock: big.NewInt(1), 84 DAOForkBlock: nil, 85 DAOForkSupport: true, 86 EIP150Block: big.NewInt(2), 87 EIP150Hash: common.HexToHash("0x9b095b36c15eaf13044373aef8ee0bd3a382a5abb92e402afa44b8249c3a90e9"), 88 EIP155Block: big.NewInt(3), 89 EIP158Block: big.NewInt(3), 90 MetropolisBlock: TestNetMetropolisBlock, 91 92 Clique: &CliqueConfig{ 93 Period: 15, 94 Epoch: 30000, 95 }, 96 } 97 98 // OttomanChainConfig contains the chain parameters to run a node on the Ottoman test network. 99 OttomanChainConfig = &ChainConfig{ 100 ChainId: big.NewInt(5), 101 HomesteadBlock: big.NewInt(1), 102 DAOForkBlock: nil, 103 DAOForkSupport: true, 104 EIP150Block: big.NewInt(2), 105 EIP150Hash: common.HexToHash("0x9b095b36c15eaf13044373aef8ee0bd3a382a5abb92e402afa44b8249c3a90e9"), 106 EIP155Block: big.NewInt(3), 107 EIP158Block: big.NewInt(3), 108 MetropolisBlock: TestNetMetropolisBlock, 109 110 111 Istanbul: &IstanbulConfig{ 112 Epoch: 30000, 113 ProposerPolicy: 0, 114 }, 115 } 116 117 // OttomanChainConfig contains the chain parameters to run a node on the Ottoman test network. 118 119 ReapChainConfig = &ChainConfig{ 120 ChainId: big.NewInt(2017), 121 HomesteadBlock: big.NewInt(1), 122 DAOForkBlock: nil, 123 DAOForkSupport: true, 124 EIP150Block: big.NewInt(2), 125 EIP150Hash: common.HexToHash("0x9b095b36c15eaf13044373aef8ee0bd3a382a5abb92e402afa44b8249c3a90e9"), 126 EIP155Block: big.NewInt(3), 127 EIP158Block: big.NewInt(3), 128 MetropolisBlock: TestNetMetropolisBlock, 129 130 PoDC: &PoDCConfig{ 131 Epoch: 30000, 132 ProposerPolicy: 0, 133 }, 134 } 135 136 // AllProtocolChanges contains every protocol change (EIPs) 137 // introduced and accepted by the Ethereum core developers. 138 // 139 // This configuration is intentionally not using keyed fields. 140 // This configuration must *always* have all forks enabled, which 141 // means that all fields must be set at all times. This forces 142 // anyone adding flags to the config to also have to set these 143 // fields. 144 145 AllProtocolChanges = &ChainConfig{big.NewInt(2017), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), new(EthashConfig), nil, nil, nil, 32} 146 TestChainConfig = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), nil, new(EthashConfig), nil, nil, nil, 32} 147 148 TestRules = TestChainConfig.Rules(new(big.Int)) 149 ) 150 151 // ChainConfig is the core config which determines the blockchain settings. 152 // 153 // ChainConfig is stored in the database on a per block basis. This means 154 // that any network, identified by its genesis block, can have its own 155 // set of configuration options. 156 type ChainConfig struct { 157 ChainId *big.Int `json:"chainId"` // Chain id identifies the current chain and is used for replay protection 158 159 HomesteadBlock *big.Int `json:"homesteadBlock,omitempty"` // Homestead switch block (nil = no fork, 0 = already homestead) 160 DAOForkBlock *big.Int `json:"daoForkBlock,omitempty"` // TheDAO hard-fork switch block (nil = no fork) 161 DAOForkSupport bool `json:"daoForkSupport,omitempty"` // Whether the nodes supports or opposes the DAO hard-fork 162 163 // EIP150 implements the Gas price changes (https://github.com/ethereum/EIPs/issues/150) 164 EIP150Block *big.Int `json:"eip150Block,omitempty"` // EIP150 HF block (nil = no fork) 165 EIP150Hash common.Hash `json:"eip150Hash,omitempty"` // EIP150 HF hash (fast sync aid) 166 167 EIP155Block *big.Int `json:"eip155Block,omitempty"` // EIP155 HF block 168 EIP158Block *big.Int `json:"eip158Block,omitempty"` // EIP158 HF block 169 170 MetropolisBlock *big.Int `json:"metropolisBlock,omitempty"` // Metropolis switch block (nil = no fork, 0 = alraedy on homestead) 171 172 // Various consensus engines 173 Ethash *EthashConfig `json:"ethash,omitempty"` 174 Clique *CliqueConfig `json:"clique,omitempty"` 175 Istanbul *IstanbulConfig `json:"istanbul,omitempty"` 176 PoDC *PoDCConfig `json:"podc,omitempty"` 177 MaxCodeSize uint64 `json:"maxCodeSize"` 178 179 } 180 181 // EthashConfig is the consensus engine configs for proof-of-work based sealing. 182 type EthashConfig struct{} 183 184 // PoDCConfig is the consensus engine configs for PoDC based sealing. 185 186 // String implements the stringer interface, returning the consensus engine details. 187 func (c *EthashConfig) String() string { 188 return "ethash" 189 } 190 191 // CliqueConfig is the consensus engine configs for proof-of-authority based sealing. 192 type CliqueConfig struct { 193 Period uint64 `json:"period"` // Number of seconds between blocks to enforce 194 Epoch uint64 `json:"epoch"` // Epoch length to reset votes and checkpoint 195 } 196 197 // String implements the stringer interface, returning the consensus engine details. 198 func (c *CliqueConfig) String() string { 199 return "clique" 200 } 201 202 // IstanbulConfig is the consensus engine configs for Istanbul based sealing. 203 type IstanbulConfig struct { 204 Epoch uint64 `json:"epoch"` // Epoch length to reset votes and checkpoint 205 ProposerPolicy uint64 `json:"policy"` // The policy for proposer selection 206 } 207 208 type PoDCConfig struct { 209 Epoch uint64 `json:"epoch"` // Epoch length to reset votes and checkpoint 210 ProposerPolicy uint64 `json:"policy"` // The policy for proposer selection 211 } 212 213 // String implements the stringer interface, returning the consensus engine details. 214 func (c *IstanbulConfig) String() string { 215 return "istanbul" 216 } 217 func (c *PoDCConfig) String() string { //display ? 218 return "podc" 219 } 220 221 // String implements the fmt.Stringer interface. 222 func (c *ChainConfig) String() string { 223 var engine interface{} 224 switch { 225 case c.Ethash != nil: 226 engine = c.Ethash 227 case c.Clique != nil: 228 engine = c.Clique 229 case c.Istanbul != nil: 230 engine = c.Istanbul 231 case c.PoDC != nil: 232 engine = c.PoDC 233 234 235 default: 236 engine = "unknown" 237 } 238 return fmt.Sprintf("{ChainID: %v Homestead: %v DAO: %v DAOSupport: %v EIP150: %v EIP155: %v EIP158: %v Metropolis: %v MaxCodeSize: %v Engine: %v}", 239 c.ChainId, 240 c.HomesteadBlock, 241 c.DAOForkBlock, 242 c.DAOForkSupport, 243 c.EIP150Block, 244 c.EIP155Block, 245 c.EIP158Block, 246 c.MetropolisBlock, 247 c.MaxCodeSize, 248 engine, 249 ) 250 } 251 252 func (c *ChainConfig) IsValid() error { 253 if c.MaxCodeSize < 24 || c.MaxCodeSize > 128 { 254 return errors.New("Genesis max code size must be between 24 and 128") 255 } 256 return nil 257 } 258 259 // IsHomestead returns whether num is either equal to the homestead block or greater. 260 func (c *ChainConfig) IsHomestead(num *big.Int) bool { 261 return isForked(c.HomesteadBlock, num) 262 } 263 264 // IsDAO returns whether num is either equal to the DAO fork block or greater. 265 func (c *ChainConfig) IsDAOFork(num *big.Int) bool { 266 return isForked(c.DAOForkBlock, num) 267 } 268 269 func (c *ChainConfig) IsEIP150(num *big.Int) bool { 270 return isForked(c.EIP150Block, num) 271 } 272 273 func (c *ChainConfig) IsEIP155(num *big.Int) bool { 274 return isForked(c.EIP155Block, num) 275 } 276 277 func (c *ChainConfig) IsEIP158(num *big.Int) bool { 278 return isForked(c.EIP158Block, num) 279 } 280 281 func (c *ChainConfig) IsMetropolis(num *big.Int) bool { 282 return isForked(c.MetropolisBlock, num) 283 } 284 285 // GasTable returns the gas table corresponding to the current phase (homestead or homestead reprice). 286 // 287 // The returned GasTable's fields shouldn't, under any circumstances, be changed. 288 func (c *ChainConfig) GasTable(num *big.Int) GasTable { 289 if num == nil { 290 return GasTableHomestead 291 } 292 switch { 293 case c.IsEIP158(num): 294 return GasTableEIP158 295 case c.IsEIP150(num): 296 return GasTableHomesteadGasRepriceFork 297 default: 298 return GasTableHomestead 299 } 300 } 301 302 // CheckCompatible checks whether scheduled fork transitions have been imported 303 // with a mismatching chain configuration. 304 func (c *ChainConfig) CheckCompatible(newcfg *ChainConfig, height uint64) *ConfigCompatError { 305 bhead := new(big.Int).SetUint64(height) 306 307 // Iterate checkCompatible to find the lowest conflict. 308 var lasterr *ConfigCompatError 309 for { 310 err := c.checkCompatible(newcfg, bhead) 311 if err == nil || (lasterr != nil && err.RewindTo == lasterr.RewindTo) { 312 break 313 } 314 lasterr = err 315 bhead.SetUint64(err.RewindTo) 316 } 317 return lasterr 318 } 319 320 func (c *ChainConfig) checkCompatible(newcfg *ChainConfig, head *big.Int) *ConfigCompatError { 321 if isForkIncompatible(c.HomesteadBlock, newcfg.HomesteadBlock, head) { 322 return newCompatError("Homestead fork block", c.HomesteadBlock, newcfg.HomesteadBlock) 323 } 324 if isForkIncompatible(c.DAOForkBlock, newcfg.DAOForkBlock, head) { 325 return newCompatError("DAO fork block", c.DAOForkBlock, newcfg.DAOForkBlock) 326 } 327 if c.IsDAOFork(head) && c.DAOForkSupport != newcfg.DAOForkSupport { 328 return newCompatError("DAO fork support flag", c.DAOForkBlock, newcfg.DAOForkBlock) 329 } 330 if isForkIncompatible(c.EIP150Block, newcfg.EIP150Block, head) { 331 return newCompatError("EIP150 fork block", c.EIP150Block, newcfg.EIP150Block) 332 } 333 if isForkIncompatible(c.EIP155Block, newcfg.EIP155Block, head) { 334 return newCompatError("EIP155 fork block", c.EIP155Block, newcfg.EIP155Block) 335 } 336 if isForkIncompatible(c.EIP158Block, newcfg.EIP158Block, head) { 337 return newCompatError("EIP158 fork block", c.EIP158Block, newcfg.EIP158Block) 338 } 339 if c.IsEIP158(head) && !configNumEqual(c.ChainId, newcfg.ChainId) { 340 return newCompatError("EIP158 chain ID", c.EIP158Block, newcfg.EIP158Block) 341 } 342 if isForkIncompatible(c.MetropolisBlock, newcfg.MetropolisBlock, head) { 343 return newCompatError("Metropolis fork block", c.MetropolisBlock, newcfg.MetropolisBlock) 344 } 345 return nil 346 } 347 348 // isForkIncompatible returns true if a fork scheduled at s1 cannot be rescheduled to 349 // block s2 because head is already past the fork. 350 func isForkIncompatible(s1, s2, head *big.Int) bool { 351 return (isForked(s1, head) || isForked(s2, head)) && !configNumEqual(s1, s2) 352 } 353 354 // isForked returns whether a fork scheduled at block s is active at the given head block. 355 func isForked(s, head *big.Int) bool { 356 if s == nil || head == nil { 357 return false 358 } 359 return s.Cmp(head) <= 0 360 } 361 362 func configNumEqual(x, y *big.Int) bool { 363 if x == nil { 364 return y == nil 365 } 366 if y == nil { 367 return x == nil 368 } 369 return x.Cmp(y) == 0 370 } 371 372 // ConfigCompatError is raised if the locally-stored blockchain is initialised with a 373 // ChainConfig that would alter the past. 374 type ConfigCompatError struct { 375 What string 376 // block numbers of the stored and new configurations 377 StoredConfig, NewConfig *big.Int 378 // the block number to which the local chain must be rewound to correct the error 379 RewindTo uint64 380 } 381 382 func newCompatError(what string, storedblock, newblock *big.Int) *ConfigCompatError { 383 var rew *big.Int 384 switch { 385 case storedblock == nil: 386 rew = newblock 387 case newblock == nil || storedblock.Cmp(newblock) < 0: 388 rew = storedblock 389 default: 390 rew = newblock 391 } 392 err := &ConfigCompatError{what, storedblock, newblock, 0} 393 if rew != nil && rew.Sign() > 0 { 394 err.RewindTo = rew.Uint64() - 1 395 } 396 return err 397 } 398 399 func (err *ConfigCompatError) Error() string { 400 return fmt.Sprintf("mismatching %s in database (have %d, want %d, rewindto %d)", err.What, err.StoredConfig, err.NewConfig, err.RewindTo) 401 } 402 403 // Rules wraps ChainConfig and is merely syntatic sugar or can be used for functions 404 // that do not have or require information about the block. 405 // 406 // Rules is a one time interface meaning that it shouldn't be used in between transition 407 // phases. 408 type Rules struct { 409 ChainId *big.Int 410 IsHomestead, IsEIP150, IsEIP155, IsEIP158 bool 411 IsMetropolis bool 412 } 413 414 func (c *ChainConfig) Rules(num *big.Int) Rules { 415 chainId := c.ChainId 416 if chainId == nil { 417 chainId = new(big.Int) 418 } 419 return Rules{ChainId: new(big.Int).Set(chainId), IsHomestead: c.IsHomestead(num), IsEIP150: c.IsEIP150(num), IsEIP155: c.IsEIP155(num), IsEIP158: c.IsEIP158(num), IsMetropolis: c.IsMetropolis(num)} 420 } 421