forked from cerc-io/plugeth
core, eth, trie: expose more detailed dirty ram tracking for diff layers (#27971)
This commit is contained in:
+9
-5
@@ -1021,7 +1021,7 @@ func (bc *BlockChain) Stop() {
|
||||
for !bc.triegc.Empty() {
|
||||
triedb.Dereference(bc.triegc.PopItem())
|
||||
}
|
||||
if size, _ := triedb.Size(); size != 0 {
|
||||
if _, nodes, _ := triedb.Size(); nodes != 0 { // all memory is contained within the nodes return for hashdb
|
||||
log.Error("Dangling trie nodes after full cleanup")
|
||||
}
|
||||
}
|
||||
@@ -1429,8 +1429,8 @@ func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types.
|
||||
}
|
||||
// If we exceeded our memory allowance, flush matured singleton nodes to disk
|
||||
var (
|
||||
nodes, imgs = bc.triedb.Size()
|
||||
limit = common.StorageSize(bc.cacheConfig.TrieDirtyLimit) * 1024 * 1024
|
||||
_, nodes, imgs = bc.triedb.Size() // all memory is contained within the nodes return for hashdb
|
||||
limit = common.StorageSize(bc.cacheConfig.TrieDirtyLimit) * 1024 * 1024
|
||||
)
|
||||
if nodes > limit || imgs > 4*1024*1024 {
|
||||
bc.triedb.Cap(limit - ethdb.IdealBatchSize)
|
||||
@@ -1866,8 +1866,12 @@ func (bc *BlockChain) insertChain(chain types.Blocks, setHead bool) (int, error)
|
||||
stats.processed++
|
||||
stats.usedGas += usedGas
|
||||
|
||||
dirty, _ := bc.triedb.Size()
|
||||
stats.report(chain, it.index, dirty, setHead)
|
||||
var snapDiffItems, snapBufItems common.StorageSize
|
||||
if bc.snaps != nil {
|
||||
snapDiffItems, snapBufItems = bc.snaps.Size()
|
||||
}
|
||||
trieDiffNodes, trieBufNodes, _ := bc.triedb.Size()
|
||||
stats.report(chain, it.index, snapDiffItems, snapBufItems, trieDiffNodes, trieBufNodes, setHead)
|
||||
|
||||
if !setHead {
|
||||
// After merge we expect few side chains. Simply count
|
||||
|
||||
@@ -39,7 +39,7 @@ const statsReportLimit = 8 * time.Second
|
||||
|
||||
// report prints statistics if some number of blocks have been processed
|
||||
// or more than a few seconds have passed since the last message.
|
||||
func (st *insertStats) report(chain []*types.Block, index int, dirty common.StorageSize, setHead bool) {
|
||||
func (st *insertStats) report(chain []*types.Block, index int, snapDiffItems, snapBufItems, trieDiffNodes, triebufNodes common.StorageSize, setHead bool) {
|
||||
// Fetch the timings for the batch
|
||||
var (
|
||||
now = mclock.Now()
|
||||
@@ -63,7 +63,16 @@ func (st *insertStats) report(chain []*types.Block, index int, dirty common.Stor
|
||||
if timestamp := time.Unix(int64(end.Time()), 0); time.Since(timestamp) > time.Minute {
|
||||
context = append(context, []interface{}{"age", common.PrettyAge(timestamp)}...)
|
||||
}
|
||||
context = append(context, []interface{}{"dirty", dirty}...)
|
||||
if snapDiffItems != 0 || snapBufItems != 0 { // snapshots enabled
|
||||
context = append(context, []interface{}{"snapdiffs", snapDiffItems}...)
|
||||
if snapBufItems != 0 { // future snapshot refactor
|
||||
context = append(context, []interface{}{"snapdirty", snapBufItems}...)
|
||||
}
|
||||
}
|
||||
if trieDiffNodes != 0 { // pathdb
|
||||
context = append(context, []interface{}{"triediffs", trieDiffNodes}...)
|
||||
}
|
||||
context = append(context, []interface{}{"triedirty", triebufNodes}...)
|
||||
|
||||
if st.queued > 0 {
|
||||
context = append(context, []interface{}{"queued", st.queued}...)
|
||||
|
||||
@@ -1844,7 +1844,7 @@ func TestTrieForkGC(t *testing.T) {
|
||||
chain.TrieDB().Dereference(blocks[len(blocks)-1-i].Root())
|
||||
chain.TrieDB().Dereference(forks[len(blocks)-1-i].Root())
|
||||
}
|
||||
if nodes, _ := chain.TrieDB().Size(); nodes > 0 {
|
||||
if _, nodes, _ := chain.TrieDB().Size(); nodes > 0 { // all memory is returned in the nodes return for hashdb
|
||||
t.Fatalf("stale tries still alive after garbase collection")
|
||||
}
|
||||
}
|
||||
|
||||
@@ -852,3 +852,21 @@ func (t *Tree) DiskRoot() common.Hash {
|
||||
|
||||
return t.diskRoot()
|
||||
}
|
||||
|
||||
// Size returns the memory usage of the diff layers above the disk layer and the
|
||||
// dirty nodes buffered in the disk layer. Currently, the implementation uses a
|
||||
// special diff layer (the first) as an aggregator simulating a dirty buffer, so
|
||||
// the second return will always be 0. However, this will be made consistent with
|
||||
// the pathdb, which will require a second return.
|
||||
func (t *Tree) Size() (diffs common.StorageSize, buf common.StorageSize) {
|
||||
t.lock.RLock()
|
||||
defer t.lock.RUnlock()
|
||||
|
||||
var size common.StorageSize
|
||||
for _, layer := range t.layers {
|
||||
if layer, ok := layer.(*diffLayer); ok {
|
||||
size += common.StorageSize(layer.memory)
|
||||
}
|
||||
}
|
||||
return size, 0
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user