Skip to content

Commit

Permalink
System contract upgrade fix and RPC refine (#146)
Browse files Browse the repository at this point in the history
* e2: avoid do RestoreCodeHash twice (erigontech#7706)

- do it only once in HistoryStateReader

* fix system contract upgrade

* update

---------

Co-authored-by: Alex Sharov <AskAlexSharov@gmail.com>
  • Loading branch information
calmbeing and AskAlexSharov authored Jun 27, 2023
1 parent 5d2d172 commit 30da7a2
Show file tree
Hide file tree
Showing 4 changed files with 47 additions and 35 deletions.
2 changes: 1 addition & 1 deletion core/state/history_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,7 @@ func TestMutationCommit(t *testing.T) {
for k, v := range accHistoryStateStorage[i] {
c1, _ := tx.Cursor(kv.StorageHistory)
c2, _ := tx.CursorDupSort(kv.StorageChangeSet)
res, err := historyv2read.GetAsOf(tx, c1, c2, true /* storage */, dbutils.PlainGenerateCompositeStorageKey(addr.Bytes(), acc.Incarnation, k.Bytes()), 1)
res, _, err := historyv2read.GetAsOf(tx, c1, c2, true /* storage */, dbutils.PlainGenerateCompositeStorageKey(addr.Bytes(), acc.Incarnation, k.Bytes()), 1)
if err != nil {
t.Fatal(err)
}
Expand Down
18 changes: 5 additions & 13 deletions core/state/historyv2read/history.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,22 +40,14 @@ func RestoreCodeHash(tx kv.Getter, key, v []byte, force *libcommon.Hash) ([]byte
return v, nil
}

func GetAsOf(tx kv.Tx, indexC kv.Cursor, changesC kv.CursorDupSort, storage bool, key []byte, timestamp uint64) ([]byte, error) {
func GetAsOf(tx kv.Tx, indexC kv.Cursor, changesC kv.CursorDupSort, storage bool, key []byte, timestamp uint64) (v []byte, fromHistory bool, err error) {
v, ok, err := historyv2.FindByHistory(indexC, changesC, storage, key, timestamp)
if err != nil {
return nil, err
return nil, true, err
}
if ok {
//restore codehash
if !storage {
//restore codehash
v, err = RestoreCodeHash(tx, key, v, nil)
if err != nil {
return nil, err
}
}

return v, nil
return v, true, nil
}
return tx.GetOne(kv.PlainState, key)
v, err = tx.GetOne(kv.PlainState, key)
return v, false, err
}
44 changes: 23 additions & 21 deletions core/state/plain_readonly.go
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ func (s *PlainState) ForEachStorage(addr libcommon.Address, startLocation libcom
st := btree.New(16)
var k [length.Addr + length.Incarnation + length.Hash]byte
copy(k[:], addr[:])
accData, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, addr[:], s.blockNr)
accData, _, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, addr[:], s.blockNr)
if err != nil {
return err
}
Expand Down Expand Up @@ -170,7 +170,7 @@ func (s *PlainState) ForEachStorage(addr libcommon.Address, startLocation libcom
}

func (s *PlainState) ReadAccountData(address libcommon.Address) (*accounts.Account, error) {
enc, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, address[:], s.blockNr)
enc, fromHistory, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, address[:], s.blockNr)
if err != nil {
return nil, err
}
Expand All @@ -184,19 +184,21 @@ func (s *PlainState) ReadAccountData(address libcommon.Address) (*accounts.Accou
if err = a.DecodeForStorage(enc); err != nil {
return nil, err
}
//restore codehash
if records, ok := s.systemContractLookup[address]; ok {
p := sort.Search(len(records), func(i int) bool {
return records[i].BlockNumber > s.blockNr
})
a.CodeHash = records[p-1].CodeHash
} else if a.Incarnation > 0 && a.IsEmptyCodeHash() {
if codeHash, err1 := s.tx.GetOne(kv.PlainContractCode, dbutils.PlainGenerateStoragePrefix(address[:], a.Incarnation)); err1 == nil {
if len(codeHash) > 0 {
a.CodeHash = libcommon.BytesToHash(codeHash)
if fromHistory {
//restore codehash
if records, ok := s.systemContractLookup[address]; ok {
p := sort.Search(len(records), func(i int) bool {
return records[i].BlockNumber > s.blockNr
})
a.CodeHash = records[p-1].CodeHash
} else if a.Incarnation > 0 && a.IsEmptyCodeHash() {
if codeHash, err1 := s.tx.GetOne(kv.PlainContractCode, dbutils.PlainGenerateStoragePrefix(address[:], a.Incarnation)); err1 == nil {
if len(codeHash) > 0 {
a.CodeHash = libcommon.BytesToHash(codeHash)
}
} else {
return nil, err1
}
} else {
return nil, err1
}
}
if s.trace {
Expand All @@ -207,7 +209,7 @@ func (s *PlainState) ReadAccountData(address libcommon.Address) (*accounts.Accou

func (s *PlainState) ReadAccountStorage(address libcommon.Address, incarnation uint64, key *libcommon.Hash) ([]byte, error) {
compositeKey := dbutils.PlainGenerateCompositeStorageKey(address.Bytes(), incarnation, key.Bytes())
enc, err := historyv2read.GetAsOf(s.tx, s.storageHistoryC, s.storageChangesC, true /* storage */, compositeKey, s.blockNr)
enc, _, err := historyv2read.GetAsOf(s.tx, s.storageHistoryC, s.storageChangesC, true /* storage */, compositeKey, s.blockNr)
if err != nil {
return nil, err
}
Expand Down Expand Up @@ -243,7 +245,7 @@ func (s *PlainState) ReadAccountCodeSize(address libcommon.Address, incarnation
}

func (s *PlainState) ReadAccountIncarnation(address libcommon.Address) (uint64, error) {
enc, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, address[:], s.blockNr+1)
enc, _, err := historyv2read.GetAsOf(s.tx, s.accHistoryC, s.accChangesC, false /* storage */, address[:], s.blockNr+1)
if err != nil {
return 0, err
}
Expand All @@ -253,20 +255,20 @@ func (s *PlainState) ReadAccountIncarnation(address libcommon.Address) (uint64,
}
return 0, nil
}
var acc accounts.Account
if err = acc.DecodeForStorage(enc); err != nil {
inc, err := accounts.DecodeIncarnationFromStorage(enc)
if err != nil {
return 0, err
}
if acc.Incarnation == 0 {
if inc == 0 {
if s.trace {
fmt.Printf("ReadAccountIncarnation [%x] => [%d]\n", address, 0)
}
return 0, nil
}
if s.trace {
fmt.Printf("ReadAccountIncarnation [%x] => [%d]\n", address, acc.Incarnation-1)
fmt.Printf("ReadAccountIncarnation [%x] => [%d]\n", address, inc-1)
}
return acc.Incarnation - 1, nil
return inc - 1, nil
}

func (s *PlainState) UpdateAccountData(address libcommon.Address, original, account *accounts.Account) error {
Expand Down
18 changes: 18 additions & 0 deletions core/system_contract_lookup.go
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,24 @@ func init() {
addCodeRecords(systemcontracts.GibbsUpgrade[chainName], blockNum, byChain)
}
}
if chainConfig.PlanckBlock != nil {
blockNum := chainConfig.PlanckBlock.Uint64()
if blockNum != 0 {
addCodeRecords(systemcontracts.PlanckUpgrade[chainName], blockNum, byChain)
}
}
if chainConfig.LubanBlock != nil {
blockNum := chainConfig.LubanBlock.Uint64()
if blockNum != 0 {
addCodeRecords(systemcontracts.LubanUpgrade[chainName], blockNum, byChain)
}
}
if chainConfig.PlatoBlock != nil {
blockNum := chainConfig.PlatoBlock.Uint64()
if blockNum != 0 {
addCodeRecords(systemcontracts.PlatoUpgrade[chainName], blockNum, byChain)
}
}
if chainConfig.Bor != nil && chainConfig.Bor.CalcuttaBlock != nil {
blockNum := chainConfig.Bor.CalcuttaBlock.Uint64()
if blockNum != 0 {
Expand Down

0 comments on commit 30da7a2

Please sign in to comment.