mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-08-20 10:52:25 +00:00
core/rawdb : freezer sync closed and timer loops
This commit is contained in:
parent
1aa83290f5
commit
a04ed31615
2 changed files with 135 additions and 112 deletions
|
|
@ -29,17 +29,22 @@ import (
|
|||
"github.com/ethereum/go-ethereum/ethdb/memorydb"
|
||||
"github.com/ethereum/go-ethereum/log"
|
||||
"github.com/olekukonko/tablewriter"
|
||||
|
||||
"sync"
|
||||
)
|
||||
|
||||
// freezerdb is a database wrapper that enabled freezer data retrievals.
|
||||
type freezerdb struct {
|
||||
ethdb.KeyValueStore
|
||||
ethdb.AncientStore
|
||||
quitChan chan struct{}
|
||||
wg sync.WaitGroup
|
||||
}
|
||||
|
||||
// Close implements io.Closer, closing both the fast key-value store as well as
|
||||
// the slow ancient tables.
|
||||
func (frdb *freezerdb) Close() error {
|
||||
close(frdb.quitChan)
|
||||
var errs []error
|
||||
if err := frdb.KeyValueStore.Close(); err != nil {
|
||||
errs = append(errs, err)
|
||||
|
|
@ -171,13 +176,22 @@ func NewDatabaseWithFreezer(db ethdb.KeyValueStore, freezer string, namespace st
|
|||
// feezer.
|
||||
}
|
||||
}
|
||||
// Freezer is consistent with the key-value database, permit combining the two
|
||||
go frdb.freeze(db)
|
||||
|
||||
return &freezerdb{
|
||||
fdb := &freezerdb{
|
||||
KeyValueStore: db,
|
||||
AncientStore: frdb,
|
||||
}, nil
|
||||
//AncientStore: frdb,
|
||||
quitChan: make(chan struct{}),
|
||||
}
|
||||
// Freezer is consistent with the key-value database, permit combining the two
|
||||
fdb.wg.Add(1)
|
||||
go func() {
|
||||
defer fdb.wg.Done()
|
||||
frdb.freeze(db, fdb.quitChan)
|
||||
}()
|
||||
|
||||
fdb.AncientStore = frdb
|
||||
|
||||
return fdb, nil
|
||||
}
|
||||
|
||||
// NewMemoryDatabase creates an ephemeral in-memory key-value database without a
|
||||
|
|
|
|||
|
|
@ -251,38 +251,44 @@ func (f *freezer) Sync() error {
|
|||
//
|
||||
// This functionality is deliberately broken off from block importing to avoid
|
||||
// incurring additional data shuffling delays on block propagation.
|
||||
func (f *freezer) freeze(db ethdb.KeyValueStore) {
|
||||
func (f *freezer) freeze(db ethdb.KeyValueStore, quitChan chan struct{}) {
|
||||
nfdb := &nofreezedb{KeyValueStore: db}
|
||||
|
||||
timer := time.NewTimer(freezerRecheckInterval)
|
||||
defer timer.Stop()
|
||||
for {
|
||||
select {
|
||||
case <-quitChan:
|
||||
log.Info("Database freezer quit")
|
||||
return
|
||||
case <-timer.C:
|
||||
// Retrieve the freezing threshold.
|
||||
hash := ReadHeadBlockHash(nfdb)
|
||||
if hash == (common.Hash{}) {
|
||||
log.Debug("Current full block hash unavailable") // new chain, empty database
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
continue
|
||||
}
|
||||
number := ReadHeaderNumber(nfdb, hash)
|
||||
switch {
|
||||
case number == nil:
|
||||
log.Error("Current full block number unavailable", "hash", hash)
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
continue
|
||||
|
||||
case *number < params.ImmutabilityThreshold:
|
||||
log.Debug("Current full block not old enough", "number", *number, "hash", hash, "delay", params.ImmutabilityThreshold)
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
continue
|
||||
|
||||
case *number-params.ImmutabilityThreshold <= f.frozen:
|
||||
log.Debug("Ancient blocks frozen already", "number", *number, "hash", hash, "frozen", f.frozen)
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
continue
|
||||
}
|
||||
head := ReadHeader(nfdb, hash, *number)
|
||||
if head == nil {
|
||||
log.Error("Current full block unavailable", "number", *number, "hash", hash)
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
continue
|
||||
}
|
||||
// Seems we have data ready to be frozen, process in usable batches
|
||||
|
|
@ -369,7 +375,10 @@ func (f *freezer) freeze(db ethdb.KeyValueStore) {
|
|||
|
||||
// Avoid database thrashing with tiny writes
|
||||
if f.frozen-first < freezerBatchLimit {
|
||||
time.Sleep(freezerRecheckInterval)
|
||||
timer.Reset(freezerRecheckInterval)
|
||||
} else {
|
||||
timer.Reset(0)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue