From 8e491607829d9096d6fd19d46cd832ca1767311d Mon Sep 17 00:00:00 2001 From: VM Date: Tue, 28 May 2024 10:36:51 +0800 Subject: [PATCH] fix: add an empty freeze db --- cmd/geth/dbcmd.go | 2 +- core/rawdb/database.go | 141 ++++++++++++++++++++++++++++++++++++++++- 2 files changed, 140 insertions(+), 3 deletions(-) diff --git a/cmd/geth/dbcmd.go b/cmd/geth/dbcmd.go index 1cbf031975..fae0f63532 100644 --- a/cmd/geth/dbcmd.go +++ b/cmd/geth/dbcmd.go @@ -508,7 +508,7 @@ func ancientInspect(ctx *cli.Context) error { stack, _ := makeConfigNode(ctx) defer stack.Close() - db := utils.MakeChainDatabase(ctx, stack, true, true) + db := utils.MakeChainDatabase(ctx, stack, true, false) defer db.Close() return rawdb.AncientInspect(db) } diff --git a/core/rawdb/database.go b/core/rawdb/database.go index a0e3147f2a..e7f00fdf10 100644 --- a/core/rawdb/database.go +++ b/core/rawdb/database.go @@ -61,7 +61,7 @@ func (frdb *freezerdb) BlockStoreReader() ethdb.Reader { } func (frdb *freezerdb) BlockStoreWriter() ethdb.Writer { - //TODO implement me + // TODO implement me panic("implement me") } @@ -318,6 +318,137 @@ func NewDatabase(db ethdb.KeyValueStore) ethdb.Database { return &nofreezedb{KeyValueStore: db} } +type emptyfreezedb struct { + ethdb.KeyValueStore +} + +// HasAncient returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) HasAncient(kind string, number uint64) (bool, error) { + return false, nil +} + +// Ancient returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) Ancient(kind string, number uint64) ([]byte, error) { + return nil, nil +} + +// AncientRange returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) AncientRange(kind string, start, max, maxByteSize uint64) ([][]byte, error) { + return nil, nil +} + +// Ancients returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) Ancients() (uint64, error) { + return 0, nil +} + +// Ancients returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) ItemAmountInAncient() (uint64, error) { + return 0, nil +} + +// Tail returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) Tail() (uint64, error) { + return 0, nil +} + +// AncientSize returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) AncientSize(kind string) (uint64, error) { + return 0, nil +} + +// ModifyAncients returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) ModifyAncients(func(ethdb.AncientWriteOp) error) (int64, error) { + return 0, nil +} + +// TruncateHead returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) TruncateHead(items uint64) (uint64, error) { + return 0, nil +} + +// TruncateTail returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) TruncateTail(items uint64) (uint64, error) { + return 0, nil +} + +// TruncateTableTail returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) TruncateTableTail(kind string, tail uint64) (uint64, error) { + return 0, nil +} + +// ResetTable returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) ResetTable(kind string, startAt uint64, onlyEmpty bool) error { + return nil +} + +// Sync returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) Sync() error { + return nil +} + +func (db *emptyfreezedb) DiffStore() ethdb.KeyValueStore { + return db +} + +func (db *emptyfreezedb) SetDiffStore(diff ethdb.KeyValueStore) { +} + +func (db *emptyfreezedb) StateStore() ethdb.Database { + return db +} + +func (db *emptyfreezedb) SetStateStore(state ethdb.Database) { +} + +func (db *emptyfreezedb) StateStoreReader() ethdb.Reader { + return db +} + +func (db *emptyfreezedb) BlockStore() ethdb.Database { + return db +} + +func (db *emptyfreezedb) SetBlockStore(block ethdb.Database) { +} + +func (db *emptyfreezedb) BlockStoreReader() ethdb.Reader { + return db +} + +func (db *emptyfreezedb) BlockStoreWriter() ethdb.Writer { + return db +} + +func (db *emptyfreezedb) ReadAncients(fn func(reader ethdb.AncientReaderOp) error) (err error) { + return nil +} + +func (db *emptyfreezedb) AncientOffSet() uint64 { + return 0 +} + +// MigrateTable returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) MigrateTable(kind string, convert convertLegacyFn) error { + return nil +} + +// AncientDatadir returns nil for pruned db that we don't have a backing chain freezer. +func (db *emptyfreezedb) AncientDatadir() (string, error) { + return "", nil +} + +func (db *emptyfreezedb) SetupFreezerEnv(env *ethdb.FreezerEnv) error { + return nil +} + +// NewEmptyFreezeDB is used for CLI such as `geth db inspect` in pruned db that we don't +// have a backing chain freezer. +// WARNING: it must be only used in the above case. +func NewEmptyFreezeDB(db ethdb.KeyValueStore) ethdb.Database { + return &emptyfreezedb{KeyValueStore: db} +} + // NewFreezerDb only create a freezer without statedb. func NewFreezerDb(db ethdb.KeyValueStore, frz, namespace string, readonly bool, newOffSet uint64) (*Freezer, error) { // Create the idle freezer instance, this operation should be atomic to avoid mismatch between offset and acientDB. @@ -367,6 +498,12 @@ func NewDatabaseWithFreezer(db ethdb.KeyValueStore, ancient string, namespace st offset = ReadOffSetOfCurrentAncientFreezer(db) } + // This case is used for someone who wants to execute geth db inspect CLI in a pruned db + if !disableFreeze && readonly && ReadAncientType(db) == PruneFreezerType { + log.Warn("Disk db is pruned, return an empty freezer db which is used for CLI") + return NewEmptyFreezeDB(db), nil + } + if pruneAncientData && !disableFreeze && !readonly { frdb, err := newPrunedFreezer(resolveChainFreezerDir(ancient), db, offset) if err != nil { @@ -619,7 +756,7 @@ func Open(o OpenOptions) (ethdb.Database, error) { } if ReadAncientType(kvdb) == PruneFreezerType { if !o.PruneAncientData { - log.Warn("Disk db is pruned") + log.Warn("NOTICE: You're opening a disk db is pruned!") } } if len(o.AncientsDirectory) == 0 {