mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-05-09 01:26:36 +00:00
attempt to align behavior with other clients (spec tests currently incorrect)
This commit is contained in:
parent
00136d1735
commit
abaef48d54
5 changed files with 82 additions and 55 deletions
|
|
@ -125,6 +125,12 @@ func (e *BlockAccessList) Hash() common.Hash {
|
||||||
// under reasonable conditions.
|
// under reasonable conditions.
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
/*
|
||||||
|
bal, err := json.MarshalIndent(e.StringableRepresentation(), "", " ")
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
*/
|
||||||
return crypto.Keccak256Hash(enc.Bytes())
|
return crypto.Keccak256Hash(enc.Bytes())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -142,29 +148,32 @@ type encodingAccountNonce struct {
|
||||||
|
|
||||||
// encodingStorageWrite is the encoding format of StorageWrites.
|
// encodingStorageWrite is the encoding format of StorageWrites.
|
||||||
type encodingStorageWrite struct {
|
type encodingStorageWrite struct {
|
||||||
TxIdx uint16 `json:"txIndex"`
|
TxIdx uint16 `json:"txIndex"`
|
||||||
ValueAfter encodedStorage `json:"valueAfter"`
|
ValueAfter *EncodedStorage `json:"valueAfter"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// encodedStorage can represent either a storage key or value
|
// EncodedStorage can represent either a storage key or value
|
||||||
type encodedStorage []byte
|
type EncodedStorage struct {
|
||||||
|
inner *uint256.Int
|
||||||
|
}
|
||||||
|
|
||||||
func (e *encodedStorage) ToHash() common.Hash {
|
var _ rlp.Encoder = &EncodedStorage{}
|
||||||
|
var _ rlp.Decoder = &EncodedStorage{}
|
||||||
|
|
||||||
|
func (e *EncodedStorage) ToHash() common.Hash {
|
||||||
if e == nil {
|
if e == nil {
|
||||||
return common.Hash{}
|
return common.Hash{}
|
||||||
}
|
}
|
||||||
return common.BytesToHash(*e)
|
return e.inner.Bytes32()
|
||||||
}
|
}
|
||||||
|
|
||||||
func newEncodedStorageFromHash(hash common.Hash) encodedStorage {
|
func newEncodedStorageFromHash(hash common.Hash) *EncodedStorage {
|
||||||
return bytes.TrimLeft(hash[:], "\x00")
|
return &EncodedStorage{
|
||||||
|
new(uint256.Int).SetBytes(hash[:]),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *encodedStorage) FromHash(hash common.Hash) {
|
func (s *EncodedStorage) UnmarshalJSON(b []byte) error {
|
||||||
*e = hash[:]
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *encodedStorage) UnmarshalJSON(b []byte) error {
|
|
||||||
var str string
|
var str string
|
||||||
if err := json.Unmarshal(b, &str); err != nil {
|
if err := json.Unmarshal(b, &str); err != nil {
|
||||||
return err
|
return err
|
||||||
|
|
@ -190,34 +199,31 @@ func (s *encodedStorage) UnmarshalJSON(b []byte) error {
|
||||||
|
|
||||||
// TODO: check is s == nil ?? should be programmer error
|
// TODO: check is s == nil ?? should be programmer error
|
||||||
|
|
||||||
*s = make([]byte, len(val)-1)
|
*s = EncodedStorage{
|
||||||
copy((*s)[:len(val)-1], val[:])
|
inner: new(uint256.Int).SetBytes(val),
|
||||||
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s encodedStorage) MarshalJSON() ([]byte, error) {
|
func (s EncodedStorage) MarshalJSON() ([]byte, error) {
|
||||||
trimmed := bytes.TrimLeft(s[:], "\x00")
|
return json.Marshal(s.inner.Hex())
|
||||||
return json.Marshal("0x" + common.Bytes2Hex(trimmed))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *encodedStorage) EncodeRLP(_w io.Writer) error {
|
func (s *EncodedStorage) EncodeRLP(_w io.Writer) error {
|
||||||
var obj encodedStorage
|
return s.inner.EncodeRLP(_w)
|
||||||
if s != nil {
|
}
|
||||||
obj = *s
|
|
||||||
|
func (s *EncodedStorage) DecodeRLP(dec *rlp.Stream) error {
|
||||||
|
if s == nil {
|
||||||
|
*s = EncodedStorage{}
|
||||||
}
|
}
|
||||||
trimmed := bytes.TrimLeft(obj[:], "\x00")
|
s.inner = uint256.NewInt(0)
|
||||||
fmt.Println("here")
|
return dec.ReadUint256(s.inner)
|
||||||
return rlp.Encode(_w, trimmed)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *encodedStorage) DecodeRLP(dec *rlp.Stream) error {
|
|
||||||
err := dec.ReadBytes((*s)[:])
|
|
||||||
return err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// encodingStorageWrite is the encoding format of SlotWrites.
|
// encodingStorageWrite is the encoding format of SlotWrites.
|
||||||
type encodingSlotWrites struct {
|
type encodingSlotWrites struct {
|
||||||
Slot encodedStorage `json:"slot"`
|
Slot *EncodedStorage `json:"slot"`
|
||||||
Accesses []encodingStorageWrite `json:"accesses"`
|
Accesses []encodingStorageWrite `json:"accesses"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -237,8 +243,8 @@ func (e *encodingSlotWrites) validate() error {
|
||||||
// AccountAccess is the encoding format of ConstructionAccountAccesses.
|
// AccountAccess is the encoding format of ConstructionAccountAccesses.
|
||||||
type AccountAccess struct {
|
type AccountAccess struct {
|
||||||
Address common.Address `json:"address,omitempty"` // 20-byte Ethereum address
|
Address common.Address `json:"address,omitempty"` // 20-byte Ethereum address
|
||||||
StorageChanges []encodingSlotWrites `json:"storageChanges,omitempty"` // encodedStorage changes (slot -> [tx_index -> new_value])
|
StorageChanges []encodingSlotWrites `json:"storageChanges,omitempty"` // EncodedStorage changes (slot -> [tx_index -> new_value])
|
||||||
StorageReads []encodedStorage `json:"storageReads,omitempty"` // Read-only storage keys
|
StorageReads []*EncodedStorage `json:"storageReads,omitempty"` // Read-only storage keys
|
||||||
BalanceChanges []encodingBalanceChange `json:"balanceChanges,omitempty"` // Balance changes ([tx_index -> post_balance])
|
BalanceChanges []encodingBalanceChange `json:"balanceChanges,omitempty"` // Balance changes ([tx_index -> post_balance])
|
||||||
NonceChanges []encodingAccountNonce `json:"nonceChanges,omitempty"` // Nonce changes ([tx_index -> new_nonce])
|
NonceChanges []encodingAccountNonce `json:"nonceChanges,omitempty"` // Nonce changes ([tx_index -> new_nonce])
|
||||||
CodeChanges []CodeChange `json:"code,omitempty"` // CodeChanges changes ([tx_index -> new_code])
|
CodeChanges []CodeChange `json:"code,omitempty"` // CodeChanges changes ([tx_index -> new_code])
|
||||||
|
|
@ -283,7 +289,7 @@ func (e *AccountAccess) validate() error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check the storage read slots are sorted in order
|
// Check the storage read slots are sorted in order
|
||||||
if !slices.IsSortedFunc(e.StorageReads, func(a, b encodedStorage) int {
|
if !slices.IsSortedFunc(e.StorageReads, func(a, b *EncodedStorage) int {
|
||||||
aHash, bHash := a.ToHash(), b.ToHash()
|
aHash, bHash := a.ToHash(), b.ToHash()
|
||||||
return bytes.Compare(aHash[:], bHash[:])
|
return bytes.Compare(aHash[:], bHash[:])
|
||||||
}) {
|
}) {
|
||||||
|
|
@ -351,7 +357,7 @@ func (a *ConstructionAccountAccesses) toEncodingObj(addr common.Address) Account
|
||||||
res := AccountAccess{
|
res := AccountAccess{
|
||||||
Address: addr,
|
Address: addr,
|
||||||
StorageChanges: make([]encodingSlotWrites, 0),
|
StorageChanges: make([]encodingSlotWrites, 0),
|
||||||
StorageReads: make([]encodedStorage, 0),
|
StorageReads: make([]*EncodedStorage, 0),
|
||||||
BalanceChanges: make([]encodingBalanceChange, 0),
|
BalanceChanges: make([]encodingBalanceChange, 0),
|
||||||
NonceChanges: make([]encodingAccountNonce, 0),
|
NonceChanges: make([]encodingAccountNonce, 0),
|
||||||
CodeChanges: make([]CodeChange, 0),
|
CodeChanges: make([]CodeChange, 0),
|
||||||
|
|
|
||||||
|
|
@ -14,12 +14,16 @@ func (obj *AccountAccess) EncodeRLP(_w io.Writer) error {
|
||||||
_tmp1 := w.List()
|
_tmp1 := w.List()
|
||||||
for _, _tmp2 := range obj.StorageChanges {
|
for _, _tmp2 := range obj.StorageChanges {
|
||||||
_tmp3 := w.List()
|
_tmp3 := w.List()
|
||||||
w.WriteBytes(_tmp2.Slot)
|
if err := _tmp2.Slot.EncodeRLP(w); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
_tmp4 := w.List()
|
_tmp4 := w.List()
|
||||||
for _, _tmp5 := range _tmp2.Accesses {
|
for _, _tmp5 := range _tmp2.Accesses {
|
||||||
_tmp6 := w.List()
|
_tmp6 := w.List()
|
||||||
w.WriteUint64(uint64(_tmp5.TxIdx))
|
w.WriteUint64(uint64(_tmp5.TxIdx))
|
||||||
w.WriteBytes(_tmp5.ValueAfter)
|
if err := _tmp5.ValueAfter.EncodeRLP(w); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
w.ListEnd(_tmp6)
|
w.ListEnd(_tmp6)
|
||||||
}
|
}
|
||||||
w.ListEnd(_tmp4)
|
w.ListEnd(_tmp4)
|
||||||
|
|
@ -28,7 +32,9 @@ func (obj *AccountAccess) EncodeRLP(_w io.Writer) error {
|
||||||
w.ListEnd(_tmp1)
|
w.ListEnd(_tmp1)
|
||||||
_tmp7 := w.List()
|
_tmp7 := w.List()
|
||||||
for _, _tmp8 := range obj.StorageReads {
|
for _, _tmp8 := range obj.StorageReads {
|
||||||
w.WriteBytes(_tmp8)
|
if err := _tmp8.EncodeRLP(w); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
}
|
}
|
||||||
w.ListEnd(_tmp7)
|
w.ListEnd(_tmp7)
|
||||||
_tmp9 := w.List()
|
_tmp9 := w.List()
|
||||||
|
|
@ -87,8 +93,8 @@ func (obj *AccountAccess) DecodeRLP(dec *rlp.Stream) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// Slot:
|
// Slot:
|
||||||
_tmp4, err := dec.Bytes()
|
_tmp4 := new(EncodedStorage)
|
||||||
if err != nil {
|
if err := _tmp4.DecodeRLP(dec); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
_tmp3.Slot = _tmp4
|
_tmp3.Slot = _tmp4
|
||||||
|
|
@ -110,8 +116,8 @@ func (obj *AccountAccess) DecodeRLP(dec *rlp.Stream) error {
|
||||||
}
|
}
|
||||||
_tmp6.TxIdx = _tmp7
|
_tmp6.TxIdx = _tmp7
|
||||||
// ValueAfter:
|
// ValueAfter:
|
||||||
_tmp8, err := dec.Bytes()
|
_tmp8 := new(EncodedStorage)
|
||||||
if err != nil {
|
if err := _tmp8.DecodeRLP(dec); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
_tmp6.ValueAfter = _tmp8
|
_tmp6.ValueAfter = _tmp8
|
||||||
|
|
@ -136,13 +142,13 @@ func (obj *AccountAccess) DecodeRLP(dec *rlp.Stream) error {
|
||||||
}
|
}
|
||||||
_tmp0.StorageChanges = _tmp2
|
_tmp0.StorageChanges = _tmp2
|
||||||
// StorageReads:
|
// StorageReads:
|
||||||
var _tmp9 []encodedStorage
|
var _tmp9 []*EncodedStorage
|
||||||
if _, err := dec.List(); err != nil {
|
if _, err := dec.List(); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
for dec.MoreDataInList() {
|
for dec.MoreDataInList() {
|
||||||
_tmp10, err := dec.Bytes()
|
_tmp10 := new(EncodedStorage)
|
||||||
if err != nil {
|
if err := _tmp10.DecodeRLP(dec); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
_tmp9 = append(_tmp9, _tmp10)
|
_tmp9 = append(_tmp9, _tmp10)
|
||||||
|
|
|
||||||
|
|
@ -119,12 +119,12 @@ func makeTestAccountAccess(sort bool) AccountAccess {
|
||||||
)
|
)
|
||||||
for i := 0; i < 5; i++ {
|
for i := 0; i < 5; i++ {
|
||||||
slot := encodingSlotWrites{
|
slot := encodingSlotWrites{
|
||||||
Slot: testrand.Hash(),
|
Slot: newEncodedStorageFromHash(testrand.Hash()),
|
||||||
}
|
}
|
||||||
for j := 0; j < 3; j++ {
|
for j := 0; j < 3; j++ {
|
||||||
slot.Accesses = append(slot.Accesses, encodingStorageWrite{
|
slot.Accesses = append(slot.Accesses, encodingStorageWrite{
|
||||||
TxIdx: uint16(2 * j),
|
TxIdx: uint16(2 * j),
|
||||||
ValueAfter: testrand.Hash(),
|
ValueAfter: newEncodedStorageFromHash(testrand.Hash()),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
if sort {
|
if sort {
|
||||||
|
|
@ -173,10 +173,14 @@ func makeTestAccountAccess(sort bool) AccountAccess {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var encodedStorageReads []EncodedStorage
|
||||||
|
for _, slot := range storageReads {
|
||||||
|
encodedStorageReads = append(encodedStorageReads, newEncodedStorageFromHash(slot))
|
||||||
|
}
|
||||||
return AccountAccess{
|
return AccountAccess{
|
||||||
Address: [20]byte(testrand.Bytes(20)),
|
Address: [20]byte(testrand.Bytes(20)),
|
||||||
StorageChanges: storageWrites,
|
StorageChanges: storageWrites,
|
||||||
StorageReads: storageReads,
|
StorageReads: encodedStorageReads,
|
||||||
BalanceChanges: balances,
|
BalanceChanges: balances,
|
||||||
NonceChanges: nonces,
|
NonceChanges: nonces,
|
||||||
CodeChanges: []CodeChange{
|
CodeChanges: []CodeChange{
|
||||||
|
|
@ -216,7 +220,7 @@ func TestBlockAccessListCopy(t *testing.T) {
|
||||||
// Make sure the mutations on copy won't affect the origin
|
// Make sure the mutations on copy won't affect the origin
|
||||||
for _, aa := range cpyCpy {
|
for _, aa := range cpyCpy {
|
||||||
for i := 0; i < len(aa.StorageReads); i++ {
|
for i := 0; i < len(aa.StorageReads); i++ {
|
||||||
aa.StorageReads[i] = [32]byte(testrand.Bytes(32))
|
aa.StorageReads[i] = testrand.Bytes(32)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if !reflect.DeepEqual(list, cpy) {
|
if !reflect.DeepEqual(list, cpy) {
|
||||||
|
|
|
||||||
|
|
@ -515,6 +515,7 @@ func (api *ConsensusAPI) getPayload(payloadID engine.PayloadID, full bool) (*eng
|
||||||
if data == nil {
|
if data == nil {
|
||||||
return nil, engine.UnknownPayload
|
return nil, engine.UnknownPayload
|
||||||
}
|
}
|
||||||
|
|
||||||
return data, nil
|
return data, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -22,12 +22,6 @@ import (
|
||||||
"encoding/hex"
|
"encoding/hex"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/ethereum/go-ethereum/core/types/bal"
|
|
||||||
stdmath "math"
|
|
||||||
"math/big"
|
|
||||||
"os"
|
|
||||||
"reflect"
|
|
||||||
|
|
||||||
"github.com/ethereum/go-ethereum/common"
|
"github.com/ethereum/go-ethereum/common"
|
||||||
"github.com/ethereum/go-ethereum/common/hexutil"
|
"github.com/ethereum/go-ethereum/common/hexutil"
|
||||||
"github.com/ethereum/go-ethereum/common/math"
|
"github.com/ethereum/go-ethereum/common/math"
|
||||||
|
|
@ -38,6 +32,7 @@ import (
|
||||||
"github.com/ethereum/go-ethereum/core/state"
|
"github.com/ethereum/go-ethereum/core/state"
|
||||||
"github.com/ethereum/go-ethereum/core/tracing"
|
"github.com/ethereum/go-ethereum/core/tracing"
|
||||||
"github.com/ethereum/go-ethereum/core/types"
|
"github.com/ethereum/go-ethereum/core/types"
|
||||||
|
"github.com/ethereum/go-ethereum/core/types/bal"
|
||||||
"github.com/ethereum/go-ethereum/core/vm"
|
"github.com/ethereum/go-ethereum/core/vm"
|
||||||
"github.com/ethereum/go-ethereum/log"
|
"github.com/ethereum/go-ethereum/log"
|
||||||
"github.com/ethereum/go-ethereum/params"
|
"github.com/ethereum/go-ethereum/params"
|
||||||
|
|
@ -45,6 +40,11 @@ import (
|
||||||
"github.com/ethereum/go-ethereum/triedb"
|
"github.com/ethereum/go-ethereum/triedb"
|
||||||
"github.com/ethereum/go-ethereum/triedb/hashdb"
|
"github.com/ethereum/go-ethereum/triedb/hashdb"
|
||||||
"github.com/ethereum/go-ethereum/triedb/pathdb"
|
"github.com/ethereum/go-ethereum/triedb/pathdb"
|
||||||
|
stdmath "math"
|
||||||
|
"math/big"
|
||||||
|
"os"
|
||||||
|
"reflect"
|
||||||
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
// A BlockTest checks handling of entire blocks.
|
// A BlockTest checks handling of entire blocks.
|
||||||
|
|
@ -305,6 +305,16 @@ func (t *BlockTest) insertBlocks(blockchain *core.BlockChain) ([]btBlock, error)
|
||||||
return nil, fmt.Errorf("block RLP decoding failed when expected to succeed: %v", err)
|
return nil, fmt.Errorf("block RLP decoding failed when expected to succeed: %v", err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check that if we encode the same block, it will result in the same RLP
|
||||||
|
var enc bytes.Buffer
|
||||||
|
if err := rlp.Encode(&enc, cb); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
expected := common.Hex2Bytes(strings.TrimLeft(b.Rlp, "0x"))
|
||||||
|
if !bytes.Equal(enc.Bytes(), expected) {
|
||||||
|
return nil, fmt.Errorf("mismatch. expected\n%s\ngot\n%x\n", expected, enc.Bytes())
|
||||||
|
}
|
||||||
// RLP decoding worked, try to insert into chain:
|
// RLP decoding worked, try to insert into chain:
|
||||||
blocks := types.Blocks{cb}
|
blocks := types.Blocks{cb}
|
||||||
i, err := blockchain.InsertChain(blocks)
|
i, err := blockchain.InsertChain(blocks)
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue