github.com/kisexp/xdchain@v0.0.0-20211206025815-490d6b732aa7/core/genesis.go (about)

     1  // Copyright 2014 The go-ethereum Authors
     2  // This file is part of the go-ethereum library.
     3  //
     4  // The go-ethereum 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 go-ethereum 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 go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package core
    18  
    19  import (
    20  	"bytes"
    21  	"encoding/hex"
    22  	"encoding/json"
    23  	"errors"
    24  	"fmt"
    25  	"math/big"
    26  	"strings"
    27  
    28  	"github.com/kisexp/xdchain/common"
    29  	"github.com/kisexp/xdchain/common/hexutil"
    30  	"github.com/kisexp/xdchain/common/math"
    31  	"github.com/kisexp/xdchain/core/rawdb"
    32  	"github.com/kisexp/xdchain/core/state"
    33  	"github.com/kisexp/xdchain/core/types"
    34  	"github.com/kisexp/xdchain/crypto"
    35  	"github.com/kisexp/xdchain/ethdb"
    36  	"github.com/kisexp/xdchain/log"
    37  	"github.com/kisexp/xdchain/params"
    38  	"github.com/kisexp/xdchain/rlp"
    39  	"github.com/kisexp/xdchain/trie"
    40  )
    41  
    42  //go:generate gencodec -type Genesis -field-override genesisSpecMarshaling -out gen_genesis.go
    43  //go:generate gencodec -type GenesisAccount -field-override genesisAccountMarshaling -out gen_genesis_account.go
    44  
    45  var errGenesisNoConfig = errors.New("genesis has no chain configuration")
    46  
    47  // Genesis specifies the header fields, state of a genesis block. It also defines hard
    48  // fork switch-over blocks through the chain configuration.
    49  type Genesis struct {
    50  	Config     *params.ChainConfig `json:"config"`
    51  	Nonce      uint64              `json:"nonce"`
    52  	Timestamp  uint64              `json:"timestamp"`
    53  	ExtraData  []byte              `json:"extraData"`
    54  	GasLimit   uint64              `json:"gasLimit"   gencodec:"required"`
    55  	Difficulty *big.Int            `json:"difficulty" gencodec:"required"`
    56  	Mixhash    common.Hash         `json:"mixHash"`
    57  	Coinbase   common.Address      `json:"coinbase"`
    58  	Alloc      GenesisAlloc        `json:"alloc"      gencodec:"required"`
    59  
    60  	// These fields are used for consensus tests. Please don't use them
    61  	// in actual genesis blocks.
    62  	Number     uint64      `json:"number"`
    63  	GasUsed    uint64      `json:"gasUsed"`
    64  	ParentHash common.Hash `json:"parentHash"`
    65  }
    66  
    67  // GenesisAlloc specifies the initial state that is part of the genesis block.
    68  type GenesisAlloc map[common.Address]GenesisAccount
    69  
    70  func (ga *GenesisAlloc) UnmarshalJSON(data []byte) error {
    71  	m := make(map[common.UnprefixedAddress]GenesisAccount)
    72  	if err := json.Unmarshal(data, &m); err != nil {
    73  		return err
    74  	}
    75  	*ga = make(GenesisAlloc)
    76  	for addr, a := range m {
    77  		(*ga)[common.Address(addr)] = a
    78  	}
    79  	return nil
    80  }
    81  
    82  // GenesisAccount is an account in the state of the genesis block.
    83  type GenesisAccount struct {
    84  	Code       []byte                      `json:"code,omitempty"`
    85  	Storage    map[common.Hash]common.Hash `json:"storage,omitempty"`
    86  	Balance    *big.Int                    `json:"balance" gencodec:"required"`
    87  	Nonce      uint64                      `json:"nonce,omitempty"`
    88  	PrivateKey []byte                      `json:"secretKey,omitempty"` // for tests
    89  }
    90  
    91  // field type overrides for gencodec
    92  type genesisSpecMarshaling struct {
    93  	Nonce      math.HexOrDecimal64
    94  	Timestamp  math.HexOrDecimal64
    95  	ExtraData  hexutil.Bytes
    96  	GasLimit   math.HexOrDecimal64
    97  	GasUsed    math.HexOrDecimal64
    98  	Number     math.HexOrDecimal64
    99  	Difficulty *math.HexOrDecimal256
   100  	Alloc      map[common.UnprefixedAddress]GenesisAccount
   101  }
   102  
   103  type genesisAccountMarshaling struct {
   104  	Code       hexutil.Bytes
   105  	Balance    *math.HexOrDecimal256
   106  	Nonce      math.HexOrDecimal64
   107  	Storage    map[storageJSON]storageJSON
   108  	PrivateKey hexutil.Bytes
   109  }
   110  
   111  // storageJSON represents a 256 bit byte array, but allows less than 256 bits when
   112  // unmarshaling from hex.
   113  type storageJSON common.Hash
   114  
   115  func (h *storageJSON) UnmarshalText(text []byte) error {
   116  	text = bytes.TrimPrefix(text, []byte("0x"))
   117  	if len(text) > 64 {
   118  		return fmt.Errorf("too many hex characters in storage key/value %q", text)
   119  	}
   120  	offset := len(h) - len(text)/2 // pad on the left
   121  	if _, err := hex.Decode(h[offset:], text); err != nil {
   122  		fmt.Println(err)
   123  		return fmt.Errorf("invalid hex storage key/value %q", text)
   124  	}
   125  	return nil
   126  }
   127  
   128  func (h storageJSON) MarshalText() ([]byte, error) {
   129  	return hexutil.Bytes(h[:]).MarshalText()
   130  }
   131  
   132  // GenesisMismatchError is raised when trying to overwrite an existing
   133  // genesis block with an incompatible one.
   134  type GenesisMismatchError struct {
   135  	Stored, New common.Hash
   136  }
   137  
   138  func (e *GenesisMismatchError) Error() string {
   139  	return fmt.Sprintf("database contains incompatible genesis (have %x, new %x)", e.Stored, e.New)
   140  }
   141  
   142  // SetupGenesisBlock writes or updates the genesis block in db.
   143  // The block that will be used is:
   144  //
   145  //                          genesis == nil       genesis != nil
   146  //                       +------------------------------------------
   147  //     db has no genesis |  main-net default  |  genesis
   148  //     db has genesis    |  from DB           |  genesis (if compatible)
   149  //
   150  // The stored chain configuration will be updated if it is compatible (i.e. does not
   151  // specify a fork block below the local head block). In case of a conflict, the
   152  // error is a *params.ConfigCompatError and the new, unwritten config is returned.
   153  //
   154  // The returned chain configuration is never nil.
   155  func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig, common.Hash, error) {
   156  	if genesis != nil && genesis.Config == nil {
   157  		return params.AllEthashProtocolChanges, common.Hash{}, errGenesisNoConfig
   158  	}
   159  	// Just commit the new block if there is no stored genesis block.
   160  	stored := rawdb.ReadCanonicalHash(db, 0)
   161  	if (stored == common.Hash{}) {
   162  		if genesis == nil {
   163  			log.Info("Writing default main-net genesis block")
   164  			genesis = DefaultGenesisBlock()
   165  		} else {
   166  			log.Info("Writing custom genesis block")
   167  		}
   168  
   169  		// Quorum: Set default transaction size limit if not set in genesis
   170  		if genesis.Config.TransactionSizeLimit == 0 {
   171  			genesis.Config.TransactionSizeLimit = DefaultTxPoolConfig.TransactionSizeLimit
   172  		}
   173  
   174  		// Check transaction size limit and max contract code size
   175  		err := genesis.Config.IsValid()
   176  		if err != nil {
   177  			return genesis.Config, common.Hash{}, err
   178  		}
   179  
   180  		// /Quorum
   181  
   182  		block, err := genesis.Commit(db)
   183  		if err != nil {
   184  			return genesis.Config, common.Hash{}, err
   185  		}
   186  		checkAndPrintPrivacyEnhancementsWarning(genesis.Config)
   187  		return genesis.Config, block.Hash(), nil
   188  	}
   189  
   190  	// We have the genesis block in database(perhaps in ancient database)
   191  	// but the corresponding state is missing.
   192  	header := rawdb.ReadHeader(db, stored, 0)
   193  	if _, err := state.New(header.Root, state.NewDatabaseWithConfig(db, nil), nil); err != nil {
   194  		if genesis == nil {
   195  			genesis = DefaultGenesisBlock()
   196  		}
   197  		// Ensure the stored genesis matches with the given one.
   198  		hash := genesis.ToBlock(nil).Hash()
   199  		if hash != stored {
   200  			return genesis.Config, hash, &GenesisMismatchError{stored, hash}
   201  		}
   202  		block, err := genesis.Commit(db)
   203  		if err != nil {
   204  			return genesis.Config, hash, err
   205  		}
   206  		return genesis.Config, block.Hash(), nil
   207  	}
   208  
   209  	// Check whether the genesis block is already written.
   210  	if genesis != nil {
   211  		hash := genesis.ToBlock(nil).Hash()
   212  		if hash != stored {
   213  			return genesis.Config, hash, &GenesisMismatchError{stored, hash}
   214  		}
   215  	}
   216  
   217  	// Get the existing chain configuration.
   218  	newcfg := genesis.configOrDefault(stored)
   219  	if err := newcfg.CheckConfigForkOrder(); err != nil {
   220  		return newcfg, common.Hash{}, err
   221  	}
   222  	storedcfg := rawdb.ReadChainConfig(db, stored)
   223  	if storedcfg == nil {
   224  		log.Warn("Found genesis block without chain config")
   225  		rawdb.WriteChainConfig(db, stored, newcfg)
   226  		checkAndPrintPrivacyEnhancementsWarning(newcfg)
   227  		return newcfg, stored, nil
   228  	}
   229  	// Special case: don't change the existing config of a non-mainnet chain if no new
   230  	// config is supplied. These chains would get AllProtocolChanges (and a compat error)
   231  	// if we just continued here.
   232  	if genesis == nil && stored != params.MainnetGenesisHash {
   233  		return storedcfg, stored, nil
   234  	}
   235  
   236  	// Check config compatibility and write the config. Compatibility errors
   237  	// are returned to the caller unless we're already at block zero.
   238  	height := rawdb.ReadHeaderNumber(db, rawdb.ReadHeadHeaderHash(db))
   239  	if height == nil {
   240  		return newcfg, stored, fmt.Errorf("missing block number for head header hash")
   241  	}
   242  	if storedcfg.IsMPS != newcfg.IsMPS && *height > 0 {
   243  		// TODO once we implement the MPS upgrade logic the error message should be updated (to reflect the other ways of setting the IsMPS flag value)
   244  		return newcfg, stored, fmt.Errorf("the IsMPS (multiple private states support) flag once configured at block height 0 cannot be changed")
   245  	}
   246  	compatErr := storedcfg.CheckCompatible(newcfg, *height, rawdb.GetIsQuorumEIP155Activated(db))
   247  	if compatErr != nil && *height != 0 && compatErr.RewindTo != 0 {
   248  		return newcfg, stored, compatErr
   249  	}
   250  	rawdb.WriteChainConfig(db, stored, newcfg)
   251  
   252  	// Quorum
   253  	if storedcfg.PrivacyEnhancementsBlock == nil {
   254  		checkAndPrintPrivacyEnhancementsWarning(newcfg)
   255  	}
   256  	// End Quorum
   257  
   258  	return newcfg, stored, nil
   259  }
   260  
   261  func checkAndPrintPrivacyEnhancementsWarning(config *params.ChainConfig) {
   262  	if config.PrivacyEnhancementsBlock != nil {
   263  		log.Warn("Privacy enhancements have been enabled from block height " + config.PrivacyEnhancementsBlock.String() +
   264  			". Please ensure your privacy manager is upgraded and supports privacy enhancements (tessera version 1.*) " +
   265  			"otherwise your quorum node will fail to start.")
   266  	}
   267  }
   268  
   269  func (g *Genesis) configOrDefault(ghash common.Hash) *params.ChainConfig {
   270  	switch {
   271  	case g != nil:
   272  		return g.Config
   273  	case ghash == params.MainnetGenesisHash:
   274  		return params.MainnetChainConfig
   275  	case ghash == params.RopstenGenesisHash:
   276  		return params.RopstenChainConfig
   277  	case ghash == params.RinkebyGenesisHash:
   278  		return params.RinkebyChainConfig
   279  	case ghash == params.GoerliGenesisHash:
   280  		return params.GoerliChainConfig
   281  	case ghash == params.YoloV2GenesisHash:
   282  		return params.YoloV2ChainConfig
   283  	default:
   284  		return params.AllEthashProtocolChanges
   285  	}
   286  }
   287  
   288  // ToBlock creates the genesis block and writes state of a genesis specification
   289  // to the given database (or discards it if nil).
   290  func (g *Genesis) ToBlock(db ethdb.Database) *types.Block {
   291  	if db == nil {
   292  		db = rawdb.NewMemoryDatabase()
   293  	}
   294  	statedb, _ := state.New(common.Hash{}, state.NewDatabase(db), nil)
   295  	for addr, account := range g.Alloc {
   296  		statedb.AddBalance(addr, account.Balance)
   297  		statedb.SetCode(addr, account.Code)
   298  		statedb.SetNonce(addr, account.Nonce)
   299  		for key, value := range account.Storage {
   300  			statedb.SetState(addr, key, value)
   301  		}
   302  	}
   303  	root := statedb.IntermediateRoot(false)
   304  	head := &types.Header{
   305  		Number:     new(big.Int).SetUint64(g.Number),
   306  		Nonce:      types.EncodeNonce(g.Nonce),
   307  		Time:       g.Timestamp,
   308  		ParentHash: g.ParentHash,
   309  		Extra:      g.ExtraData,
   310  		GasLimit:   g.GasLimit,
   311  		GasUsed:    g.GasUsed,
   312  		Difficulty: g.Difficulty,
   313  		MixDigest:  g.Mixhash,
   314  		Coinbase:   g.Coinbase,
   315  		Root:       root,
   316  	}
   317  	if g.GasLimit == 0 {
   318  		head.GasLimit = params.GenesisGasLimit
   319  	}
   320  	if g.Difficulty == nil {
   321  		head.Difficulty = params.GenesisDifficulty
   322  	}
   323  	statedb.Commit(false)
   324  	statedb.Database().TrieDB().Commit(root, true, nil)
   325  
   326  	return types.NewBlock(head, nil, nil, nil, new(trie.Trie))
   327  }
   328  
   329  // Commit writes the block and state of a genesis specification to the database.
   330  // The block is committed as the canonical head block.
   331  func (g *Genesis) Commit(db ethdb.Database) (*types.Block, error) {
   332  	block := g.ToBlock(db)
   333  	if block.Number().Sign() != 0 {
   334  		return nil, fmt.Errorf("can't commit genesis block with number > 0")
   335  	}
   336  	config := g.Config
   337  	if config == nil {
   338  		config = params.AllEthashProtocolChanges
   339  	}
   340  	if err := config.CheckConfigForkOrder(); err != nil {
   341  		return nil, err
   342  	}
   343  	rawdb.WriteTd(db, block.Hash(), block.NumberU64(), g.Difficulty)
   344  	rawdb.WriteBlock(db, block)
   345  	rawdb.WriteReceipts(db, block.Hash(), block.NumberU64(), nil)
   346  	rawdb.WriteCanonicalHash(db, block.Hash(), block.NumberU64())
   347  	rawdb.WriteHeadBlockHash(db, block.Hash())
   348  	rawdb.WriteHeadFastBlockHash(db, block.Hash())
   349  	rawdb.WriteHeadHeaderHash(db, block.Hash())
   350  	rawdb.WriteChainConfig(db, block.Hash(), config)
   351  	return block, nil
   352  }
   353  
   354  // MustCommit writes the genesis block and state to db, panicking on error.
   355  // The block is committed as the canonical head block.
   356  func (g *Genesis) MustCommit(db ethdb.Database) *types.Block {
   357  	block, err := g.Commit(db)
   358  	if err != nil {
   359  		panic(err)
   360  	}
   361  	return block
   362  }
   363  
   364  // GenesisBlockForTesting creates and writes a block in which addr has the given wei balance.
   365  func GenesisBlockForTesting(db ethdb.Database, addr common.Address, balance *big.Int) *types.Block {
   366  	g := Genesis{Alloc: GenesisAlloc{addr: {Balance: balance}}}
   367  	return g.MustCommit(db)
   368  }
   369  
   370  // DefaultGenesisBlock returns the Ethereum main net genesis block.
   371  func DefaultGenesisBlock() *Genesis {
   372  	return &Genesis{
   373  		Config:     params.MainnetChainConfig,
   374  		Nonce:      66,
   375  		ExtraData:  hexutil.MustDecode("0x11bbe8db4e347b4e8c937c1c8370e4b5ed33adb3db69cbdb7a38e1e50b1b82fa"),
   376  		GasLimit:   5000,
   377  		Difficulty: big.NewInt(17179869184),
   378  		Alloc:      decodePrealloc(mainnetAllocData),
   379  	}
   380  }
   381  
   382  // DefaultRopstenGenesisBlock returns the Ropsten network genesis block.
   383  func DefaultRopstenGenesisBlock() *Genesis {
   384  	return &Genesis{
   385  		Config:     params.RopstenChainConfig,
   386  		Nonce:      66,
   387  		ExtraData:  hexutil.MustDecode("0x3535353535353535353535353535353535353535353535353535353535353535"),
   388  		GasLimit:   16777216,
   389  		Difficulty: big.NewInt(1048576),
   390  		Alloc:      decodePrealloc(ropstenAllocData),
   391  	}
   392  }
   393  
   394  // DefaultRinkebyGenesisBlock returns the Rinkeby network genesis block.
   395  func DefaultRinkebyGenesisBlock() *Genesis {
   396  	return &Genesis{
   397  		Config:     params.RinkebyChainConfig,
   398  		Timestamp:  1492009146,
   399  		ExtraData:  hexutil.MustDecode("0x52657370656374206d7920617574686f7269746168207e452e436172746d616e42eb768f2244c8811c63729a21a3569731535f067ffc57839b00206d1ad20c69a1981b489f772031b279182d99e65703f0076e4812653aab85fca0f00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"),
   400  		GasLimit:   4700000,
   401  		Difficulty: big.NewInt(1),
   402  		Alloc:      decodePrealloc(rinkebyAllocData),
   403  	}
   404  }
   405  
   406  // DefaultGoerliGenesisBlock returns the Görli network genesis block.
   407  func DefaultGoerliGenesisBlock() *Genesis {
   408  	return &Genesis{
   409  		Config:     params.GoerliChainConfig,
   410  		Timestamp:  1548854791,
   411  		ExtraData:  hexutil.MustDecode("0x22466c6578692069732061207468696e6722202d204166726900000000000000e0a2bd4258d2768837baa26a28fe71dc079f84c70000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"),
   412  		GasLimit:   10485760,
   413  		Difficulty: big.NewInt(1),
   414  		Alloc:      decodePrealloc(goerliAllocData),
   415  	}
   416  }
   417  
   418  func DefaultYoloV2GenesisBlock() *Genesis {
   419  	// TODO: Update with yolov2 values + regenerate alloc data
   420  	return &Genesis{
   421  		Config:     params.YoloV2ChainConfig,
   422  		Timestamp:  0x5f91b932,
   423  		ExtraData:  hexutil.MustDecode("0x00000000000000000000000000000000000000000000000000000000000000008a37866fd3627c9205a37c8685666f32ec07bb1b0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"),
   424  		GasLimit:   0x47b760,
   425  		Difficulty: big.NewInt(1),
   426  		Alloc:      decodePrealloc(yoloV1AllocData),
   427  	}
   428  }
   429  
   430  // DeveloperGenesisBlock returns the 'geth --dev' genesis block.
   431  func DeveloperGenesisBlock(period uint64, faucet common.Address) *Genesis {
   432  	// Override the default period to the user requested one
   433  	config := *params.AllCliqueProtocolChanges
   434  	config.Clique.Period = period
   435  
   436  	// Assemble and return the genesis with the precompiles and faucet pre-funded
   437  	return &Genesis{
   438  		Config:     &config,
   439  		ExtraData:  append(append(make([]byte, 32), faucet[:]...), make([]byte, crypto.SignatureLength)...),
   440  		GasLimit:   11500000,
   441  		Difficulty: big.NewInt(1),
   442  		Alloc: map[common.Address]GenesisAccount{
   443  			common.BytesToAddress([]byte{1}): {Balance: big.NewInt(1)}, // ECRecover
   444  			common.BytesToAddress([]byte{2}): {Balance: big.NewInt(1)}, // SHA256
   445  			common.BytesToAddress([]byte{3}): {Balance: big.NewInt(1)}, // RIPEMD
   446  			common.BytesToAddress([]byte{4}): {Balance: big.NewInt(1)}, // Identity
   447  			common.BytesToAddress([]byte{5}): {Balance: big.NewInt(1)}, // ModExp
   448  			common.BytesToAddress([]byte{6}): {Balance: big.NewInt(1)}, // ECAdd
   449  			common.BytesToAddress([]byte{7}): {Balance: big.NewInt(1)}, // ECScalarMul
   450  			common.BytesToAddress([]byte{8}): {Balance: big.NewInt(1)}, // ECPairing
   451  			common.BytesToAddress([]byte{9}): {Balance: big.NewInt(1)}, // BLAKE2b
   452  			faucet:                           {Balance: new(big.Int).Sub(new(big.Int).Lsh(big.NewInt(1), 256), big.NewInt(9))},
   453  		},
   454  	}
   455  }
   456  
   457  func decodePrealloc(data string) GenesisAlloc {
   458  	var p []struct{ Addr, Balance *big.Int }
   459  	if err := rlp.NewStream(strings.NewReader(data), 0).Decode(&p); err != nil {
   460  		panic(err)
   461  	}
   462  	ga := make(GenesisAlloc, len(p))
   463  	for _, account := range p {
   464  		ga[common.BigToAddress(account.Addr)] = GenesisAccount{Balance: account.Balance}
   465  	}
   466  	return ga
   467  }