Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion accounts/abi/bind/bind_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2098,7 +2098,10 @@ func TestGolangBindings(t *testing.T) {
t.Fatalf("failed to convert binding test to modules: %v\n%s", err, out)
}
pwd, _ := os.Getwd()
replacer := exec.Command(gocmd, "mod", "edit", "-x", "-require", "github.com/ethereum/[email protected]", "-replace", "github.com/ethereum/go-ethereum="+filepath.Join(pwd, "..", "..", "..")) // Repo root
replacer := exec.Command(gocmd, "mod", "edit", "-x", "-require", "github.com/ethereum/[email protected]",
"-replace", "github.com/ethereum/go-ethereum="+filepath.Join(pwd, "..", "..", ".."), // Repo root
"-replace", "github.com/cockroachdb/pebble=github.com/jwasinger/[email protected]",
)
replacer.Dir = pkg
if out, err := replacer.CombinedOutput(); err != nil {
t.Fatalf("failed to replace binding test dependency to current source tree: %v\n%s", err, out)
Expand Down
14 changes: 14 additions & 0 deletions cmd/utils/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,11 @@ var (
Usage: "URL for remote database",
Category: flags.LoggingCategory,
}
BackingDBFlag = &cli.StringFlag{
Name: "backingdb",
Usage: "Backing database implementation to use",
Value: ethconfig.Defaults.BackingDB,
}
AncientFlag = &flags.DirectoryFlag{
Name: "datadir.ancient",
Usage: "Root directory for ancient data (default = inside chaindata)",
Expand Down Expand Up @@ -997,6 +1002,7 @@ var (
DataDirFlag,
AncientFlag,
RemoteDBFlag,
BackingDBFlag,
}
)

Expand Down Expand Up @@ -1488,6 +1494,14 @@ func SetNodeConfig(ctx *cli.Context, cfg *node.Config) {
if ctx.IsSet(InsecureUnlockAllowedFlag.Name) {
cfg.InsecureUnlockAllowed = ctx.Bool(InsecureUnlockAllowedFlag.Name)
}
if ctx.IsSet(BackingDBFlag.Name) {
backingDB := ctx.String(BackingDBFlag.Name)
if backingDB != "leveldb" && backingDB != "pebble" {
Fatalf("invalid choice for backing db: %s", backingDB)
}
log.Info(fmt.Sprintf("using %s as backing db", backingDB))
cfg.BackingDB = backingDB
}
}

func setSmartCard(ctx *cli.Context, cfg *node.Config) {
Expand Down
79 changes: 79 additions & 0 deletions core/rawdb/database.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,15 @@ import (
"fmt"
"os"
"path"
"path/filepath"
"sync/atomic"
"time"

"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/ethdb/leveldb"
"github.com/ethereum/go-ethereum/ethdb/memorydb"
"github.com/ethereum/go-ethereum/ethdb/pebble"
"github.com/ethereum/go-ethereum/log"
"github.com/olekukonko/tablewriter"
)
Expand Down Expand Up @@ -301,9 +303,71 @@ func NewLevelDBDatabase(file string, cache int, handles int, namespace string, r
if err != nil {
return nil, err
}
log.Info("using LevelDB as the backing database")
return NewDatabase(db), nil
}

// NewPebbleDBDatabase creates a persistent key-value database without a freezer
// moving immutable chain segments into cold storage.
func NewPebbleDBDatabase(file string, cache int, handles int, namespace string, readonly bool) (ethdb.Database, error) {
db, err := pebble.New(file, cache, handles, namespace, readonly)
if err != nil {
return nil, err
}
log.Info("using Pebble as the backing database")
return NewDatabase(db), nil
}

type dbType int

const (
Nonexistent dbType = iota
Pebble
LevelDb
)

func hasPreexistingDb(path string) dbType {
_, err := os.Stat(path + "/CURRENT")
if err != nil {
return Nonexistent
}
if matches, err := filepath.Glob(path + "/OPTIONS*"); len(matches) > 0 || err != nil {
if err != nil {
panic(err) // only possible if the pattern is malformed
}
return Pebble
}
return LevelDb
}

func NewPebbleOrLevelDBDatabase(backingdb string, file string, cache int, handles int, namespace string, readonly bool) (ethdb.Database, error) {
preexistingDb := hasPreexistingDb(file)

if backingdb == "pebble" && preexistingDb == LevelDb {
return nil, errors.New("backingdb choice was pebble but found pre-existing leveldb database in specified data directory")
}
if backingdb == "leveldb" && preexistingDb == Pebble {
return nil, errors.New("backingdb choice was leveldb but found pre-existing pebble database in specified data directory")
}
if backingdb == "pebble" || preexistingDb == Pebble {
return NewPebbleDBDatabase(file, cache, handles, namespace, readonly)
}
return NewLevelDBDatabase(file, cache, handles, namespace, readonly)
}

func NewPebbleOrLevelDBDatabaseWithFreezer(backingdb string, file string, cache int, handles int, ancient string, namespace string, readonly bool) (ethdb.Database, error) {
kvdb, err := NewPebbleOrLevelDBDatabase(backingdb, file, cache, handles, namespace, readonly)
if err != nil {
return nil, err
}
frdb, err := NewDatabaseWithFreezer(kvdb, ancient, namespace, readonly)
if err != nil {
kvdb.Close()
return nil, err
}
return frdb, nil
}

// NewLevelDBDatabaseWithFreezer creates a persistent key-value database with a
// freezer moving immutable chain segments into cold storage. The passed ancient
// indicates the path of root ancient directory where the chain freezer can be
Expand All @@ -321,6 +385,21 @@ func NewLevelDBDatabaseWithFreezer(file string, cache int, handles int, ancient
return frdb, nil
}

// NewPebbleDBDatabaseWithFreezer creates a persistent key-value database with a
// freezer moving immutable chain segments into cold storage.
func NewPebbleDBDatabaseWithFreezer(file string, cache int, handles int, ancient string, namespace string, readonly bool) (ethdb.Database, error) {
kvdb, err := pebble.New(file, cache, handles, namespace, readonly)
if err != nil {
return nil, err
}
frdb, err := NewDatabaseWithFreezer(kvdb, ancient, namespace, readonly)
if err != nil {
kvdb.Close()
return nil, err
}
return frdb, nil
}

type counter uint64

func (c counter) String() string {
Expand Down
2 changes: 2 additions & 0 deletions eth/ethconfig/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,7 @@ var Defaults = Config{
RPCEVMTimeout: 5 * time.Second,
GPO: FullNodeGPO,
RPCTxFeeCap: 1, // 1 ether
BackingDB: "default",
}

func init() {
Expand Down Expand Up @@ -163,6 +164,7 @@ type Config struct {
DatabaseHandles int `toml:"-"`
DatabaseCache int
DatabaseFreezer string
BackingDB string `toml:",omitempty"`

TrieCleanCache int
TrieCleanCacheJournal string `toml:",omitempty"` // Disk journal directory for trie cache to survive node restarts
Expand Down
27 changes: 15 additions & 12 deletions ethdb/leveldb/leveldb.go
Original file line number Diff line number Diff line change
Expand Up @@ -63,18 +63,19 @@ type Database struct {
fn string // filename for reporting
db *leveldb.DB // LevelDB instance

compTimeMeter metrics.Meter // Meter for measuring the total time spent in database compaction
compReadMeter metrics.Meter // Meter for measuring the data read during compaction
compWriteMeter metrics.Meter // Meter for measuring the data written during compaction
writeDelayNMeter metrics.Meter // Meter for measuring the write delay number due to database compaction
writeDelayMeter metrics.Meter // Meter for measuring the write delay duration due to database compaction
diskSizeGauge metrics.Gauge // Gauge for tracking the size of all the levels in the database
diskReadMeter metrics.Meter // Meter for measuring the effective amount of data read
diskWriteMeter metrics.Meter // Meter for measuring the effective amount of data written
memCompGauge metrics.Gauge // Gauge for tracking the number of memory compaction
level0CompGauge metrics.Gauge // Gauge for tracking the number of table compaction in level0
nonlevel0CompGauge metrics.Gauge // Gauge for tracking the number of table compaction in non0 level
seekCompGauge metrics.Gauge // Gauge for tracking the number of table compaction caused by read opt
compTimeMeter metrics.Meter // Meter for measuring the total time spent in database compaction
compReadMeter metrics.Meter // Meter for measuring the data read during compaction
compWriteMeter metrics.Meter // Meter for measuring the data written during compaction
writeDelayNMeter metrics.Meter // Meter for measuring the write delay number due to database compaction
writeDelayMeter metrics.Meter // Meter for measuring the write delay duration due to database compaction
diskSizeGauge metrics.Gauge // Gauge for tracking the size of all the levels in the database
diskReadMeter metrics.Meter // Meter for measuring the effective amount of data read
diskWriteMeter metrics.Meter // Meter for measuring the effective amount of data written
memCompGauge metrics.Gauge // Gauge for tracking the number of memory compaction
level0CompGauge metrics.Gauge // Gauge for tracking the number of table compaction in level0
nonlevel0CompGauge metrics.Gauge // Gauge for tracking the number of table compaction in non0 level
seekCompGauge metrics.Gauge // Gauge for tracking the number of table compaction caused by read opt
manualMemAllocGauge metrics.Gauge // Gauge to track the amount of memory that has been manually allocated (not a part of runtime/GC)

quitLock sync.Mutex // Mutex protecting the quit channel access
quitChan chan chan error // Quit channel to stop the metrics collection before closing the database
Expand Down Expand Up @@ -144,6 +145,8 @@ func NewCustom(file string, namespace string, customize func(options *opt.Option
ldb.nonlevel0CompGauge = metrics.NewRegisteredGauge(namespace+"compact/nonlevel0", nil)
ldb.seekCompGauge = metrics.NewRegisteredGauge(namespace+"compact/seek", nil)

ldb.manualMemAllocGauge = metrics.NewRegisteredGauge(namespace+"memory/manualalloc", nil)

// Start up the metrics gathering and return
go ldb.meter(metricsGatheringInterval)
return ldb, nil
Expand Down
Loading