mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-08-20 10:52:25 +00:00
cmd, core: resolve scheme from a read-write database
This commit is contained in:
parent
2c007cfed7
commit
b42f162a6c
3 changed files with 8 additions and 41 deletions
|
|
@ -1722,7 +1722,7 @@ func SetEthConfig(ctx *cli.Context, stack *node.Node, cfg *ethconfig.Config) {
|
||||||
cfg.StateHistory = ctx.Uint64(StateHistoryFlag.Name)
|
cfg.StateHistory = ctx.Uint64(StateHistoryFlag.Name)
|
||||||
}
|
}
|
||||||
// Parse state scheme, abort the process if it's not compatible.
|
// Parse state scheme, abort the process if it's not compatible.
|
||||||
chaindb := tryMakeReadOnlyDatabase(ctx, stack)
|
chaindb := MakeChainDatabase(ctx, stack, false)
|
||||||
scheme, err := ParseStateScheme(ctx, chaindb)
|
scheme, err := ParseStateScheme(ctx, chaindb)
|
||||||
chaindb.Close()
|
chaindb.Close()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
|
||||||
|
|
@ -120,8 +120,8 @@ func (ga *GenesisAlloc) UnmarshalJSON(data []byte) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// deriveHash computes the state root according to the genesis specification.
|
// hash computes the state root according to the genesis specification.
|
||||||
func (ga *GenesisAlloc) deriveHash() (common.Hash, error) {
|
func (ga *GenesisAlloc) hash() (common.Hash, error) {
|
||||||
// Create an ephemeral in-memory database for computing hash,
|
// Create an ephemeral in-memory database for computing hash,
|
||||||
// all the derived states will be discarded to not pollute disk.
|
// all the derived states will be discarded to not pollute disk.
|
||||||
db := state.NewDatabase(rawdb.NewMemoryDatabase())
|
db := state.NewDatabase(rawdb.NewMemoryDatabase())
|
||||||
|
|
@ -142,9 +142,9 @@ func (ga *GenesisAlloc) deriveHash() (common.Hash, error) {
|
||||||
return statedb.Commit(0, false)
|
return statedb.Commit(0, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
// flush is very similar with deriveHash, but the main difference is
|
// flush is very similar with hash, but the main difference is all the generated
|
||||||
// all the generated states will be persisted into the given database.
|
// states will be persisted into the given database. Also, the genesis state
|
||||||
// Also, the genesis state specification will be flushed as well.
|
// specification will be flushed as well.
|
||||||
func (ga *GenesisAlloc) flush(db ethdb.Database, triedb *trie.Database, blockhash common.Hash) error {
|
func (ga *GenesisAlloc) flush(db ethdb.Database, triedb *trie.Database, blockhash common.Hash) error {
|
||||||
statedb, err := state.New(types.EmptyRootHash, state.NewDatabaseWithNodeDB(db, triedb), nil)
|
statedb, err := state.New(types.EmptyRootHash, state.NewDatabaseWithNodeDB(db, triedb), nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -179,39 +179,6 @@ func (ga *GenesisAlloc) flush(db ethdb.Database, triedb *trie.Database, blockhas
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// CommitGenesisState loads the stored genesis state with the given block
|
|
||||||
// hash and commits it into the provided trie database.
|
|
||||||
func CommitGenesisState(db ethdb.Database, triedb *trie.Database, blockhash common.Hash) error {
|
|
||||||
var alloc GenesisAlloc
|
|
||||||
blob := rawdb.ReadGenesisStateSpec(db, blockhash)
|
|
||||||
if len(blob) != 0 {
|
|
||||||
if err := alloc.UnmarshalJSON(blob); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// Genesis allocation is missing and there are several possibilities:
|
|
||||||
// the node is legacy which doesn't persist the genesis allocation or
|
|
||||||
// the persisted allocation is just lost.
|
|
||||||
// - supported networks(mainnet, testnets), recover with defined allocations
|
|
||||||
// - private network, can't recover
|
|
||||||
var genesis *Genesis
|
|
||||||
switch blockhash {
|
|
||||||
case params.MainnetGenesisHash:
|
|
||||||
genesis = DefaultGenesisBlock()
|
|
||||||
case params.GoerliGenesisHash:
|
|
||||||
genesis = DefaultGoerliGenesisBlock()
|
|
||||||
case params.SepoliaGenesisHash:
|
|
||||||
genesis = DefaultSepoliaGenesisBlock()
|
|
||||||
}
|
|
||||||
if genesis != nil {
|
|
||||||
alloc = genesis.Alloc
|
|
||||||
} else {
|
|
||||||
return errors.New("not found")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return alloc.flush(db, triedb, blockhash)
|
|
||||||
}
|
|
||||||
|
|
||||||
// GenesisAccount is an account in the state of the genesis block.
|
// GenesisAccount is an account in the state of the genesis block.
|
||||||
type GenesisAccount struct {
|
type GenesisAccount struct {
|
||||||
Code []byte `json:"code,omitempty"`
|
Code []byte `json:"code,omitempty"`
|
||||||
|
|
@ -444,7 +411,7 @@ func (g *Genesis) configOrDefault(ghash common.Hash) *params.ChainConfig {
|
||||||
|
|
||||||
// ToBlock returns the genesis block according to genesis specification.
|
// ToBlock returns the genesis block according to genesis specification.
|
||||||
func (g *Genesis) ToBlock() *types.Block {
|
func (g *Genesis) ToBlock() *types.Block {
|
||||||
root, err := g.Alloc.deriveHash()
|
root, err := g.Alloc.hash()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -231,7 +231,7 @@ func TestReadWriteGenesisAlloc(t *testing.T) {
|
||||||
{1}: {Balance: big.NewInt(1), Storage: map[common.Hash]common.Hash{{1}: {1}}},
|
{1}: {Balance: big.NewInt(1), Storage: map[common.Hash]common.Hash{{1}: {1}}},
|
||||||
{2}: {Balance: big.NewInt(2), Storage: map[common.Hash]common.Hash{{2}: {2}}},
|
{2}: {Balance: big.NewInt(2), Storage: map[common.Hash]common.Hash{{2}: {2}}},
|
||||||
}
|
}
|
||||||
hash, _ = alloc.deriveHash()
|
hash, _ = alloc.hash()
|
||||||
)
|
)
|
||||||
blob, _ := json.Marshal(alloc)
|
blob, _ := json.Marshal(alloc)
|
||||||
rawdb.WriteGenesisStateSpec(db, hash, blob)
|
rawdb.WriteGenesisStateSpec(db, hash, blob)
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue