github.com/dim4egster/coreth@v0.10.2/params/config.go (about) 1 // (c) 2019-2020, Ava Labs, Inc. 2 // 3 // This file is a derived work, based on the go-ethereum library whose original 4 // notices appear below. 5 // 6 // It is distributed under a license compatible with the licensing terms of the 7 // original code from which it is derived. 8 // 9 // Much love to the original authors for their work. 10 // ********** 11 // Copyright 2016 The go-ethereum Authors 12 // This file is part of the go-ethereum library. 13 // 14 // The go-ethereum library is free software: you can redistribute it and/or modify 15 // it under the terms of the GNU Lesser General Public License as published by 16 // the Free Software Foundation, either version 3 of the License, or 17 // (at your option) any later version. 18 // 19 // The go-ethereum library is distributed in the hope that it will be useful, 20 // but WITHOUT ANY WARRANTY; without even the implied warranty of 21 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 22 // GNU Lesser General Public License for more details. 23 // 24 // You should have received a copy of the GNU Lesser General Public License 25 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 26 27 package params 28 29 import ( 30 "errors" 31 "fmt" 32 "math/big" 33 "time" 34 35 "github.com/dim4egster/coreth/precompile" 36 "github.com/dim4egster/coreth/utils" 37 "github.com/ethereum/go-ethereum/common" 38 ) 39 40 // Avalanche ChainIDs 41 var ( 42 // AvalancheMainnetChainID ... 43 AvalancheMainnetChainID = big.NewInt(43114) 44 // AvalancheFujiChainID ... 45 AvalancheFujiChainID = big.NewInt(43113) 46 // AvalancheLocalChainID ... 47 AvalancheLocalChainID = big.NewInt(43112) 48 49 errNonGenesisForkByHeight = errors.New("coreth only supports forking by height at the genesis block") 50 ) 51 52 var ( 53 // AvalancheMainnetChainConfig is the configuration for Avalanche Main Network 54 AvalancheMainnetChainConfig = &ChainConfig{ 55 ChainID: AvalancheMainnetChainID, 56 HomesteadBlock: big.NewInt(0), 57 DAOForkBlock: big.NewInt(0), 58 DAOForkSupport: true, 59 EIP150Block: big.NewInt(0), 60 EIP150Hash: common.HexToHash("0x2086799aeebeae135c246c65021c82b4e15a2c451340993aacfd2751886514f0"), 61 EIP155Block: big.NewInt(0), 62 EIP158Block: big.NewInt(0), 63 ByzantiumBlock: big.NewInt(0), 64 ConstantinopleBlock: big.NewInt(0), 65 PetersburgBlock: big.NewInt(0), 66 IstanbulBlock: big.NewInt(0), 67 MuirGlacierBlock: big.NewInt(0), 68 ApricotPhase1BlockTimestamp: big.NewInt(time.Date(2021, time.March, 31, 14, 0, 0, 0, time.UTC).Unix()), 69 ApricotPhase2BlockTimestamp: big.NewInt(time.Date(2021, time.May, 10, 11, 0, 0, 0, time.UTC).Unix()), 70 ApricotPhase3BlockTimestamp: big.NewInt(time.Date(2021, time.August, 24, 14, 0, 0, 0, time.UTC).Unix()), 71 ApricotPhase4BlockTimestamp: big.NewInt(time.Date(2021, time.September, 22, 21, 0, 0, 0, time.UTC).Unix()), 72 ApricotPhase5BlockTimestamp: big.NewInt(time.Date(2021, time.December, 2, 18, 0, 0, 0, time.UTC).Unix()), 73 ApricotPhasePre6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 5, 1, 30, 0, 0, time.UTC).Unix()), 74 ApricotPhase6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 6, 20, 0, 0, 0, time.UTC).Unix()), 75 ApricotPhasePost6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 7, 3, 0, 0, 0, time.UTC).Unix()), 76 // TODO Add Banff 77 // TODO Add Clementine 78 } 79 80 // AvalancheFujiChainConfig is the configuration for the Fuji Test Network 81 AvalancheFujiChainConfig = &ChainConfig{ 82 ChainID: AvalancheFujiChainID, 83 HomesteadBlock: big.NewInt(0), 84 DAOForkBlock: big.NewInt(0), 85 DAOForkSupport: true, 86 EIP150Block: big.NewInt(0), 87 EIP150Hash: common.HexToHash("0x2086799aeebeae135c246c65021c82b4e15a2c451340993aacfd2751886514f0"), 88 EIP155Block: big.NewInt(0), 89 EIP158Block: big.NewInt(0), 90 ByzantiumBlock: big.NewInt(0), 91 ConstantinopleBlock: big.NewInt(0), 92 PetersburgBlock: big.NewInt(0), 93 IstanbulBlock: big.NewInt(0), 94 MuirGlacierBlock: big.NewInt(0), 95 ApricotPhase1BlockTimestamp: big.NewInt(time.Date(2021, time.March, 26, 14, 0, 0, 0, time.UTC).Unix()), 96 ApricotPhase2BlockTimestamp: big.NewInt(time.Date(2021, time.May, 5, 14, 0, 0, 0, time.UTC).Unix()), 97 ApricotPhase3BlockTimestamp: big.NewInt(time.Date(2021, time.August, 16, 19, 0, 0, 0, time.UTC).Unix()), 98 ApricotPhase4BlockTimestamp: big.NewInt(time.Date(2021, time.September, 16, 21, 0, 0, 0, time.UTC).Unix()), 99 ApricotPhase5BlockTimestamp: big.NewInt(time.Date(2021, time.November, 24, 15, 0, 0, 0, time.UTC).Unix()), 100 ApricotPhasePre6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 6, 20, 0, 0, 0, time.UTC).Unix()), 101 ApricotPhase6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 6, 20, 0, 0, 0, time.UTC).Unix()), 102 ApricotPhasePost6BlockTimestamp: big.NewInt(time.Date(2022, time.September, 7, 6, 0, 0, 0, time.UTC).Unix()), 103 BanffBlockTimestamp: big.NewInt(time.Date(2022, time.October, 3, 14, 0, 0, 0, time.UTC).Unix()), 104 // TODO Add Clementine 105 } 106 107 // AvalancheLocalChainConfig is the configuration for the Avalanche Local Network 108 AvalancheLocalChainConfig = &ChainConfig{ 109 ChainID: AvalancheLocalChainID, 110 HomesteadBlock: big.NewInt(0), 111 DAOForkBlock: big.NewInt(0), 112 DAOForkSupport: true, 113 EIP150Block: big.NewInt(0), 114 EIP150Hash: common.HexToHash("0x2086799aeebeae135c246c65021c82b4e15a2c451340993aacfd2751886514f0"), 115 EIP155Block: big.NewInt(0), 116 EIP158Block: big.NewInt(0), 117 ByzantiumBlock: big.NewInt(0), 118 ConstantinopleBlock: big.NewInt(0), 119 PetersburgBlock: big.NewInt(0), 120 IstanbulBlock: big.NewInt(0), 121 MuirGlacierBlock: big.NewInt(0), 122 ApricotPhase1BlockTimestamp: big.NewInt(0), 123 ApricotPhase2BlockTimestamp: big.NewInt(0), 124 ApricotPhase3BlockTimestamp: big.NewInt(0), 125 ApricotPhase4BlockTimestamp: big.NewInt(0), 126 ApricotPhase5BlockTimestamp: big.NewInt(0), 127 ApricotPhasePre6BlockTimestamp: big.NewInt(0), 128 ApricotPhase6BlockTimestamp: big.NewInt(0), 129 ApricotPhasePost6BlockTimestamp: big.NewInt(0), 130 BanffBlockTimestamp: big.NewInt(0), 131 ClementineBlockTimestamp: big.NewInt(0), 132 } 133 134 TestChainConfig = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0)} 135 TestLaunchConfig = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil, nil, nil, nil, nil, nil} 136 TestApricotPhase1Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil, nil, nil, nil, nil} 137 TestApricotPhase2Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil, nil, nil, nil} 138 TestApricotPhase3Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil, nil, nil} 139 TestApricotPhase4Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil, nil} 140 TestApricotPhase5Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil, nil} 141 TestApricotPhasePre6Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil, nil} 142 TestApricotPhase6Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil, nil} 143 TestApricotPhasePost6Config = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil, nil} 144 TestBanffChainConfig = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), nil} 145 TestClementineChainConfig = &ChainConfig{big.NewInt(1), big.NewInt(0), nil, false, big.NewInt(0), common.Hash{}, big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0), big.NewInt(0)} 146 TestRules = TestChainConfig.AvalancheRules(new(big.Int), new(big.Int)) 147 ) 148 149 // ChainConfig is the core config which determines the blockchain settings. 150 // 151 // ChainConfig is stored in the database on a per block basis. This means 152 // that any network, identified by its genesis block, can have its own 153 // set of configuration options. 154 type ChainConfig struct { 155 ChainID *big.Int `json:"chainId"` // chainId identifies the current chain and is used for replay protection 156 157 HomesteadBlock *big.Int `json:"homesteadBlock,omitempty"` // Homestead switch block (nil = no fork, 0 = already homestead) 158 159 DAOForkBlock *big.Int `json:"daoForkBlock,omitempty"` // TheDAO hard-fork switch block (nil = no fork) 160 DAOForkSupport bool `json:"daoForkSupport,omitempty"` // Whether the nodes supports or opposes the DAO hard-fork 161 162 // EIP150 implements the Gas price changes (https://github.com/ethereum/EIPs/issues/150) 163 EIP150Block *big.Int `json:"eip150Block,omitempty"` // EIP150 HF block (nil = no fork) 164 EIP150Hash common.Hash `json:"eip150Hash,omitempty"` // EIP150 HF hash (needed for header only clients as only gas pricing changed) 165 166 EIP155Block *big.Int `json:"eip155Block,omitempty"` // EIP155 HF block 167 EIP158Block *big.Int `json:"eip158Block,omitempty"` // EIP158 HF block 168 169 ByzantiumBlock *big.Int `json:"byzantiumBlock,omitempty"` // Byzantium switch block (nil = no fork, 0 = already on byzantium) 170 ConstantinopleBlock *big.Int `json:"constantinopleBlock,omitempty"` // Constantinople switch block (nil = no fork, 0 = already activated) 171 PetersburgBlock *big.Int `json:"petersburgBlock,omitempty"` // Petersburg switch block (nil = same as Constantinople) 172 IstanbulBlock *big.Int `json:"istanbulBlock,omitempty"` // Istanbul switch block (nil = no fork, 0 = already on istanbul) 173 MuirGlacierBlock *big.Int `json:"muirGlacierBlock,omitempty"` // Eip-2384 (bomb delay) switch block (nil = no fork, 0 = already activated) 174 175 // Avalanche Network Upgrades 176 ApricotPhase1BlockTimestamp *big.Int `json:"apricotPhase1BlockTimestamp,omitempty"` // Apricot Phase 1 Block Timestamp (nil = no fork, 0 = already activated) 177 // Apricot Phase 2 Block Timestamp (nil = no fork, 0 = already activated) 178 // Apricot Phase 2 includes a modified version of the Berlin Hard Fork from Ethereum 179 ApricotPhase2BlockTimestamp *big.Int `json:"apricotPhase2BlockTimestamp,omitempty"` 180 // Apricot Phase 3 introduces dynamic fees and a modified version of the London Hard Fork from Ethereum (nil = no fork, 0 = already activated) 181 ApricotPhase3BlockTimestamp *big.Int `json:"apricotPhase3BlockTimestamp,omitempty"` 182 // Apricot Phase 4 introduces the notion of a block fee to the dynamic fee algorithm (nil = no fork, 0 = already activated) 183 ApricotPhase4BlockTimestamp *big.Int `json:"apricotPhase4BlockTimestamp,omitempty"` 184 // Apricot Phase 5 introduces a batch of atomic transactions with a maximum atomic gas limit per block. (nil = no fork, 0 = already activated) 185 ApricotPhase5BlockTimestamp *big.Int `json:"apricotPhase5BlockTimestamp,omitempty"` 186 // Apricot Phase Pre-6 deprecates the NativeAssetCall precompile (soft). (nil = no fork, 0 = already activated) 187 ApricotPhasePre6BlockTimestamp *big.Int `json:"apricotPhasePre6BlockTimestamp,omitempty"` 188 // Apricot Phase 6 deprecates the NativeAssetBalance and NativeAssetCall precompiles. (nil = no fork, 0 = already activated) 189 ApricotPhase6BlockTimestamp *big.Int `json:"apricotPhase6BlockTimestamp,omitempty"` 190 // Apricot Phase Post-6 deprecates the NativeAssetCall precompile (soft). (nil = no fork, 0 = already activated) 191 ApricotPhasePost6BlockTimestamp *big.Int `json:"apricotPhasePost6BlockTimestamp,omitempty"` 192 // Banff TODO comment. (nil = no fork, 0 = already activated) 193 BanffBlockTimestamp *big.Int `json:"banffBlockTimestamp,omitempty"` 194 // Clementine TODO comment. (nil = no fork, 0 = already activated) 195 ClementineBlockTimestamp *big.Int `json:"clementineBlockTimestamp,omitempty"` 196 } 197 198 // String implements the fmt.Stringer interface. 199 func (c *ChainConfig) String() string { 200 var banner string 201 202 banner += fmt.Sprintf("Chain ID: %v\n", c.ChainID) 203 banner += "Consensus: Dummy Consensus Engine\n\n" 204 205 // Create a list of forks with a short description of them. Forks that only 206 // makes sense for mainnet should be optional at printing to avoid bloating 207 // the output for testnets and private networks. 208 banner += "Hard Forks:\n" 209 banner += fmt.Sprintf(" - Homestead: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/homestead.md)\n", c.HomesteadBlock) 210 if c.DAOForkBlock != nil { 211 banner += fmt.Sprintf(" - DAO Fork: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/dao-fork.md)\n", c.DAOForkBlock) 212 } 213 banner += fmt.Sprintf(" - Tangerine Whistle (EIP 150): %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/tangerine-whistle.md)\n", c.EIP150Block) 214 banner += fmt.Sprintf(" - Spurious Dragon/1 (EIP 155): %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/spurious-dragon.md)\n", c.EIP155Block) 215 banner += fmt.Sprintf(" - Spurious Dragon/2 (EIP 158): %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/spurious-dragon.md)\n", c.EIP155Block) 216 banner += fmt.Sprintf(" - Byzantium: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/byzantium.md)\n", c.ByzantiumBlock) 217 banner += fmt.Sprintf(" - Constantinople: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/constantinople.md)\n", c.ConstantinopleBlock) 218 banner += fmt.Sprintf(" - Petersburg: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/petersburg.md)\n", c.PetersburgBlock) 219 banner += fmt.Sprintf(" - Istanbul: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/istanbul.md)\n", c.IstanbulBlock) 220 if c.MuirGlacierBlock != nil { 221 banner += fmt.Sprintf(" - Muir Glacier: %-8v (https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/muir-glacier.md)\n", c.MuirGlacierBlock) 222 } 223 banner += fmt.Sprintf(" - Apricot Phase 1 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.3.0)\n", c.ApricotPhase1BlockTimestamp) 224 banner += fmt.Sprintf(" - Apricot Phase 2 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.4.0)\n", c.ApricotPhase2BlockTimestamp) 225 banner += fmt.Sprintf(" - Apricot Phase 3 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.5.0)\n", c.ApricotPhase3BlockTimestamp) 226 banner += fmt.Sprintf(" - Apricot Phase 4 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.6.0)\n", c.ApricotPhase4BlockTimestamp) 227 banner += fmt.Sprintf(" - Apricot Phase 5 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.7.0)\n", c.ApricotPhase5BlockTimestamp) 228 banner += fmt.Sprintf(" - Apricot Phase P6 Timestamp %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.8.0)\n", c.ApricotPhasePre6BlockTimestamp) 229 banner += fmt.Sprintf(" - Apricot Phase 6 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.8.0)\n", c.ApricotPhase6BlockTimestamp) 230 banner += fmt.Sprintf(" - Apricot Phase Post-6 Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.8.0\n", c.ApricotPhasePost6BlockTimestamp) 231 banner += fmt.Sprintf(" - Banff Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.9.0)\n", c.BanffBlockTimestamp) 232 banner += fmt.Sprintf(" - Clementine Timestamp: %-8v (https://github.com/dim4egster/qmallgo/releases/tag/v1.10.0)\n", c.ClementineBlockTimestamp) 233 banner += "\n" 234 return banner 235 } 236 237 // IsHomestead returns whether num is either equal to the homestead block or greater. 238 func (c *ChainConfig) IsHomestead(num *big.Int) bool { 239 return utils.IsForked(c.HomesteadBlock, num) 240 } 241 242 // IsDAOFork returns whether num is either equal to the DAO fork block or greater. 243 func (c *ChainConfig) IsDAOFork(num *big.Int) bool { 244 return utils.IsForked(c.DAOForkBlock, num) 245 } 246 247 // IsEIP150 returns whether num is either equal to the EIP150 fork block or greater. 248 func (c *ChainConfig) IsEIP150(num *big.Int) bool { 249 return utils.IsForked(c.EIP150Block, num) 250 } 251 252 // IsEIP155 returns whether num is either equal to the EIP155 fork block or greater. 253 func (c *ChainConfig) IsEIP155(num *big.Int) bool { 254 return utils.IsForked(c.EIP155Block, num) 255 } 256 257 // IsEIP158 returns whether num is either equal to the EIP158 fork block or greater. 258 func (c *ChainConfig) IsEIP158(num *big.Int) bool { 259 return utils.IsForked(c.EIP158Block, num) 260 } 261 262 // IsByzantium returns whether num is either equal to the Byzantium fork block or greater. 263 func (c *ChainConfig) IsByzantium(num *big.Int) bool { 264 return utils.IsForked(c.ByzantiumBlock, num) 265 } 266 267 // IsConstantinople returns whether num is either equal to the Constantinople fork block or greater. 268 func (c *ChainConfig) IsConstantinople(num *big.Int) bool { 269 return utils.IsForked(c.ConstantinopleBlock, num) 270 } 271 272 // IsMuirGlacier returns whether num is either equal to the Muir Glacier (EIP-2384) fork block or greater. 273 func (c *ChainConfig) IsMuirGlacier(num *big.Int) bool { 274 return utils.IsForked(c.MuirGlacierBlock, num) 275 } 276 277 // IsPetersburg returns whether num is either 278 // - equal to or greater than the PetersburgBlock fork block, 279 // - OR is nil, and Constantinople is active 280 func (c *ChainConfig) IsPetersburg(num *big.Int) bool { 281 return utils.IsForked(c.PetersburgBlock, num) || c.PetersburgBlock == nil && utils.IsForked(c.ConstantinopleBlock, num) 282 } 283 284 // IsIstanbul returns whether num is either equal to the Istanbul fork block or greater. 285 func (c *ChainConfig) IsIstanbul(num *big.Int) bool { 286 return utils.IsForked(c.IstanbulBlock, num) 287 } 288 289 // Avalanche Upgrades: 290 291 // IsApricotPhase1 returns whether [blockTimestamp] represents a block 292 // with a timestamp after the Apricot Phase 1 upgrade time. 293 func (c *ChainConfig) IsApricotPhase1(blockTimestamp *big.Int) bool { 294 return utils.IsForked(c.ApricotPhase1BlockTimestamp, blockTimestamp) 295 } 296 297 // IsApricotPhase2 returns whether [blockTimestamp] represents a block 298 // with a timestamp after the Apricot Phase 2 upgrade time. 299 func (c *ChainConfig) IsApricotPhase2(blockTimestamp *big.Int) bool { 300 return utils.IsForked(c.ApricotPhase2BlockTimestamp, blockTimestamp) 301 } 302 303 // IsApricotPhase3 returns whether [blockTimestamp] represents a block 304 // with a timestamp after the Apricot Phase 3 upgrade time. 305 func (c *ChainConfig) IsApricotPhase3(blockTimestamp *big.Int) bool { 306 return utils.IsForked(c.ApricotPhase3BlockTimestamp, blockTimestamp) 307 } 308 309 // IsApricotPhase4 returns whether [blockTimestamp] represents a block 310 // with a timestamp after the Apricot Phase 4 upgrade time. 311 func (c *ChainConfig) IsApricotPhase4(blockTimestamp *big.Int) bool { 312 return utils.IsForked(c.ApricotPhase4BlockTimestamp, blockTimestamp) 313 } 314 315 // IsApricotPhase5 returns whether [blockTimestamp] represents a block 316 // with a timestamp after the Apricot Phase 5 upgrade time. 317 func (c *ChainConfig) IsApricotPhase5(blockTimestamp *big.Int) bool { 318 return utils.IsForked(c.ApricotPhase5BlockTimestamp, blockTimestamp) 319 } 320 321 // IsApricotPhasePre6 returns whether [blockTimestamp] represents a block 322 // with a timestamp after the Apricot Phase Pre 6 upgrade time. 323 func (c *ChainConfig) IsApricotPhasePre6(blockTimestamp *big.Int) bool { 324 return utils.IsForked(c.ApricotPhasePre6BlockTimestamp, blockTimestamp) 325 } 326 327 // IsApricotPhase6 returns whether [blockTimestamp] represents a block 328 // with a timestamp after the Apricot Phase 6 upgrade time. 329 func (c *ChainConfig) IsApricotPhase6(blockTimestamp *big.Int) bool { 330 return utils.IsForked(c.ApricotPhase6BlockTimestamp, blockTimestamp) 331 } 332 333 // IsApricotPhasePost6 returns whether [blockTimestamp] represents a block 334 // with a timestamp after the Apricot Phase 6 Post upgrade time. 335 func (c *ChainConfig) IsApricotPhasePost6(blockTimestamp *big.Int) bool { 336 return utils.IsForked(c.ApricotPhasePost6BlockTimestamp, blockTimestamp) 337 } 338 339 // IsBanff returns whether [blockTimestamp] represents a block 340 // with a timestamp after the Banff upgrade time. 341 func (c *ChainConfig) IsBanff(blockTimestamp *big.Int) bool { 342 return utils.IsForked(c.BanffBlockTimestamp, blockTimestamp) 343 } 344 345 // IsClementine returns whether [blockTimestamp] represents a block 346 // with a timestamp after the Clementine upgrade time. 347 func (c *ChainConfig) IsClementine(blockTimestamp *big.Int) bool { 348 return utils.IsForked(c.ClementineBlockTimestamp, blockTimestamp) 349 } 350 351 // CheckCompatible checks whether scheduled fork transitions have been imported 352 // with a mismatching chain configuration. 353 func (c *ChainConfig) CheckCompatible(newcfg *ChainConfig, height uint64, timestamp uint64) *ConfigCompatError { 354 bhead := new(big.Int).SetUint64(height) 355 bheadTimestamp := new(big.Int).SetUint64(timestamp) 356 357 // Iterate checkCompatible to find the lowest conflict. 358 var lasterr *ConfigCompatError 359 for { 360 err := c.checkCompatible(newcfg, bhead, bheadTimestamp) 361 if err == nil || (lasterr != nil && err.RewindTo == lasterr.RewindTo) { 362 break 363 } 364 lasterr = err 365 bhead.SetUint64(err.RewindTo) 366 } 367 return lasterr 368 } 369 370 // CheckConfigForkOrder checks that we don't "skip" any forks, geth isn't pluggable enough 371 // to guarantee that forks can be implemented in a different order than on official networks 372 func (c *ChainConfig) CheckConfigForkOrder() error { 373 type fork struct { 374 name string 375 block *big.Int 376 optional bool // if true, the fork may be nil and next fork is still allowed 377 } 378 var lastFork fork 379 for _, cur := range []fork{ 380 {name: "homesteadBlock", block: c.HomesteadBlock}, 381 {name: "daoForkBlock", block: c.DAOForkBlock, optional: true}, 382 {name: "eip150Block", block: c.EIP150Block}, 383 {name: "eip155Block", block: c.EIP155Block}, 384 {name: "eip158Block", block: c.EIP158Block}, 385 {name: "byzantiumBlock", block: c.ByzantiumBlock}, 386 {name: "constantinopleBlock", block: c.ConstantinopleBlock}, 387 {name: "petersburgBlock", block: c.PetersburgBlock}, 388 {name: "istanbulBlock", block: c.IstanbulBlock}, 389 {name: "muirGlacierBlock", block: c.MuirGlacierBlock, optional: true}, 390 } { 391 if cur.block != nil && common.Big0.Cmp(cur.block) != 0 { 392 return errNonGenesisForkByHeight 393 } 394 if lastFork.name != "" { 395 // Next one must be higher number 396 if lastFork.block == nil && cur.block != nil { 397 return fmt.Errorf("unsupported fork ordering: %v not enabled, but %v enabled at %v", 398 lastFork.name, cur.name, cur.block) 399 } 400 if lastFork.block != nil && cur.block != nil { 401 if lastFork.block.Cmp(cur.block) > 0 { 402 return fmt.Errorf("unsupported fork ordering: %v enabled at %v, but %v enabled at %v", 403 lastFork.name, lastFork.block, cur.name, cur.block) 404 } 405 } 406 } 407 // If it was optional and not set, then ignore it 408 if !cur.optional || cur.block != nil { 409 lastFork = cur 410 } 411 } 412 413 // Note: ApricotPhase1 and ApricotPhase2 override the rules set by block number 414 // hard forks. In Avalanche, hard forks must take place via block timestamps instead 415 // of block numbers since blocks are produced asynchronously. Therefore, we do not 416 // check that the block timestamps for Apricot Phase1 and Phase2 in the same way as for 417 // the block number forks since it would not be a meaningful comparison. 418 // Instead, we check only that Apricot Phases are enabled in order. 419 lastFork = fork{} 420 for _, cur := range []fork{ 421 {name: "apricotPhase1BlockTimestamp", block: c.ApricotPhase1BlockTimestamp}, 422 {name: "apricotPhase2BlockTimestamp", block: c.ApricotPhase2BlockTimestamp}, 423 {name: "apricotPhase3BlockTimestamp", block: c.ApricotPhase3BlockTimestamp}, 424 {name: "apricotPhase4BlockTimestamp", block: c.ApricotPhase4BlockTimestamp}, 425 {name: "apricotPhase5BlockTimestamp", block: c.ApricotPhase5BlockTimestamp}, 426 {name: "apricotPhasePre6BlockTimestamp", block: c.ApricotPhasePre6BlockTimestamp}, 427 {name: "apricotPhase6BlockTimestamp", block: c.ApricotPhase6BlockTimestamp}, 428 {name: "apricotPhasePost6BlockTimestamp", block: c.ApricotPhasePost6BlockTimestamp}, 429 {name: "banffBlockTimestamp", block: c.BanffBlockTimestamp}, 430 {name: "clementineBlockTimestamp", block: c.ClementineBlockTimestamp}, 431 } { 432 if lastFork.name != "" { 433 // Next one must be higher number 434 if lastFork.block == nil && cur.block != nil { 435 return fmt.Errorf("unsupported fork ordering: %v not enabled, but %v enabled at %v", 436 lastFork.name, cur.name, cur.block) 437 } 438 if lastFork.block != nil && cur.block != nil { 439 if lastFork.block.Cmp(cur.block) > 0 { 440 return fmt.Errorf("unsupported fork ordering: %v enabled at %v, but %v enabled at %v", 441 lastFork.name, lastFork.block, cur.name, cur.block) 442 } 443 } 444 } 445 // If it was optional and not set, then ignore it 446 if !cur.optional || cur.block != nil { 447 lastFork = cur 448 } 449 } 450 // TODO(aaronbuchwald) check that avalanche block timestamps are at least possible with the other rule set changes 451 // additional change: require that block number hard forks are either 0 or nil since they should not 452 // be enabled at a specific block number. 453 454 return nil 455 } 456 457 func (c *ChainConfig) checkCompatible(newcfg *ChainConfig, headHeight *big.Int, headTimestamp *big.Int) *ConfigCompatError { 458 if isForkIncompatible(c.HomesteadBlock, newcfg.HomesteadBlock, headHeight) { 459 return newCompatError("Homestead fork block", c.HomesteadBlock, newcfg.HomesteadBlock) 460 } 461 if isForkIncompatible(c.DAOForkBlock, newcfg.DAOForkBlock, headHeight) { 462 return newCompatError("DAO fork block", c.DAOForkBlock, newcfg.DAOForkBlock) 463 } 464 if c.IsDAOFork(headHeight) && c.DAOForkSupport != newcfg.DAOForkSupport { 465 return newCompatError("DAO fork support flag", c.DAOForkBlock, newcfg.DAOForkBlock) 466 } 467 if isForkIncompatible(c.EIP150Block, newcfg.EIP150Block, headHeight) { 468 return newCompatError("EIP150 fork block", c.EIP150Block, newcfg.EIP150Block) 469 } 470 if isForkIncompatible(c.EIP155Block, newcfg.EIP155Block, headHeight) { 471 return newCompatError("EIP155 fork block", c.EIP155Block, newcfg.EIP155Block) 472 } 473 if isForkIncompatible(c.EIP158Block, newcfg.EIP158Block, headHeight) { 474 return newCompatError("EIP158 fork block", c.EIP158Block, newcfg.EIP158Block) 475 } 476 if c.IsEIP158(headHeight) && !configNumEqual(c.ChainID, newcfg.ChainID) { 477 return newCompatError("EIP158 chain ID", c.EIP158Block, newcfg.EIP158Block) 478 } 479 if isForkIncompatible(c.ByzantiumBlock, newcfg.ByzantiumBlock, headHeight) { 480 return newCompatError("Byzantium fork block", c.ByzantiumBlock, newcfg.ByzantiumBlock) 481 } 482 if isForkIncompatible(c.ConstantinopleBlock, newcfg.ConstantinopleBlock, headHeight) { 483 return newCompatError("Constantinople fork block", c.ConstantinopleBlock, newcfg.ConstantinopleBlock) 484 } 485 if isForkIncompatible(c.PetersburgBlock, newcfg.PetersburgBlock, headHeight) { 486 // the only case where we allow Petersburg to be set in the past is if it is equal to Constantinople 487 // mainly to satisfy fork ordering requirements which state that Petersburg fork be set if Constantinople fork is set 488 if isForkIncompatible(c.ConstantinopleBlock, newcfg.PetersburgBlock, headHeight) { 489 return newCompatError("Petersburg fork block", c.PetersburgBlock, newcfg.PetersburgBlock) 490 } 491 } 492 if isForkIncompatible(c.IstanbulBlock, newcfg.IstanbulBlock, headHeight) { 493 return newCompatError("Istanbul fork block", c.IstanbulBlock, newcfg.IstanbulBlock) 494 } 495 if isForkIncompatible(c.MuirGlacierBlock, newcfg.MuirGlacierBlock, headHeight) { 496 return newCompatError("Muir Glacier fork block", c.MuirGlacierBlock, newcfg.MuirGlacierBlock) 497 } 498 if isForkIncompatible(c.ApricotPhase1BlockTimestamp, newcfg.ApricotPhase1BlockTimestamp, headTimestamp) { 499 return newCompatError("ApricotPhase1 fork block timestamp", c.ApricotPhase1BlockTimestamp, newcfg.ApricotPhase1BlockTimestamp) 500 } 501 if isForkIncompatible(c.ApricotPhase2BlockTimestamp, newcfg.ApricotPhase2BlockTimestamp, headTimestamp) { 502 return newCompatError("ApricotPhase2 fork block timestamp", c.ApricotPhase2BlockTimestamp, newcfg.ApricotPhase2BlockTimestamp) 503 } 504 if isForkIncompatible(c.ApricotPhase3BlockTimestamp, newcfg.ApricotPhase3BlockTimestamp, headTimestamp) { 505 return newCompatError("ApricotPhase3 fork block timestamp", c.ApricotPhase3BlockTimestamp, newcfg.ApricotPhase3BlockTimestamp) 506 } 507 if isForkIncompatible(c.ApricotPhase4BlockTimestamp, newcfg.ApricotPhase4BlockTimestamp, headTimestamp) { 508 return newCompatError("ApricotPhase4 fork block timestamp", c.ApricotPhase4BlockTimestamp, newcfg.ApricotPhase4BlockTimestamp) 509 } 510 if isForkIncompatible(c.ApricotPhase5BlockTimestamp, newcfg.ApricotPhase5BlockTimestamp, headTimestamp) { 511 return newCompatError("ApricotPhase5 fork block timestamp", c.ApricotPhase5BlockTimestamp, newcfg.ApricotPhase5BlockTimestamp) 512 } 513 // TODO: add Phase 6 checks 514 515 if isForkIncompatible(c.BanffBlockTimestamp, newcfg.BanffBlockTimestamp, headTimestamp) { 516 return newCompatError("Banff fork block timestamp", c.BanffBlockTimestamp, newcfg.BanffBlockTimestamp) 517 } 518 if isForkIncompatible(c.ClementineBlockTimestamp, newcfg.ClementineBlockTimestamp, headTimestamp) { 519 return newCompatError("Clementine fork block timestamp", c.ClementineBlockTimestamp, newcfg.ClementineBlockTimestamp) 520 } 521 return nil 522 } 523 524 // isForkIncompatible returns true if a fork scheduled at s1 cannot be rescheduled to 525 // block s2 because head is already past the fork. 526 func isForkIncompatible(s1, s2, head *big.Int) bool { 527 return (utils.IsForked(s1, head) || utils.IsForked(s2, head)) && !configNumEqual(s1, s2) 528 } 529 530 func configNumEqual(x, y *big.Int) bool { 531 if x == nil { 532 return y == nil 533 } 534 if y == nil { 535 return x == nil 536 } 537 return x.Cmp(y) == 0 538 } 539 540 // ConfigCompatError is raised if the locally-stored blockchain is initialised with a 541 // ChainConfig that would alter the past. 542 type ConfigCompatError struct { 543 What string 544 // block numbers of the stored and new configurations 545 StoredConfig, NewConfig *big.Int 546 // the block number to which the local chain must be rewound to correct the error 547 RewindTo uint64 548 } 549 550 func newCompatError(what string, storedblock, newblock *big.Int) *ConfigCompatError { 551 var rew *big.Int 552 switch { 553 case storedblock == nil: 554 rew = newblock 555 case newblock == nil || storedblock.Cmp(newblock) < 0: 556 rew = storedblock 557 default: 558 rew = newblock 559 } 560 err := &ConfigCompatError{what, storedblock, newblock, 0} 561 if rew != nil && rew.Sign() > 0 { 562 err.RewindTo = rew.Uint64() - 1 563 } 564 return err 565 } 566 567 func (err *ConfigCompatError) Error() string { 568 return fmt.Sprintf("mismatching %s in database (have %d, want %d, rewindto %d)", err.What, err.StoredConfig, err.NewConfig, err.RewindTo) 569 } 570 571 // Rules wraps ChainConfig and is merely syntactic sugar or can be used for functions 572 // that do not have or require information about the block. 573 // 574 // Rules is a one time interface meaning that it shouldn't be used in between transition 575 // phases. 576 type Rules struct { 577 ChainID *big.Int 578 IsHomestead, IsEIP150, IsEIP155, IsEIP158 bool 579 IsByzantium, IsConstantinople, IsPetersburg, IsIstanbul bool 580 581 // Rules for Avalanche releases 582 IsApricotPhase1, IsApricotPhase2, IsApricotPhase3, IsApricotPhase4, IsApricotPhase5 bool 583 IsApricotPhasePre6, IsApricotPhase6, IsApricotPhasePost6 bool 584 IsBanff bool 585 IsClementine bool 586 587 // Precompiles maps addresses to stateful precompiled contracts that are enabled 588 // for this rule set. 589 // Note: none of these addresses should conflict with the address space used by 590 // any existing precompiles. 591 Precompiles map[common.Address]precompile.StatefulPrecompiledContract 592 } 593 594 // Rules ensures c's ChainID is not nil. 595 func (c *ChainConfig) rules(num *big.Int) Rules { 596 chainID := c.ChainID 597 if chainID == nil { 598 chainID = new(big.Int) 599 } 600 return Rules{ 601 ChainID: new(big.Int).Set(chainID), 602 IsHomestead: c.IsHomestead(num), 603 IsEIP150: c.IsEIP150(num), 604 IsEIP155: c.IsEIP155(num), 605 IsEIP158: c.IsEIP158(num), 606 IsByzantium: c.IsByzantium(num), 607 IsConstantinople: c.IsConstantinople(num), 608 IsPetersburg: c.IsPetersburg(num), 609 IsIstanbul: c.IsIstanbul(num), 610 } 611 } 612 613 // AvalancheRules returns the Avalanche modified rules to support Avalanche 614 // network upgrades 615 func (c *ChainConfig) AvalancheRules(blockNum, blockTimestamp *big.Int) Rules { 616 rules := c.rules(blockNum) 617 618 rules.IsApricotPhase1 = c.IsApricotPhase1(blockTimestamp) 619 rules.IsApricotPhase2 = c.IsApricotPhase2(blockTimestamp) 620 rules.IsApricotPhase3 = c.IsApricotPhase3(blockTimestamp) 621 rules.IsApricotPhase4 = c.IsApricotPhase4(blockTimestamp) 622 rules.IsApricotPhase5 = c.IsApricotPhase5(blockTimestamp) 623 rules.IsApricotPhasePre6 = c.IsApricotPhasePre6(blockTimestamp) 624 rules.IsApricotPhase6 = c.IsApricotPhase6(blockTimestamp) 625 rules.IsApricotPhasePost6 = c.IsApricotPhasePost6(blockTimestamp) 626 rules.IsBanff = c.IsBanff(blockTimestamp) 627 rules.IsClementine = c.IsClementine(blockTimestamp) 628 629 // Initialize the stateful precompiles that should be enabled at [blockTimestamp]. 630 rules.Precompiles = make(map[common.Address]precompile.StatefulPrecompiledContract) 631 for _, config := range c.enabledStatefulPrecompiles() { 632 if utils.IsForked(config.Timestamp(), blockTimestamp) { 633 rules.Precompiles[config.Address()] = config.Contract() 634 } 635 } 636 637 return rules 638 } 639 640 // enabledStatefulPrecompiles returns a list of stateful precompile configs in the order that they are enabled 641 // by block timestamp. 642 // Note: the return value does not include the native precompiles [nativeAssetCall] and [nativeAssetBalance]. 643 // These are handled in [evm.precompile] directly. 644 func (c *ChainConfig) enabledStatefulPrecompiles() []precompile.StatefulPrecompileConfig { 645 statefulPrecompileConfigs := make([]precompile.StatefulPrecompileConfig, 0) 646 647 return statefulPrecompileConfigs 648 } 649 650 // CheckConfigurePrecompiles checks if any of the precompiles specified in the chain config are enabled by the block 651 // transition from [parentTimestamp] to the timestamp set in [blockContext]. If this is the case, it calls [Configure] 652 // to apply the necessary state transitions for the upgrade. 653 // This function is called: 654 // - within genesis setup to configure the starting state for precompiles enabled at genesis, 655 // - during block processing to update the state before processing the given block. 656 func (c *ChainConfig) CheckConfigurePrecompiles(parentTimestamp *big.Int, blockContext precompile.BlockContext, statedb precompile.StateDB) { 657 // Iterate the enabled stateful precompiles and configure them if needed 658 for _, config := range c.enabledStatefulPrecompiles() { 659 precompile.CheckConfigure(c, parentTimestamp, blockContext, config, statedb) 660 } 661 }