Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/main' into sdk_47
Browse files Browse the repository at this point in the history
  • Loading branch information
mmsqe committed Sep 6, 2023
2 parents 6ab6c59 + c575f47 commit ebf1161
Show file tree
Hide file tree
Showing 18 changed files with 415 additions and 127 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
- [#1123](https://github.com/crypto-org-chain/cronos/pull/1123) Fix memiavl snapshot switching
- [#1125](https://github.com/crypto-org-chain/cronos/pull/1125) Fix genesis migrate for feeibc, evm, feemarket and gravity.
- [#1130](https://github.com/crypto-org-chain/cronos/pull/1130) Fix lock issues when state-sync with memiavl.
- [#1150](https://github.com/crypto-org-chain/cronos/pull/1150) Fix memiavl's unsafe retain of the root hashes.

### Features

Expand Down Expand Up @@ -69,6 +70,8 @@
- [#1092](https://github.com/crypto-org-chain/cronos/pull/1092) memiavl disable sdk address cache if zero-copy enabled, and disable zero-copy by default.
- [#1099](https://github.com/crypto-org-chain/cronos/pull/1099) clean up memiavl tmp directories left behind.
- [#940](https://github.com/crypto-org-chain/cronos/pull/940) Update rocksdb dependency to 8.1.1.
- [#1149](https://github.com/crypto-org-chain/cronos/pull/1149) memiavl support `WorkingHash` api required by `FinalizeBlock`.
- [#1151](https://github.com/crypto-org-chain/cronos/pull/1151) memiavl `CacheMultiStoreWithVersion` supports `io.Closer`.

*April 13, 2023*

Expand Down
3 changes: 1 addition & 2 deletions cmd/cronosd/cmd/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ import (
tmcfg "github.com/cometbft/cometbft/config"
tmcli "github.com/cometbft/cometbft/libs/cli"
"github.com/cometbft/cometbft/libs/log"
tmlog "github.com/cometbft/cometbft/libs/log"
"github.com/spf13/cast"
"github.com/spf13/cobra"
"github.com/spf13/pflag"
Expand Down Expand Up @@ -284,7 +283,7 @@ func (a appCreator) newApp(logger log.Logger, db dbm.DB, traceStore io.Writer, a

// appExport creates a new simapp (optionally at a given height)
func (a appCreator) appExport(
logger tmlog.Logger,
logger log.Logger,
db dbm.DB,
traceStore io.Writer,
height int64,
Expand Down
4 changes: 2 additions & 2 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ require (
github.com/cosmos/cosmos-sdk v0.47.3
github.com/cosmos/gogoproto v1.4.10
github.com/cosmos/ibc-go/v7 v7.2.0
github.com/crypto-org-chain/cronos/store v0.0.2
github.com/crypto-org-chain/cronos/store v0.0.4
github.com/crypto-org-chain/cronos/versiondb v0.0.0-00010101000000-000000000000
github.com/ethereum/go-ethereum v1.10.26
github.com/evmos/ethermint v0.0.0-00010101000000-000000000000
Expand Down Expand Up @@ -81,7 +81,7 @@ require (
github.com/cosmos/ledger-cosmos-go v0.12.2 // indirect
github.com/cosmos/rosetta-sdk-go v0.10.0 // indirect
github.com/creachadair/taskgroup v0.4.2 // indirect
github.com/crypto-org-chain/cronos/memiavl v0.0.3 // indirect
github.com/crypto-org-chain/cronos/memiavl v0.0.4 // indirect
github.com/danieljoos/wincred v1.1.2 // indirect
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/deckarep/golang-set v1.8.0 // indirect
Expand Down
136 changes: 100 additions & 36 deletions memiavl/db.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,15 @@ import (
"fmt"
"os"
"path/filepath"
"sort"
"strconv"
"strings"
"sync"
"time"

"github.com/cometbft/cometbft/libs/log"
storetypes "github.com/cosmos/cosmos-sdk/store/types"
"github.com/cosmos/iavl"
"github.com/tidwall/wal"
)

Expand Down Expand Up @@ -63,8 +65,8 @@ type DB struct {
walChan chan *walEntry
walQuit chan error

// pending store upgrades, will be written into WAL in next Commit call
pendingUpgrades []*TreeNameUpgrade
// pending changes, will be written into WAL in next Commit call
pendingLog WALEntry

// The assumptions to concurrency:
// - The methods on DB are protected by a mutex
Expand Down Expand Up @@ -281,19 +283,23 @@ func (db *DB) SetInitialVersion(initialVersion int64) error {
db.mtx.Lock()
defer db.mtx.Unlock()

if err := db.MultiTree.SetInitialVersion(initialVersion); err != nil {
return err
if db.readOnly {
return errReadOnly
}

if err := initEmptyDB(db.dir, db.initialVersion); err != nil {
if db.lastCommitInfo.Version > 0 {
return errors.New("initial version can only be set before any commit")
}

if err := db.MultiTree.SetInitialVersion(initialVersion); err != nil {
return err
}

return db.reload()
return initEmptyDB(db.dir, db.initialVersion)
}

// ApplyUpgrades wraps MultiTree.ApplyUpgrades, it also append the upgrades in a temporary field,
// and include in the WAL entry in next Commit call.
// ApplyUpgrades wraps MultiTree.ApplyUpgrades, it also append the upgrades in a pending log,
// which will be persisted to the WAL in next Commit call.
func (db *DB) ApplyUpgrades(upgrades []*TreeNameUpgrade) error {
db.mtx.Lock()
defer db.mtx.Unlock()
Expand All @@ -306,10 +312,63 @@ func (db *DB) ApplyUpgrades(upgrades []*TreeNameUpgrade) error {
return err
}

db.pendingUpgrades = append(db.pendingUpgrades, upgrades...)
db.pendingLog.Upgrades = append(db.pendingLog.Upgrades, upgrades...)
return nil
}

// ApplyChangeSets wraps MultiTree.ApplyChangeSets, it also append the changesets in the pending log,
// which will be persisted to the WAL in next Commit call.
func (db *DB) ApplyChangeSets(changeSets []*NamedChangeSet) error {
if len(changeSets) == 0 {
return nil
}

db.mtx.Lock()
defer db.mtx.Unlock()

if db.readOnly {
return errReadOnly
}

if len(db.pendingLog.Changesets) > 0 {
return errors.New("don't support multiple ApplyChangeSets calls in the same version")
}
db.pendingLog.Changesets = changeSets

return db.MultiTree.ApplyChangeSets(changeSets)
}

// ApplyChangeSet wraps MultiTree.ApplyChangeSet, it also append the changesets in the pending log,
// which will be persisted to the WAL in next Commit call.
func (db *DB) ApplyChangeSet(name string, changeSet iavl.ChangeSet) error {
if len(changeSet.Pairs) == 0 {
return nil
}

db.mtx.Lock()
defer db.mtx.Unlock()

if db.readOnly {
return errReadOnly
}

for _, cs := range db.pendingLog.Changesets {
if cs.Name == name {
return errors.New("don't support multiple ApplyChangeSet calls with the same name in the same version")
}
}

db.pendingLog.Changesets = append(db.pendingLog.Changesets, &NamedChangeSet{
Name: name,
Changeset: changeSet,
})
sort.SliceStable(db.pendingLog.Changesets, func(i, j int) bool {
return db.pendingLog.Changesets[i].Name < db.pendingLog.Changesets[j].Name
})

return db.MultiTree.ApplyChangeSet(name, changeSet)
}

// checkAsyncTasks checks the status of background tasks non-blocking-ly and process the result
func (db *DB) checkAsyncTasks() error {
return errors.Join(
Expand Down Expand Up @@ -441,32 +500,23 @@ func (db *DB) pruneSnapshots() {
}()
}

// Commit wraps `MultiTree.ApplyChangeSet` to add some db level operations:
// - manage background snapshot rewriting
// - write WAL
func (db *DB) Commit(changeSets []*NamedChangeSet) ([]byte, int64, error) {
// Commit wraps SaveVersion to bump the version and writes the pending changes into log files to persist on disk
func (db *DB) Commit() ([]byte, int64, error) {
db.mtx.Lock()
defer db.mtx.Unlock()

if db.readOnly {
return nil, 0, errReadOnly
}

if err := db.checkAsyncTasks(); err != nil {
return nil, 0, err
}

hash, v, err := db.MultiTree.ApplyChangeSet(changeSets, true)
hash, v, err := db.MultiTree.SaveVersion(true)
if err != nil {
return nil, 0, err
}

// write logs if enabled
if db.wal != nil {
// write write-ahead-log
entry := walEntry{index: walIndex(v, db.initialVersion), data: &WALEntry{
Changesets: changeSets,
Upgrades: db.pendingUpgrades,
}}
entry := walEntry{index: walIndex(v, db.initialVersion), data: db.pendingLog}
if db.walChanSize >= 0 {
if db.walChan == nil {
db.initAsyncCommit()
Expand All @@ -485,8 +535,11 @@ func (db *DB) Commit(changeSets []*NamedChangeSet) ([]byte, int64, error) {
}
}

db.pendingUpgrades = db.pendingUpgrades[:0]
db.pendingLog = WALEntry{}

if err := db.checkAsyncTasks(); err != nil {
return nil, 0, err
}
db.rewriteIfApplicable(v)

return hash, v, nil
Expand Down Expand Up @@ -607,14 +660,8 @@ func (db *DB) reloadMultiTree(mtree *MultiTree) error {
}

db.MultiTree = *mtree

if len(db.pendingUpgrades) > 0 {
if err := db.MultiTree.ApplyUpgrades(db.pendingUpgrades); err != nil {
return err
}
}

return nil
// catch-up the pending changes
return db.MultiTree.applyWALEntry(db.pendingLog)
}

// rewriteIfApplicable execute the snapshot rewrite strategy according to current height
Expand Down Expand Up @@ -734,23 +781,40 @@ func (db *DB) LastCommitInfo() *storetypes.CommitInfo {
return db.MultiTree.LastCommitInfo()
}

// ApplyChangeSet wraps MultiTree.ApplyChangeSet to add a lock.
func (db *DB) ApplyChangeSet(changeSets []*NamedChangeSet, updateCommitInfo bool) ([]byte, int64, error) {
func (db *DB) SaveVersion(updateCommitInfo bool) ([]byte, int64, error) {
db.mtx.Lock()
defer db.mtx.Unlock()

if db.readOnly {
return nil, 0, errReadOnly
}

return db.MultiTree.ApplyChangeSet(changeSets, updateCommitInfo)
return db.MultiTree.SaveVersion(updateCommitInfo)
}

func (db *DB) WorkingCommitInfo() *storetypes.CommitInfo {
db.mtx.Lock()
defer db.mtx.Unlock()

return db.MultiTree.WorkingCommitInfo()
}

func (db *DB) WorkingHash() []byte {
db.mtx.Lock()
defer db.mtx.Unlock()

return db.MultiTree.WorkingHash()
}

// UpdateCommitInfo wraps MultiTree.UpdateCommitInfo to add a lock.
func (db *DB) UpdateCommitInfo() []byte {
db.mtx.Lock()
defer db.mtx.Unlock()

if db.readOnly {
panic("can't update commit info in read-only mode")
}

return db.MultiTree.UpdateCommitInfo()
}

Expand Down Expand Up @@ -936,7 +1000,7 @@ func createDBIfNotExist(dir string, initialVersion uint32) error {

type walEntry struct {
index uint64
data *WALEntry
data WALEntry
}

func isSnapshotName(name string) bool {
Expand Down
Loading

0 comments on commit ebf1161

Please sign in to comment.