From aead14eeda87794899daed7fbdcca11fb9021fbd Mon Sep 17 00:00:00 2001 From: VM <112189277+sysvm@users.noreply.github.com> Date: Fri, 5 Jul 2024 11:50:24 +0800 Subject: [PATCH] pathdb: handle persistent id when using nodebufferlist (#121) --- trie/triedb/pathdb/disklayer.go | 18 ++++++++++++++++-- trie/triedb/pathdb/nodebufferlist.go | 7 +++++++ 2 files changed, 23 insertions(+), 2 deletions(-) diff --git a/trie/triedb/pathdb/disklayer.go b/trie/triedb/pathdb/disklayer.go index 26219ad58d..c934f2f5c3 100644 --- a/trie/triedb/pathdb/disklayer.go +++ b/trie/triedb/pathdb/disklayer.go @@ -281,6 +281,7 @@ func (dl *diskLayer) commit(bottom *diffLayer, force bool) (*diskLayer, error) { var ( overflow bool oldest uint64 + limit = dl.db.config.StateHistory ) if dl.db.freezer != nil { err := writeHistory(dl.db.freezer, bottom) @@ -293,7 +294,6 @@ func (dl *diskLayer) commit(bottom *diffLayer, force bool) (*diskLayer, error) { if err != nil { return nil, err } - limit := dl.db.config.StateHistory if limit != 0 && bottom.stateID()-tail > limit { overflow = true oldest = bottom.stateID() - limit + 1 // track the id of history **after truncation** @@ -322,17 +322,31 @@ func (dl *diskLayer) commit(bottom *diffLayer, force bool) (*diskLayer, error) { if !force && rawdb.ReadPersistentStateID(dl.db.diskdb) < oldest { force = true } + if err := ndl.buffer.flush(ndl.db.diskdb, ndl.cleans, ndl.id, force); err != nil { return nil, err } // To remove outdated history objects from the end, we set the 'tail' parameter // to 'oldest-1' due to the offset between the freezer index and the history ID. if overflow { + if _, ok := dl.buffer.(*nodebufferlist); ok { + persistentID := rawdb.ReadPersistentStateID(dl.db.diskdb) + if persistentID > limit { + oldest = persistentID - limit + 1 + log.Info("Forcing prune ancient under nodebufferlist", "disk_persistent_state_id", + persistentID, "truncate_tail", oldest) + } else { + log.Info("No prune ancient under nodebufferlist, less than db config state history limit") + return ndl, nil + } + } + pruned, err := truncateFromTail(ndl.db.diskdb, ndl.db.freezer, oldest-1) if err != nil { + log.Error("Failed to truncate from tail", "ntail", oldest-1, "error", err) return nil, err } - log.Debug("Pruned state history", "items", pruned, "tailid", oldest) + log.Debug("Pruned state history", "items", pruned, "tail_id", oldest) } // The bottom has been eaten by disklayer, releasing the hash cache of bottom difflayer. diff --git a/trie/triedb/pathdb/nodebufferlist.go b/trie/triedb/pathdb/nodebufferlist.go index 2b92fef855..12d055b06d 100644 --- a/trie/triedb/pathdb/nodebufferlist.go +++ b/trie/triedb/pathdb/nodebufferlist.go @@ -270,12 +270,18 @@ func (nf *nodebufferlist) flush(db ethdb.KeyValueStore, clean *fastcache.Cache, } commitFunc := func(buffer *multiDifflayer) bool { + if nf.count <= nf.rsevMdNum { + log.Info("keep multiDiffLayer in node bufferList for getting withdrawal proof", + "reserved_multidiflayer", nf.rsevMdNum, "bufferList_count", nf.count) + return false + } if err := nf.base.commit(buffer.root, buffer.id, buffer.block, buffer.layers, buffer.nodes); err != nil { log.Crit("failed to commit nodes to base node buffer", "error", err) } _ = nf.popBack() return true } + nf.traverseReverse(commitFunc) persistID := nf.persistID + nf.base.layers err := nf.base.flush(nf.db, nf.clean, persistID) @@ -285,6 +291,7 @@ func (nf *nodebufferlist) flush(db ethdb.KeyValueStore, clean *fastcache.Cache, nf.isFlushing.Store(false) nf.base.reset() nf.persistID = persistID + return nil }