|
|
|
@ -35,6 +35,7 @@ import ( |
|
|
|
|
"github.com/ethereum/go-ethereum/core/state/snapshot" |
|
|
|
|
"github.com/ethereum/go-ethereum/core/types" |
|
|
|
|
"github.com/ethereum/go-ethereum/crypto" |
|
|
|
|
"github.com/ethereum/go-ethereum/rlp" |
|
|
|
|
"github.com/ethereum/go-ethereum/trie" |
|
|
|
|
"github.com/ethereum/go-ethereum/trie/triedb/hashdb" |
|
|
|
|
"github.com/ethereum/go-ethereum/trie/triedb/pathdb" |
|
|
|
@ -447,6 +448,43 @@ func (test *snapshotTest) run() bool { |
|
|
|
|
return true |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func forEachStorage(s *StateDB, addr common.Address, cb func(key, value common.Hash) bool) error { |
|
|
|
|
so := s.getStateObject(addr) |
|
|
|
|
if so == nil { |
|
|
|
|
return nil |
|
|
|
|
} |
|
|
|
|
tr, err := so.getTrie() |
|
|
|
|
if err != nil { |
|
|
|
|
return err |
|
|
|
|
} |
|
|
|
|
trieIt, err := tr.NodeIterator(nil) |
|
|
|
|
if err != nil { |
|
|
|
|
return err |
|
|
|
|
} |
|
|
|
|
it := trie.NewIterator(trieIt) |
|
|
|
|
|
|
|
|
|
for it.Next() { |
|
|
|
|
key := common.BytesToHash(s.trie.GetKey(it.Key)) |
|
|
|
|
if value, dirty := so.dirtyStorage[key]; dirty { |
|
|
|
|
if !cb(key, value) { |
|
|
|
|
return nil |
|
|
|
|
} |
|
|
|
|
continue |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if len(it.Value) > 0 { |
|
|
|
|
_, content, _, err := rlp.Split(it.Value) |
|
|
|
|
if err != nil { |
|
|
|
|
return err |
|
|
|
|
} |
|
|
|
|
if !cb(key, common.BytesToHash(content)) { |
|
|
|
|
return nil |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
return nil |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// checkEqual checks that methods of state and checkstate return the same values.
|
|
|
|
|
func (test *snapshotTest) checkEqual(state, checkstate *StateDB) error { |
|
|
|
|
for _, addr := range test.addrs { |
|
|
|
@ -468,10 +506,10 @@ func (test *snapshotTest) checkEqual(state, checkstate *StateDB) error { |
|
|
|
|
checkeq("GetCodeSize", state.GetCodeSize(addr), checkstate.GetCodeSize(addr)) |
|
|
|
|
// Check storage.
|
|
|
|
|
if obj := state.getStateObject(addr); obj != nil { |
|
|
|
|
state.ForEachStorage(addr, func(key, value common.Hash) bool { |
|
|
|
|
forEachStorage(state, addr, func(key, value common.Hash) bool { |
|
|
|
|
return checkeq("GetState("+key.Hex()+")", checkstate.GetState(addr, key), value) |
|
|
|
|
}) |
|
|
|
|
checkstate.ForEachStorage(addr, func(key, value common.Hash) bool { |
|
|
|
|
forEachStorage(checkstate, addr, func(key, value common.Hash) bool { |
|
|
|
|
return checkeq("GetState("+key.Hex()+")", checkstate.GetState(addr, key), value) |
|
|
|
|
}) |
|
|
|
|
} |
|
|
|
|