Skip to content

Commit 992cad5

Browse files
fjljagdeep sidhu
authored and
jagdeep sidhu
committed
core/rawdb: improve database stats output (ethereum#31463)
Instead of reporting all filtermaps stuff in one line, I'm breaking it down into the three separate kinds of entries here. ``` +-----------------------+-----------------------------+------------+------------+ | DATABASE | CATEGORY | SIZE | ITEMS | +-----------------------+-----------------------------+------------+------------+ | Key-Value store | Log index filter-map rows | 59.21 GiB | 616077345 | | Key-Value store | Log index last-block-of-map | 12.35 MiB | 269755 | | Key-Value store | Log index block-lv | 421.70 MiB | 22109169 | ``` Also added some other changes to make it easier to debug: - restored bloombits into the inspect output, so we notice if it doesn't get deleted for some reason - tracking of unaccounted key examples
1 parent dd34b94 commit 992cad5

File tree

3 files changed

+94
-54
lines changed

3 files changed

+94
-54
lines changed

core/rawdb/accessors_indexes.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -502,5 +502,5 @@ func DeleteBloomBitsDb(db ethdb.KeyValueRangeDeleter) error {
502502
if err := deletePrefixRange(db, bloomBitsPrefix); err != nil {
503503
return err
504504
}
505-
return deletePrefixRange(db, bloomBitsIndexPrefix)
505+
return deletePrefixRange(db, bloomBitsMetaPrefix)
506506
}

core/rawdb/database.go

+81-42
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,10 @@ import (
2020
"bytes"
2121
"errors"
2222
"fmt"
23+
"maps"
2324
"os"
2425
"path/filepath"
26+
"slices"
2527
"strings"
2628
"time"
2729

@@ -360,24 +362,27 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
360362
logged = time.Now()
361363

362364
// Key-value store statistics
363-
headers stat
364-
bodies stat
365-
receipts stat
366-
tds stat
367-
numHashPairings stat
368-
hashNumPairings stat
369-
legacyTries stat
370-
stateLookups stat
371-
accountTries stat
372-
storageTries stat
373-
codes stat
374-
txLookups stat
375-
accountSnaps stat
376-
storageSnaps stat
377-
preimages stat
378-
filterMaps stat
379-
beaconHeaders stat
380-
cliqueSnaps stat
365+
headers stat
366+
bodies stat
367+
receipts stat
368+
tds stat
369+
numHashPairings stat
370+
hashNumPairings stat
371+
legacyTries stat
372+
stateLookups stat
373+
accountTries stat
374+
storageTries stat
375+
codes stat
376+
txLookups stat
377+
accountSnaps stat
378+
storageSnaps stat
379+
preimages stat
380+
beaconHeaders stat
381+
cliqueSnaps stat
382+
bloomBits stat
383+
filterMapRows stat
384+
filterMapLastBlock stat
385+
filterMapBlockLV stat
381386

382387
// Verkle statistics
383388
verkleTries stat
@@ -393,6 +398,11 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
393398

394399
// Totals
395400
total common.StorageSize
401+
402+
// This map tracks example keys for unaccounted data.
403+
// For each unique two-byte prefix, the first unaccounted key encountered
404+
// by the iterator will be stored.
405+
unaccountedKeys = make(map[[2]byte][]byte)
396406
)
397407
// Inspect key-value database first.
398408
for it.Next() {
@@ -436,19 +446,33 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
436446
metadata.Add(size)
437447
case bytes.HasPrefix(key, genesisPrefix) && len(key) == (len(genesisPrefix)+common.HashLength):
438448
metadata.Add(size)
439-
case bytes.HasPrefix(key, []byte(filterMapsPrefix)):
440-
filterMaps.Add(size)
441449
case bytes.HasPrefix(key, skeletonHeaderPrefix) && len(key) == (len(skeletonHeaderPrefix)+8):
442450
beaconHeaders.Add(size)
443451
case bytes.HasPrefix(key, CliqueSnapshotPrefix) && len(key) == 7+common.HashLength:
444452
cliqueSnaps.Add(size)
445-
case bytes.HasPrefix(key, ChtTablePrefix) ||
446-
bytes.HasPrefix(key, ChtIndexTablePrefix) ||
447-
bytes.HasPrefix(key, ChtPrefix): // Canonical hash trie
453+
454+
// new log index
455+
case bytes.HasPrefix(key, filterMapRowPrefix) && len(key) <= len(filterMapRowPrefix)+9:
456+
filterMapRows.Add(size)
457+
case bytes.HasPrefix(key, filterMapLastBlockPrefix) && len(key) == len(filterMapLastBlockPrefix)+4:
458+
filterMapLastBlock.Add(size)
459+
case bytes.HasPrefix(key, filterMapBlockLVPrefix) && len(key) == len(filterMapBlockLVPrefix)+8:
460+
filterMapBlockLV.Add(size)
461+
462+
// old log index (deprecated)
463+
case bytes.HasPrefix(key, bloomBitsPrefix) && len(key) == (len(bloomBitsPrefix)+10+common.HashLength):
464+
bloomBits.Add(size)
465+
case bytes.HasPrefix(key, bloomBitsMetaPrefix) && len(key) < len(bloomBitsMetaPrefix)+8:
466+
bloomBits.Add(size)
467+
468+
// LES indexes (deprecated)
469+
case bytes.HasPrefix(key, chtTablePrefix) ||
470+
bytes.HasPrefix(key, chtIndexTablePrefix) ||
471+
bytes.HasPrefix(key, chtPrefix): // Canonical hash trie
448472
chtTrieNodes.Add(size)
449-
case bytes.HasPrefix(key, BloomTrieTablePrefix) ||
450-
bytes.HasPrefix(key, BloomTrieIndexPrefix) ||
451-
bytes.HasPrefix(key, BloomTriePrefix): // Bloomtrie sub
473+
case bytes.HasPrefix(key, bloomTrieTablePrefix) ||
474+
bytes.HasPrefix(key, bloomTrieIndexPrefix) ||
475+
bytes.HasPrefix(key, bloomTriePrefix): // Bloomtrie sub
452476
bloomTrieNodes.Add(size)
453477

454478
// Verkle trie data is detected, determine the sub-category
@@ -468,24 +492,19 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
468492
default:
469493
unaccounted.Add(size)
470494
}
495+
496+
// Metadata keys
497+
case slices.ContainsFunc(knownMetadataKeys, func(x []byte) bool { return bytes.Equal(x, key) }):
498+
metadata.Add(size)
499+
471500
default:
472-
var accounted bool
473-
for _, meta := range [][]byte{
474-
databaseVersionKey, headHeaderKey, headBlockKey, headFastBlockKey, headFinalizedBlockKey,
475-
lastPivotKey, fastTrieProgressKey, snapshotDisabledKey, SnapshotRootKey, snapshotJournalKey,
476-
snapshotGeneratorKey, snapshotRecoveryKey, txIndexTailKey, fastTxLookupLimitKey,
477-
uncleanShutdownKey, badBlockKey, transitionStatusKey, skeletonSyncStatusKey,
478-
persistentStateIDKey, trieJournalKey, snapshotSyncStatusKey, snapSyncStatusFlagKey,
479-
} {
480-
if bytes.Equal(key, meta) {
481-
metadata.Add(size)
482-
accounted = true
483-
break
501+
unaccounted.Add(size)
502+
if len(key) >= 2 {
503+
prefix := [2]byte(key[:2])
504+
if _, ok := unaccountedKeys[prefix]; !ok {
505+
unaccountedKeys[prefix] = bytes.Clone(key)
484506
}
485507
}
486-
if !accounted {
487-
unaccounted.Add(size)
488-
}
489508
}
490509
count++
491510
if count%1000 == 0 && time.Since(logged) > 8*time.Second {
@@ -502,7 +521,10 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
502521
{"Key-Value store", "Block number->hash", numHashPairings.Size(), numHashPairings.Count()},
503522
{"Key-Value store", "Block hash->number", hashNumPairings.Size(), hashNumPairings.Count()},
504523
{"Key-Value store", "Transaction index", txLookups.Size(), txLookups.Count()},
505-
{"Key-Value store", "Log search index", filterMaps.Size(), filterMaps.Count()},
524+
{"Key-Value store", "Log index filter-map rows", filterMapRows.Size(), filterMapRows.Count()},
525+
{"Key-Value store", "Log index last-block-of-map", filterMapLastBlock.Size(), filterMapLastBlock.Count()},
526+
{"Key-Value store", "Log index block-lv", filterMapBlockLV.Size(), filterMapBlockLV.Count()},
527+
{"Key-Value store", "Log bloombits (deprecated)", bloomBits.Size(), bloomBits.Count()},
506528
{"Key-Value store", "Contract codes", codes.Size(), codes.Count()},
507529
{"Key-Value store", "Hash trie nodes", legacyTries.Size(), legacyTries.Count()},
508530
{"Key-Value store", "Path trie state lookups", stateLookups.Size(), stateLookups.Count()},
@@ -543,10 +565,23 @@ func InspectDatabase(db ethdb.Database, keyPrefix, keyStart []byte) error {
543565

544566
if unaccounted.size > 0 {
545567
log.Error("Database contains unaccounted data", "size", unaccounted.size, "count", unaccounted.count)
568+
for _, e := range slices.SortedFunc(maps.Values(unaccountedKeys), bytes.Compare) {
569+
log.Error(fmt.Sprintf(" example key: %x", e))
570+
}
546571
}
547572
return nil
548573
}
549574

575+
// This is the list of known 'metadata' keys stored in the databasse.
576+
var knownMetadataKeys = [][]byte{
577+
databaseVersionKey, headHeaderKey, headBlockKey, headFastBlockKey, headFinalizedBlockKey,
578+
lastPivotKey, fastTrieProgressKey, snapshotDisabledKey, SnapshotRootKey, snapshotJournalKey,
579+
snapshotGeneratorKey, snapshotRecoveryKey, txIndexTailKey, fastTxLookupLimitKey,
580+
uncleanShutdownKey, badBlockKey, transitionStatusKey, skeletonSyncStatusKey,
581+
persistentStateIDKey, trieJournalKey, snapshotSyncStatusKey, snapSyncStatusFlagKey,
582+
filterMapsRangeKey,
583+
}
584+
550585
// printChainMetadata prints out chain metadata to stderr.
551586
func printChainMetadata(db ethdb.KeyValueStore) {
552587
fmt.Fprintf(os.Stderr, "Chain metadata\n")
@@ -566,6 +601,7 @@ func ReadChainMetadata(db ethdb.KeyValueStore) [][]string {
566601
}
567602
return fmt.Sprintf("%d (%#x)", *val, *val)
568603
}
604+
569605
data := [][]string{
570606
{"databaseVersion", pp(ReadDatabaseVersion(db))},
571607
{"headBlockHash", fmt.Sprintf("%v", ReadHeadBlockHash(db))},
@@ -582,5 +618,8 @@ func ReadChainMetadata(db ethdb.KeyValueStore) [][]string {
582618
if b := ReadSkeletonSyncStatus(db); b != nil {
583619
data = append(data, []string{"SkeletonSyncStatus", string(b)})
584620
}
621+
if fmr, ok, _ := ReadFilterMapsRange(db); ok {
622+
data = append(data, []string{"filterMapsRange", fmt.Sprintf("%+v", fmr)})
623+
}
585624
return data
586625
}

core/rawdb/schema.go

+12-11
Original file line numberDiff line numberDiff line change
@@ -135,29 +135,30 @@ var (
135135
configPrefix = []byte("ethereum-config-") // config prefix for the db
136136
genesisPrefix = []byte("ethereum-genesis-") // genesis state prefix for the db
137137

138-
// bloomBitsIndexPrefix is the data table of a chain indexer to track its progress
139-
bloomBitsIndexPrefix = []byte("iB")
140-
141-
ChtPrefix = []byte("chtRootV2-") // ChtPrefix + chtNum (uint64 big endian) -> trie root hash
142-
ChtTablePrefix = []byte("cht-")
143-
ChtIndexTablePrefix = []byte("chtIndexV2-")
144-
145-
BloomTriePrefix = []byte("bltRoot-") // BloomTriePrefix + bloomTrieNum (uint64 big endian) -> trie root hash
146-
BloomTrieTablePrefix = []byte("blt-")
147-
BloomTrieIndexPrefix = []byte("bltIndex-")
148-
149138
CliqueSnapshotPrefix = []byte("clique-")
150139

151140
BestUpdateKey = []byte("update-") // bigEndian64(syncPeriod) -> RLP(types.LightClientUpdate) (nextCommittee only referenced by root hash)
152141
FixedCommitteeRootKey = []byte("fixedRoot-") // bigEndian64(syncPeriod) -> committee root hash
153142
SyncCommitteeKey = []byte("committee-") // bigEndian64(syncPeriod) -> serialized committee
154143

144+
// new log index
155145
filterMapsPrefix = "fm-"
156146
filterMapsRangeKey = []byte(filterMapsPrefix + "R")
157147
filterMapRowPrefix = []byte(filterMapsPrefix + "r") // filterMapRowPrefix + mapRowIndex (uint64 big endian) -> filter row
158148
filterMapLastBlockPrefix = []byte(filterMapsPrefix + "b") // filterMapLastBlockPrefix + mapIndex (uint32 big endian) -> block number (uint64 big endian)
159149
filterMapBlockLVPrefix = []byte(filterMapsPrefix + "p") // filterMapBlockLVPrefix + num (uint64 big endian) -> log value pointer (uint64 big endian)
160150

151+
// old log index
152+
bloomBitsMetaPrefix = []byte("iB")
153+
154+
// LES indexes
155+
chtPrefix = []byte("chtRootV2-") // ChtPrefix + chtNum (uint64 big endian) -> trie root hash
156+
chtTablePrefix = []byte("cht-")
157+
chtIndexTablePrefix = []byte("chtIndexV2-")
158+
bloomTriePrefix = []byte("bltRoot-") // BloomTriePrefix + bloomTrieNum (uint64 big endian) -> trie root hash
159+
bloomTrieTablePrefix = []byte("blt-")
160+
bloomTrieIndexPrefix = []byte("bltIndex-")
161+
161162
preimageCounter = metrics.NewRegisteredCounter("db/preimage/total", nil)
162163
preimageHitsCounter = metrics.NewRegisteredCounter("db/preimage/hits", nil)
163164
preimageMissCounter = metrics.NewRegisteredCounter("db/preimage/miss", nil)

0 commit comments

Comments
 (0)