all: implement EIP-2929 (gas cost increases for state access opcodes) + yolo-v2 (#21509)
* core/vm, core/state: implement EIP-2929 + YOLOv2 * core/state, core/vm: fix some review concerns * core/state, core/vm: address review concerns * core/vm: address review concerns * core/vm: better documentation * core/vm: unify sload cost as fully dynamic * core/vm: fix typo * core/vm/runtime: fix compilation flaw * core/vm/runtime: fix renaming-err leftovers * core/vm: renaming * params/config: use correct yolov2 chainid for config * core, params: use a proper new genesis for yolov2 * core/state/tests: golinter nitpicks
This commit is contained in:
committed by
GitHub
parent
fb2c79df19
commit
6487c002f6
@ -328,6 +328,20 @@ func newTestAction(addr common.Address, r *rand.Rand) testAction {
|
||||
},
|
||||
args: make([]int64, 1),
|
||||
},
|
||||
{
|
||||
name: "AddAddressToAccessList",
|
||||
fn: func(a testAction, s *StateDB) {
|
||||
s.AddAddressToAccessList(addr)
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "AddSlotToAccessList",
|
||||
fn: func(a testAction, s *StateDB) {
|
||||
s.AddSlotToAccessList(addr,
|
||||
common.Hash{byte(a.args[0])})
|
||||
},
|
||||
args: make([]int64, 1),
|
||||
},
|
||||
}
|
||||
action := actions[r.Intn(len(actions))]
|
||||
var nameargs []string
|
||||
@ -727,3 +741,177 @@ func TestMissingTrieNodes(t *testing.T) {
|
||||
t.Fatalf("expected error, got root :%x", root)
|
||||
}
|
||||
}
|
||||
|
||||
func TestStateDBAccessList(t *testing.T) {
|
||||
// Some helpers
|
||||
addr := func(a string) common.Address {
|
||||
return common.HexToAddress(a)
|
||||
}
|
||||
slot := func(a string) common.Hash {
|
||||
return common.HexToHash(a)
|
||||
}
|
||||
|
||||
memDb := rawdb.NewMemoryDatabase()
|
||||
db := NewDatabase(memDb)
|
||||
state, _ := New(common.Hash{}, db, nil)
|
||||
state.accessList = newAccessList()
|
||||
|
||||
verifyAddrs := func(astrings ...string) {
|
||||
t.Helper()
|
||||
// convert to common.Address form
|
||||
var addresses []common.Address
|
||||
var addressMap = make(map[common.Address]struct{})
|
||||
for _, astring := range astrings {
|
||||
address := addr(astring)
|
||||
addresses = append(addresses, address)
|
||||
addressMap[address] = struct{}{}
|
||||
}
|
||||
// Check that the given addresses are in the access list
|
||||
for _, address := range addresses {
|
||||
if !state.AddressInAccessList(address) {
|
||||
t.Fatalf("expected %x to be in access list", address)
|
||||
}
|
||||
}
|
||||
// Check that only the expected addresses are present in the acesslist
|
||||
for address := range state.accessList.addresses {
|
||||
if _, exist := addressMap[address]; !exist {
|
||||
t.Fatalf("extra address %x in access list", address)
|
||||
}
|
||||
}
|
||||
}
|
||||
verifySlots := func(addrString string, slotStrings ...string) {
|
||||
if !state.AddressInAccessList(addr(addrString)) {
|
||||
t.Fatalf("scope missing address/slots %v", addrString)
|
||||
}
|
||||
var address = addr(addrString)
|
||||
// convert to common.Hash form
|
||||
var slots []common.Hash
|
||||
var slotMap = make(map[common.Hash]struct{})
|
||||
for _, slotString := range slotStrings {
|
||||
s := slot(slotString)
|
||||
slots = append(slots, s)
|
||||
slotMap[s] = struct{}{}
|
||||
}
|
||||
// Check that the expected items are in the access list
|
||||
for i, s := range slots {
|
||||
if _, slotPresent := state.SlotInAccessList(address, s); !slotPresent {
|
||||
t.Fatalf("input %d: scope missing slot %v (address %v)", i, s, addrString)
|
||||
}
|
||||
}
|
||||
// Check that no extra elements are in the access list
|
||||
index := state.accessList.addresses[address]
|
||||
if index >= 0 {
|
||||
stateSlots := state.accessList.slots[index]
|
||||
for s := range stateSlots {
|
||||
if _, slotPresent := slotMap[s]; !slotPresent {
|
||||
t.Fatalf("scope has extra slot %v (address %v)", s, addrString)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
state.AddAddressToAccessList(addr("aa")) // 1
|
||||
state.AddSlotToAccessList(addr("bb"), slot("01")) // 2,3
|
||||
state.AddSlotToAccessList(addr("bb"), slot("02")) // 4
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("bb", "01", "02")
|
||||
|
||||
// Make a copy
|
||||
stateCopy1 := state.Copy()
|
||||
if exp, got := 4, state.journal.length(); exp != got {
|
||||
t.Fatalf("journal length mismatch: have %d, want %d", got, exp)
|
||||
}
|
||||
|
||||
// same again, should cause no journal entries
|
||||
state.AddSlotToAccessList(addr("bb"), slot("01"))
|
||||
state.AddSlotToAccessList(addr("bb"), slot("02"))
|
||||
state.AddAddressToAccessList(addr("aa"))
|
||||
if exp, got := 4, state.journal.length(); exp != got {
|
||||
t.Fatalf("journal length mismatch: have %d, want %d", got, exp)
|
||||
}
|
||||
// some new ones
|
||||
state.AddSlotToAccessList(addr("bb"), slot("03")) // 5
|
||||
state.AddSlotToAccessList(addr("aa"), slot("01")) // 6
|
||||
state.AddSlotToAccessList(addr("cc"), slot("01")) // 7,8
|
||||
state.AddAddressToAccessList(addr("cc"))
|
||||
if exp, got := 8, state.journal.length(); exp != got {
|
||||
t.Fatalf("journal length mismatch: have %d, want %d", got, exp)
|
||||
}
|
||||
|
||||
verifyAddrs("aa", "bb", "cc")
|
||||
verifySlots("aa", "01")
|
||||
verifySlots("bb", "01", "02", "03")
|
||||
verifySlots("cc", "01")
|
||||
|
||||
// now start rolling back changes
|
||||
state.journal.revert(state, 7)
|
||||
if _, ok := state.SlotInAccessList(addr("cc"), slot("01")); ok {
|
||||
t.Fatalf("slot present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb", "cc")
|
||||
verifySlots("aa", "01")
|
||||
verifySlots("bb", "01", "02", "03")
|
||||
|
||||
state.journal.revert(state, 6)
|
||||
if state.AddressInAccessList(addr("cc")) {
|
||||
t.Fatalf("addr present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("aa", "01")
|
||||
verifySlots("bb", "01", "02", "03")
|
||||
|
||||
state.journal.revert(state, 5)
|
||||
if _, ok := state.SlotInAccessList(addr("aa"), slot("01")); ok {
|
||||
t.Fatalf("slot present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("bb", "01", "02", "03")
|
||||
|
||||
state.journal.revert(state, 4)
|
||||
if _, ok := state.SlotInAccessList(addr("bb"), slot("03")); ok {
|
||||
t.Fatalf("slot present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("bb", "01", "02")
|
||||
|
||||
state.journal.revert(state, 3)
|
||||
if _, ok := state.SlotInAccessList(addr("bb"), slot("02")); ok {
|
||||
t.Fatalf("slot present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("bb", "01")
|
||||
|
||||
state.journal.revert(state, 2)
|
||||
if _, ok := state.SlotInAccessList(addr("bb"), slot("01")); ok {
|
||||
t.Fatalf("slot present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa", "bb")
|
||||
|
||||
state.journal.revert(state, 1)
|
||||
if state.AddressInAccessList(addr("bb")) {
|
||||
t.Fatalf("addr present, expected missing")
|
||||
}
|
||||
verifyAddrs("aa")
|
||||
|
||||
state.journal.revert(state, 0)
|
||||
if state.AddressInAccessList(addr("aa")) {
|
||||
t.Fatalf("addr present, expected missing")
|
||||
}
|
||||
if got, exp := len(state.accessList.addresses), 0; got != exp {
|
||||
t.Fatalf("expected empty, got %d", got)
|
||||
}
|
||||
if got, exp := len(state.accessList.slots), 0; got != exp {
|
||||
t.Fatalf("expected empty, got %d", got)
|
||||
}
|
||||
// Check the copy
|
||||
// Make a copy
|
||||
state = stateCopy1
|
||||
verifyAddrs("aa", "bb")
|
||||
verifySlots("bb", "01", "02")
|
||||
if got, exp := len(state.accessList.addresses), 2; got != exp {
|
||||
t.Fatalf("expected empty, got %d", got)
|
||||
}
|
||||
if got, exp := len(state.accessList.slots), 1; got != exp {
|
||||
t.Fatalf("expected empty, got %d", got)
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user