Skip to content

Commit 90e5325

Browse files
gballetjsign
andcommitted
core/{.,state,vm},miner,ethr/tracers: implement 7709
Co-authored-by: Ignacio Hagopian <[email protected]>
1 parent 4d94bd8 commit 90e5325

19 files changed

+118
-70
lines changed

core/chain_makers.go

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -122,6 +122,11 @@ func (b *BlockGen) addTx(bc *BlockChain, vmConfig vm.Config, tx *types.Transacti
122122
if err != nil {
123123
panic(err)
124124
}
125+
// Merge the tx-local access event into the "block-local" one, in order to collect
126+
// all values, so that the witness can be built.
127+
if b.statedb.GetTrie().IsVerkle() {
128+
b.statedb.AccessEvents().Merge(evm.AccessEvents)
129+
}
125130
b.txs = append(b.txs, tx)
126131
b.receipts = append(b.receipts, receipt)
127132
if b.header.BlobGasUsed != nil {
@@ -379,7 +384,7 @@ func GenerateChain(config *params.ChainConfig, parent *types.Block, engine conse
379384
misc.ApplyDAOHardFork(statedb)
380385
}
381386

382-
if config.IsPrague(b.header.Number, b.header.Time) {
387+
if config.IsPrague(b.header.Number, b.header.Time) || config.IsVerkle(b.header.Number, b.header.Time) {
383388
// EIP-2935
384389
blockContext := NewEVMBlockContext(b.header, cm, &b.header.Coinbase)
385390
blockContext.Random = &common.Hash{} // enable post-merge instruction set
@@ -487,13 +492,11 @@ func GenerateVerkleChain(config *params.ChainConfig, parent *types.Block, engine
487492
// Save pre state for proof generation
488493
// preState := statedb.Copy()
489494

490-
// Pre-execution system calls.
491-
if config.IsPrague(b.header.Number, b.header.Time) {
492-
// EIP-2935
493-
blockContext := NewEVMBlockContext(b.header, cm, &b.header.Coinbase)
494-
evm := vm.NewEVM(blockContext, statedb, cm.config, vm.Config{})
495-
ProcessParentBlockHash(b.header.ParentHash, evm)
496-
}
495+
// EIP-2935 / 7709
496+
blockContext := NewEVMBlockContext(b.header, cm, &b.header.Coinbase)
497+
blockContext.Random = &common.Hash{} // enable post-merge instruction set
498+
evm := vm.NewEVM(blockContext, statedb, cm.config, vm.Config{})
499+
ProcessParentBlockHash(b.header.ParentHash, evm)
497500

498501
// Execute any user modifications to the block.
499502
if gen != nil {
@@ -561,7 +564,7 @@ func GenerateVerkleChain(config *params.ChainConfig, parent *types.Block, engine
561564
return cm.chain, cm.receipts, proofs, keyvals
562565
}
563566

564-
func GenerateVerkleChainWithGenesis(genesis *Genesis, engine consensus.Engine, n int, gen func(int, *BlockGen)) (ethdb.Database, []*types.Block, []types.Receipts, []*verkle.VerkleProof, []verkle.StateDiff) {
567+
func GenerateVerkleChainWithGenesis(genesis *Genesis, engine consensus.Engine, n int, gen func(int, *BlockGen)) (common.Hash, ethdb.Database, []*types.Block, []types.Receipts, []*verkle.VerkleProof, []verkle.StateDiff) {
565568
db := rawdb.NewMemoryDatabase()
566569
cacheConfig := DefaultCacheConfigWithScheme(rawdb.PathScheme)
567570
cacheConfig.SnapshotLimit = 0
@@ -572,7 +575,7 @@ func GenerateVerkleChainWithGenesis(genesis *Genesis, engine consensus.Engine, n
572575
panic(err)
573576
}
574577
blocks, receipts, proofs, keyvals := GenerateVerkleChain(genesis.Config, genesisBlock, engine, db, triedb, n, gen)
575-
return db, blocks, receipts, proofs, keyvals
578+
return genesisBlock.Hash(), db, blocks, receipts, proofs, keyvals
576579
}
577580

578581
func (cm *chainMaker) makeHeader(parent *types.Block, state *state.StateDB, engine consensus.Engine) *types.Header {

core/state/statedb_hooked.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,10 @@ func (s *hookedStateDB) Witness() *stateless.Witness {
157157
return s.inner.Witness()
158158
}
159159

160+
func (s *hookedStateDB) AccessEvents() *AccessEvents {
161+
return s.inner.AccessEvents()
162+
}
163+
160164
func (s *hookedStateDB) SubBalance(addr common.Address, amount *uint256.Int, reason tracing.BalanceChangeReason) uint256.Int {
161165
prev := s.inner.SubBalance(addr, amount, reason)
162166
if s.hooks.OnBalanceChange != nil && !amount.IsZero() {

core/state_processor.go

Lines changed: 17 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ func (p *StateProcessor) Process(block *types.Block, statedb *state.StateDB, cfg
8585
if beaconRoot := block.BeaconRoot(); beaconRoot != nil {
8686
ProcessBeaconBlockRoot(*beaconRoot, evm)
8787
}
88-
if p.config.IsPrague(block.Number(), block.Time()) {
88+
if p.config.IsPrague(block.Number(), block.Time()) || p.config.IsVerkle(block.Number(), block.Time()) {
8989
ProcessParentBlockHash(block.ParentHash(), evm)
9090
}
9191

@@ -155,6 +155,12 @@ func ApplyTransactionWithEVM(msg *Message, gp *GasPool, statedb *state.StateDB,
155155
}
156156
*usedGas += result.UsedGas
157157

158+
// Merge the tx-local access event into the "block-local" one, in order to collect
159+
// all values, so that the witness can be built.
160+
if statedb.GetTrie().IsVerkle() {
161+
statedb.AccessEvents().Merge(evm.AccessEvents)
162+
}
163+
158164
return MakeReceipt(evm, result, statedb, blockNumber, blockHash, tx, *usedGas, root), nil
159165
}
160166

@@ -181,12 +187,6 @@ func MakeReceipt(evm *vm.EVM, result *ExecutionResult, statedb *state.StateDB, b
181187
receipt.ContractAddress = crypto.CreateAddress(evm.TxContext.Origin, tx.Nonce())
182188
}
183189

184-
// Merge the tx-local access event into the "block-local" one, in order to collect
185-
// all values, so that the witness can be built.
186-
if statedb.GetTrie().IsVerkle() {
187-
statedb.AccessEvents().Merge(evm.AccessEvents)
188-
}
189-
190190
// Set the receipt logs and create the bloom filter.
191191
receipt.Logs = statedb.GetLogs(tx.Hash(), blockNumber.Uint64(), blockHash)
192192
receipt.Bloom = types.CreateBloom(types.Receipts{receipt})
@@ -229,12 +229,12 @@ func ProcessBeaconBlockRoot(beaconRoot common.Hash, evm *vm.EVM) {
229229
}
230230
evm.SetTxContext(NewEVMTxContext(msg))
231231
evm.StateDB.AddAddressToAccessList(params.BeaconRootsAddress)
232-
_, _, _ = evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560)
232+
_, _, _ = evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560, true)
233233
evm.StateDB.Finalise(true)
234234
}
235235

236236
// ProcessParentBlockHash stores the parent block hash in the history storage contract
237-
// as per EIP-2935.
237+
// as per EIP-2935/7709.
238238
func ProcessParentBlockHash(prevHash common.Hash, evm *vm.EVM) {
239239
if tracer := evm.Config.Tracer; tracer != nil {
240240
onSystemCallStart(tracer, evm.GetVMContext())
@@ -253,7 +253,13 @@ func ProcessParentBlockHash(prevHash common.Hash, evm *vm.EVM) {
253253
}
254254
evm.SetTxContext(NewEVMTxContext(msg))
255255
evm.StateDB.AddAddressToAccessList(params.HistoryStorageAddress)
256-
_, _, _ = evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560)
256+
_, _, err := evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560, true)
257+
if err != nil {
258+
panic(err)
259+
}
260+
if evm.StateDB.AccessEvents() != nil {
261+
evm.StateDB.AccessEvents().Merge(evm.AccessEvents)
262+
}
257263
evm.StateDB.Finalise(true)
258264
}
259265

@@ -286,7 +292,7 @@ func processRequestsSystemCall(requests *[][]byte, evm *vm.EVM, requestType byte
286292
}
287293
evm.SetTxContext(NewEVMTxContext(msg))
288294
evm.StateDB.AddAddressToAccessList(addr)
289-
ret, _, _ := evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560)
295+
ret, _, _ := evm.Call(vm.AccountRef(msg.From), *msg.To, msg.Data, 30_000_000, common.U2560, true)
290296
evm.StateDB.Finalise(true)
291297
if len(ret) == 0 {
292298
return // skip empty output

core/state_transition.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -484,7 +484,7 @@ func (st *stateTransition) execute() (*ExecutionResult, error) {
484484
}
485485

486486
// Execute the transaction's call.
487-
ret, st.gasRemaining, vmerr = st.evm.Call(sender, st.to(), msg.Data, st.gasRemaining, value)
487+
ret, st.gasRemaining, vmerr = st.evm.Call(sender, st.to(), msg.Data, st.gasRemaining, value, false)
488488
}
489489

490490
var gasRefund uint64

core/verkle_witness_test.go

Lines changed: 31 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -152,7 +152,7 @@ func TestProcessVerkle(t *testing.T) {
152152
txCost1*2 + txCost2,
153153
txCost1*2 + txCost2 + contractCreationCost + codeWithExtCodeCopyGas,
154154
}
155-
_, chain, _, proofs, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
155+
_, _, chain, _, proofs, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
156156
gen.SetPoS()
157157

158158
// TODO need to check that the tx cost provided is the exact amount used (no remaining left-over)
@@ -219,44 +219,51 @@ func TestProcessParentBlockHash(t *testing.T) {
219219
// block 1 parent hash is 0x0100....
220220
// block 2 parent hash is 0x0200....
221221
// etc
222-
checkBlockHashes := func(statedb *state.StateDB) {
222+
checkBlockHashes := func(statedb *state.StateDB, isVerkle bool) {
223223
statedb.SetNonce(params.HistoryStorageAddress, 1)
224224
statedb.SetCode(params.HistoryStorageAddress, params.HistoryStorageCode)
225225
// Process n blocks, from 1 .. num
226226
var num = 2
227227
for i := 1; i <= num; i++ {
228228
header := &types.Header{ParentHash: common.Hash{byte(i)}, Number: big.NewInt(int64(i)), Difficulty: new(big.Int)}
229229
vmContext := NewEVMBlockContext(header, nil, new(common.Address))
230-
evm := vm.NewEVM(vmContext, statedb, params.MergedTestChainConfig, vm.Config{})
230+
chainConfig := params.MergedTestChainConfig
231+
if isVerkle {
232+
chainConfig = testVerkleChainConfig
233+
}
234+
evm := vm.NewEVM(vmContext, statedb, chainConfig, vm.Config{})
231235
ProcessParentBlockHash(header.ParentHash, evm)
232236
}
233237
// Read block hashes for block 0 .. num-1
234238
for i := 0; i < num; i++ {
235-
have, want := getContractStoredBlockHash(statedb, uint64(i)), common.Hash{byte(i + 1)}
239+
have, want := getContractStoredBlockHash(statedb, uint64(i), isVerkle), common.Hash{byte(i + 1)}
236240
if have != want {
237-
t.Errorf("block %d, have parent hash %v, want %v", i, have, want)
241+
t.Errorf("block %d, verkle=%v, have parent hash %v, want %v", i, isVerkle, have, want)
238242
}
239243
}
240244
}
241245
t.Run("MPT", func(t *testing.T) {
242246
statedb, _ := state.New(types.EmptyRootHash, state.NewDatabaseForTesting())
243-
checkBlockHashes(statedb)
247+
checkBlockHashes(statedb, false)
244248
})
245249
t.Run("Verkle", func(t *testing.T) {
246250
db := rawdb.NewMemoryDatabase()
247251
cacheConfig := DefaultCacheConfigWithScheme(rawdb.PathScheme)
248252
cacheConfig.SnapshotLimit = 0
249253
triedb := triedb.NewDatabase(db, cacheConfig.triedbConfig(true))
250254
statedb, _ := state.New(types.EmptyVerkleHash, state.NewDatabase(triedb, nil))
251-
checkBlockHashes(statedb)
255+
checkBlockHashes(statedb, true)
252256
})
253257
}
254258

255259
// getContractStoredBlockHash is a utility method which reads the stored parent blockhash for block 'number'
256-
func getContractStoredBlockHash(statedb *state.StateDB, number uint64) common.Hash {
260+
func getContractStoredBlockHash(statedb *state.StateDB, number uint64, isVerkle bool) common.Hash {
257261
ringIndex := number % params.HistoryServeWindow
258262
var key common.Hash
259263
binary.BigEndian.PutUint64(key[24:], ringIndex)
264+
if isVerkle {
265+
return statedb.GetState(params.HistoryStorageAddress, key)
266+
}
260267
return statedb.GetState(params.HistoryStorageAddress, key)
261268
}
262269

@@ -279,7 +286,7 @@ func TestProcessVerkleInvalidContractCreation(t *testing.T) {
279286
//
280287
// - The second block contains a single failing contract creation transaction,
281288
// that fails right off the bat.
282-
_, chain, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
289+
genesisH, _, chain, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
283290
gen.SetPoS()
284291

285292
if i == 0 {
@@ -364,8 +371,9 @@ func TestProcessVerkleInvalidContractCreation(t *testing.T) {
364371
if stemStateDiff.SuffixDiffs[0].NewValue == nil {
365372
t.Fatalf("nil new value in BLOCKHASH contract insert")
366373
}
367-
if *stemStateDiff.SuffixDiffs[0].NewValue != chain[0].Hash() {
368-
t.Fatalf("invalid BLOCKHASH value: %x != %x", *stemStateDiff.SuffixDiffs[0].NewValue, chain[0].Hash())
374+
if *stemStateDiff.SuffixDiffs[0].NewValue != genesisH {
375+
// je sais pas pourquoi, le hash storé est faux. On dirait le empty code hash mais c'est un hasard
376+
t.Fatalf("invalid BLOCKHASH value: %x != %x", *stemStateDiff.SuffixDiffs[0].NewValue, genesisH)
369377
}
370378
} else {
371379
// For all other entries present in the witness, check that nothing beyond
@@ -393,8 +401,8 @@ func TestProcessVerkleInvalidContractCreation(t *testing.T) {
393401
if stemStateDiff.SuffixDiffs[0].NewValue == nil {
394402
t.Fatalf("missing post state value for BLOCKHASH contract at block #2")
395403
}
396-
if *stemStateDiff.SuffixDiffs[0].NewValue != common.HexToHash("0788c2c0f23aa07eb8bf76fe6c1ca9064a4821c1fd0af803913da488a58dba54") {
397-
t.Fatalf("invalid post state value for BLOCKHASH contract at block #2: 0788c2c0f23aa07eb8bf76fe6c1ca9064a4821c1fd0af803913da488a58dba54 != %x", (*stemStateDiff.SuffixDiffs[0].NewValue)[:])
404+
if *stemStateDiff.SuffixDiffs[0].NewValue != chain[0].Hash() {
405+
t.Fatalf("invalid post state value for BLOCKHASH contract at block #2: %x != %x", chain[0].Hash(), (*stemStateDiff.SuffixDiffs[0].NewValue)[:])
398406
}
399407
} else if suffixDiff.Suffix > 4 {
400408
t.Fatalf("invalid suffix diff found for %x in block #2: %d\n", stemStateDiff.Stem, suffixDiff.Suffix)
@@ -440,7 +448,7 @@ func TestProcessVerkleContractWithEmptyCode(t *testing.T) {
440448
config.ChainID.SetUint64(69421)
441449
gspec := verkleTestGenesis(&config)
442450

443-
_, chain, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
451+
genesisH, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
444452
gen.SetPoS()
445453
var tx types.Transaction
446454
// a transaction that does some PUSH1n but returns a 0-sized contract
@@ -472,8 +480,8 @@ func TestProcessVerkleContractWithEmptyCode(t *testing.T) {
472480
if stemStateDiff.SuffixDiffs[0].NewValue == nil {
473481
t.Fatalf("nil new value in BLOCKHASH contract insert")
474482
}
475-
if *stemStateDiff.SuffixDiffs[0].NewValue != chain[0].Hash() {
476-
t.Fatalf("invalid BLOCKHASH value: %x != %x", *stemStateDiff.SuffixDiffs[0].NewValue, chain[0].Hash())
483+
if *stemStateDiff.SuffixDiffs[0].NewValue != genesisH {
484+
t.Fatalf("invalid BLOCKHASH value: %x != %x", *stemStateDiff.SuffixDiffs[0].NewValue, genesisH)
477485
}
478486
} else {
479487
for _, suffixDiff := range stemStateDiff.SuffixDiffs {
@@ -532,7 +540,7 @@ func TestProcessVerkleExtCodeHashOpcode(t *testing.T) {
532540
}
533541
extCodeHashContractAddr := crypto.CreateAddress(deployer, 1)
534542

535-
_, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
543+
_, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
536544
gen.SetPoS()
537545

538546
if i == 0 {
@@ -605,7 +613,7 @@ func TestProcessVerkleBalanceOpcode(t *testing.T) {
605613
account2 = common.HexToAddress("0x6177843db3138ae69679A54b95cf345ED759450d")
606614
gspec = verkleTestGenesis(&config)
607615
)
608-
_, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
616+
_, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
609617
gen.SetPoS()
610618
txData := slices.Concat(
611619
[]byte{byte(vm.PUSH20)},
@@ -686,7 +694,7 @@ func TestProcessVerkleSelfDestructInSeparateTx(t *testing.T) {
686694
deployer := crypto.PubkeyToAddress(testKey.PublicKey)
687695
contract := crypto.CreateAddress(deployer, 0)
688696

689-
_, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
697+
_, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
690698
gen.SetPoS()
691699

692700
if i == 0 {
@@ -794,7 +802,7 @@ func TestProcessVerkleSelfDestructInSameTx(t *testing.T) {
794802
deployer := crypto.PubkeyToAddress(testKey.PublicKey)
795803
contract := crypto.CreateAddress(deployer, 0)
796804

797-
_, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
805+
_, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
798806
gen.SetPoS()
799807
tx, _ := types.SignNewTx(testKey, signer, &types.LegacyTx{Nonce: 0,
800808
Value: big.NewInt(42),
@@ -897,7 +905,7 @@ func TestProcessVerkleSelfDestructInSeparateTxWithSelfBeneficiary(t *testing.T)
897905
deployer := crypto.PubkeyToAddress(testKey.PublicKey)
898906
contract := crypto.CreateAddress(deployer, 0)
899907

900-
_, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
908+
_, _, _, _, _, statediffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 2, func(i int, gen *BlockGen) {
901909
gen.SetPoS()
902910
if i == 0 {
903911
// Create self-destruct contract, sending 42 wei.
@@ -977,7 +985,7 @@ func TestProcessVerkleSelfDestructInSameTxWithSelfBeneficiary(t *testing.T) {
977985

978986
selfDestructContract := []byte{byte(vm.ADDRESS), byte(vm.SELFDESTRUCT)}
979987

980-
_, _, _, _, stateDiffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
988+
_, _, _, _, _, stateDiffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
981989
gen.SetPoS()
982990
tx, _ := types.SignNewTx(testKey, signer, &types.LegacyTx{Nonce: 0,
983991
Value: big.NewInt(42),
@@ -1043,7 +1051,7 @@ func TestProcessVerkleSelfDestructInSameTxWithSelfBeneficiaryAndPrefundedAccount
10431051

10441052
selfDestructContract := []byte{byte(vm.ADDRESS), byte(vm.SELFDESTRUCT)}
10451053

1046-
_, _, _, _, stateDiffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
1054+
_, _, _, _, _, stateDiffs := GenerateVerkleChainWithGenesis(gspec, beacon.New(ethash.NewFaker()), 1, func(i int, gen *BlockGen) {
10471055
gen.SetPoS()
10481056
tx, _ := types.SignNewTx(testKey, signer, &types.LegacyTx{Nonce: 0,
10491057
Value: big.NewInt(42),

core/vm/contract.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ type Contract struct {
5959

6060
// is the execution frame represented by this object a contract deployment
6161
IsDeployment bool
62+
IsSystemCall bool
6263

6364
Gas uint64
6465
value *uint256.Int

core/vm/eips.go

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -345,10 +345,12 @@ func opExtCodeCopyEIP4762(pc *uint64, interpreter *EVMInterpreter, scope *ScopeC
345345
self: AccountRef(addr),
346346
}
347347
paddedCodeCopy, copyOffset, nonPaddedCopyLength := getDataAndAdjustedBounds(code, uint64CodeOffset, length.Uint64())
348-
statelessGas := interpreter.evm.AccessEvents.CodeChunksRangeGas(addr, copyOffset, nonPaddedCopyLength, uint64(len(contract.Code)), false)
349-
if !scope.Contract.UseGas(statelessGas, interpreter.evm.Config.Tracer, tracing.GasChangeUnspecified) {
350-
scope.Contract.Gas = 0
351-
return nil, ErrOutOfGas
348+
if !contract.IsSystemCall {
349+
statelessGas := interpreter.evm.AccessEvents.CodeChunksRangeGas(addr, copyOffset, nonPaddedCopyLength, uint64(len(contract.Code)), false)
350+
if !scope.Contract.UseGas(statelessGas, interpreter.evm.Config.Tracer, tracing.GasChangeUnspecified) {
351+
scope.Contract.Gas = 0
352+
return nil, ErrOutOfGas
353+
}
352354
}
353355
scope.Memory.Set(memOffset.Uint64(), length.Uint64(), paddedCodeCopy)
354356

@@ -367,7 +369,7 @@ func opPush1EIP4762(pc *uint64, interpreter *EVMInterpreter, scope *ScopeContext
367369
if *pc < codeLen {
368370
scope.Stack.push(integer.SetUint64(uint64(scope.Contract.Code[*pc])))
369371

370-
if !scope.Contract.IsDeployment && *pc%31 == 0 {
372+
if !scope.Contract.IsDeployment && !scope.Contract.IsSystemCall && *pc%31 == 0 {
371373
// touch next chunk if PUSH1 is at the boundary. if so, *pc has
372374
// advanced past this boundary.
373375
contractAddr := scope.Contract.Address()
@@ -397,7 +399,7 @@ func makePushEIP4762(size uint64, pushByteSize int) executionFunc {
397399
)),
398400
)
399401

400-
if !scope.Contract.IsDeployment {
402+
if !scope.Contract.IsDeployment && !scope.Contract.IsSystemCall {
401403
contractAddr := scope.Contract.Address()
402404
statelessGas := interpreter.evm.AccessEvents.CodeChunksRangeGas(contractAddr, uint64(start), uint64(pushByteSize), uint64(len(scope.Contract.Code)), false)
403405
if !scope.Contract.UseGas(statelessGas, interpreter.evm.Config.Tracer, tracing.GasChangeUnspecified) {

0 commit comments

Comments
 (0)