@@ -57,6 +57,7 @@ const (
5757// Config includes all the configurations for pruning.
5858type Config struct {
5959 Datadir string // The directory of the state database
60+ Cachedir string // The directory of state clean cache
6061 BloomSize uint64 // The Megabytes of memory allocated to bloom-filter
6162}
6263
@@ -240,7 +241,7 @@ func (p *Pruner) Prune(root common.Hash) error {
240241 return err
241242 }
242243 if stateBloomRoot != (common.Hash {}) {
243- return RecoverPruning (p .config .Datadir , p .db )
244+ return RecoverPruning (p .config .Datadir , p .db , p . config . Cachedir )
244245 }
245246 // If the target state root is not specified, use the HEAD-127 as the
246247 // target. The reason for picking it is:
@@ -298,6 +299,12 @@ func (p *Pruner) Prune(root common.Hash) error {
298299 log .Info ("Selecting user-specified state as the pruning target" , "root" , root )
299300 }
300301 }
302+ // Before start the pruning, delete the clean trie cache first.
303+ // It's necessary otherwise in the next restart we will hit the
304+ // deleted state root in the "clean cache" so that the incomplete
305+ // state is picked for usage.
306+ deleteCleanTrieCache (p .config .Cachedir )
307+
301308 // All the state roots of the middle layer should be forcibly pruned,
302309 // otherwise the dangling state will be left.
303310 middleRoots := make (map [common.Hash ]struct {})
@@ -335,7 +342,7 @@ func (p *Pruner) Prune(root common.Hash) error {
335342// pruning can be resumed. What's more if the bloom filter is constructed, the
336343// pruning **has to be resumed**. Otherwise a lot of dangling nodes may be left
337344// in the disk.
338- func RecoverPruning (datadir string , db ethdb.Database ) error {
345+ func RecoverPruning (datadir string , db ethdb.Database , trieCachePath string ) error {
339346 stateBloomPath , stateBloomRoot , err := findBloomFilter (datadir )
340347 if err != nil {
341348 return err
@@ -371,6 +378,12 @@ func RecoverPruning(datadir string, db ethdb.Database) error {
371378 }
372379 log .Info ("Loaded state bloom filter" , "path" , stateBloomPath )
373380
381+ // Before start the pruning, delete the clean trie cache first.
382+ // It's necessary otherwise in the next restart we will hit the
383+ // deleted state root in the "clean cache" so that the incomplete
384+ // state is picked for usage.
385+ deleteCleanTrieCache (trieCachePath )
386+
374387 // All the state roots of the middle layers should be forcibly pruned,
375388 // otherwise the dangling state will be left.
376389 var (
@@ -484,3 +497,23 @@ func findBloomFilter(datadir string) (string, common.Hash, error) {
484497 }
485498 return stateBloomPath , stateBloomRoot , nil
486499}
500+
501+ const warningLog = `
502+
503+ WARNING!
504+
505+ The clean trie cache is not found. Please delete it by yourself after the
506+ pruning. Remember don't start the Geth without deleting the clean trie cache
507+ otherwise the entire database may be damaged!
508+
509+ Check the command description "geth snapshot prune-state --help" for more details.
510+ `
511+
512+ func deleteCleanTrieCache (path string ) {
513+ if ! common .FileExist (path ) {
514+ log .Warn (warningLog )
515+ return
516+ }
517+ os .RemoveAll (path )
518+ log .Info ("Deleted trie clean cache" , "path" , path )
519+ }
0 commit comments