Skip to content

Commit 0c8dcc0

Browse files
authored
Merge pull request #17 from vulcanize/transaction_execution
Transaction execution
2 parents a50d3c6 + 1937670 commit 0c8dcc0

File tree

17 files changed

+392
-87
lines changed

17 files changed

+392
-87
lines changed

accounts/abi/bind/backends/simulated.go

Lines changed: 36 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -299,7 +299,23 @@ func (b *SimulatedBackend) EstimateGas(ctx context.Context, call ethereum.CallMs
299299
// state is modified during execution, make sure to copy it if necessary.
300300
func (b *SimulatedBackend) callContract(ctx context.Context, call ethereum.CallMsg, block *types.Block, statedb *state.StateDB) ([]byte, uint64, bool, error) {
301301
// Ensure message is initialized properly.
302-
if call.GasPrice == nil {
302+
// EIP1559 guards
303+
if b.config.IsEIP1559Finalized(block.Number()) && (call.GasPremium == nil || call.FeeCap == nil || call.GasPrice != nil) {
304+
return nil, 0, false, core.ErrTxNotEIP1559
305+
}
306+
if !b.config.IsEIP1559(block.Number()) && (call.GasPremium != nil || call.FeeCap != nil || call.GasPrice == nil) {
307+
return nil, 0, false, core.ErrTxIsEIP1559
308+
}
309+
if call.GasPrice != nil && (call.GasPremium != nil || call.FeeCap != nil) {
310+
return nil, 0, false, core.ErrTxSetsLegacyAndEIP1559Fields
311+
}
312+
if call.FeeCap != nil && call.GasPremium == nil {
313+
return nil, 0, false, errors.New("if FeeCap is set, GasPremium must be set")
314+
}
315+
if call.GasPremium != nil && call.FeeCap == nil {
316+
return nil, 0, false, errors.New("if GasPremium is set, FeeCap must be set")
317+
}
318+
if call.GasPrice == nil && call.GasPremium == nil {
303319
call.GasPrice = big.NewInt(1)
304320
}
305321
if call.Gas == 0 {
@@ -319,8 +335,12 @@ func (b *SimulatedBackend) callContract(ctx context.Context, call ethereum.CallM
319335
// about the transaction and calling mechanisms.
320336
vmenv := vm.NewEVM(evmContext, statedb, b.config, vm.Config{})
321337
gaspool := new(core.GasPool).AddGas(math.MaxUint64)
338+
var gp1559 *core.GasPool
339+
if b.config.IsEIP1559(block.Number()) {
340+
gp1559 = new(core.GasPool).AddGas(params.MaxGasEIP1559)
341+
}
322342

323-
return core.NewStateTransition(vmenv, msg, gaspool).TransitionDb()
343+
return core.NewStateTransition(vmenv, msg, gaspool, gp1559).TransitionDb()
324344
}
325345

326346
// SendTransaction updates the pending block to include the given transaction.
@@ -329,6 +349,20 @@ func (b *SimulatedBackend) SendTransaction(ctx context.Context, tx *types.Transa
329349
b.mu.Lock()
330350
defer b.mu.Unlock()
331351

352+
// EIP1559 guards
353+
if b.config.IsEIP1559Finalized(b.blockchain.CurrentBlock().Number()) && (tx.GasPremium() == nil || tx.FeeCap() == nil || tx.GasPrice() != nil) {
354+
return core.ErrTxNotEIP1559
355+
}
356+
if !b.config.IsEIP1559(b.blockchain.CurrentBlock().Number()) && (tx.GasPremium() != nil || tx.FeeCap() != nil || tx.GasPrice() == nil) {
357+
return core.ErrTxIsEIP1559
358+
}
359+
if tx.GasPrice() != nil && (tx.GasPremium() != nil || tx.FeeCap() != nil) {
360+
return core.ErrTxSetsLegacyAndEIP1559Fields
361+
}
362+
if tx.GasPrice() == nil && (tx.GasPremium() == nil || tx.FeeCap() == nil) {
363+
return core.ErrMissingGasFields
364+
}
365+
332366
sender, err := types.Sender(types.NewEIP155Signer(b.config.ChainID), tx)
333367
if err != nil {
334368
panic(fmt.Errorf("invalid transaction: %v", err))

cmd/geth/retesteth.go

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -492,6 +492,10 @@ func (api *RetestethAPI) mineBlock() error {
492492
misc.ApplyDAOHardFork(statedb)
493493
}
494494
gasPool := new(core.GasPool).AddGas(header.GasLimit)
495+
var gp1559 *core.GasPool
496+
if api.chainConfig.IsEIP1559(header.Number) {
497+
gp1559 = new(core.GasPool).AddGas(params.MaxGasEIP1559)
498+
}
495499
txCount := 0
496500
var txs []*types.Transaction
497501
var receipts []*types.Receipt
@@ -513,6 +517,7 @@ func (api *RetestethAPI) mineBlock() error {
513517
api.blockchain,
514518
&api.author,
515519
gasPool,
520+
gp1559,
516521
statedb,
517522
header, tx, &header.GasUsed, *api.blockchain.GetVMConfig(),
518523
)
@@ -657,7 +662,11 @@ func (api *RetestethAPI) AccountRange(ctx context.Context,
657662
context := core.NewEVMContext(msg, block.Header(), api.blockchain, nil)
658663
// Not yet the searched for transaction, execute on top of the current state
659664
vmenv := vm.NewEVM(context, statedb, api.blockchain.Config(), vm.Config{})
660-
if _, _, _, err := core.ApplyMessage(vmenv, msg, new(core.GasPool).AddGas(tx.Gas())); err != nil {
665+
var gp1559 *core.GasPool
666+
if vmenv.ChainConfig().IsEIP1559(block.Number()) {
667+
gp1559 = new(core.GasPool).AddGas(params.MaxGasEIP1559)
668+
}
669+
if _, _, _, err := core.ApplyMessage(vmenv, msg, new(core.GasPool).AddGas(tx.Gas()), gp1559); err != nil {
661670
return AccountRangeResult{}, fmt.Errorf("transaction %#x failed: %v", tx.Hash(), err)
662671
}
663672
// Ensure any modifications are committed to the state
@@ -770,7 +779,11 @@ func (api *RetestethAPI) StorageRangeAt(ctx context.Context,
770779
context := core.NewEVMContext(msg, block.Header(), api.blockchain, nil)
771780
// Not yet the searched for transaction, execute on top of the current state
772781
vmenv := vm.NewEVM(context, statedb, api.blockchain.Config(), vm.Config{})
773-
if _, _, _, err := core.ApplyMessage(vmenv, msg, new(core.GasPool).AddGas(tx.Gas())); err != nil {
782+
var gp1559 *core.GasPool
783+
if vmenv.ChainConfig().IsEIP1559(block.Number()) {
784+
gp1559 = new(core.GasPool).AddGas(params.MaxGasEIP1559)
785+
}
786+
if _, _, _, err := core.ApplyMessage(vmenv, msg, new(core.GasPool).AddGas(tx.Gas()), gp1559); err != nil {
774787
return StorageRangeResult{}, fmt.Errorf("transaction %#x failed: %v", tx.Hash(), err)
775788
}
776789
// Ensure any modifications are committed to the state

core/chain_makers.go

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -39,10 +39,11 @@ type BlockGen struct {
3939
header *types.Header
4040
statedb *state.StateDB
4141

42-
gasPool *GasPool
43-
txs []*types.Transaction
44-
receipts []*types.Receipt
45-
uncles []*types.Header
42+
gasPool *GasPool
43+
gasPool1559 *GasPool
44+
txs []*types.Transaction
45+
receipts []*types.Receipt
46+
uncles []*types.Header
4647

4748
config *params.ChainConfig
4849
engine consensus.Engine
@@ -102,8 +103,11 @@ func (b *BlockGen) AddTxWithChain(bc *BlockChain, tx *types.Transaction) {
102103
if b.gasPool == nil {
103104
b.SetCoinbase(common.Address{})
104105
}
106+
if b.gasPool1559 == nil && b.config.IsEIP1559(b.header.Number) {
107+
b.gasPool1559 = new(GasPool).AddGas(params.MaxGasEIP1559)
108+
}
105109
b.statedb.Prepare(tx.Hash(), common.Hash{}, len(b.txs))
106-
receipt, err := ApplyTransaction(b.config, bc, &b.header.Coinbase, b.gasPool, b.statedb, b.header, tx, &b.header.GasUsed, vm.Config{})
110+
receipt, err := ApplyTransaction(b.config, bc, &b.header.Coinbase, b.gasPool, b.gasPool1559, b.statedb, b.header, tx, &b.header.GasUsed, vm.Config{})
107111
if err != nil {
108112
panic(err)
109113
}

core/evm.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ func NewEVMContext(msg Message, header *types.Header, chain ChainContext, author
5555
Difficulty: new(big.Int).Set(header.Difficulty),
5656
GasLimit: header.GasLimit,
5757
GasPrice: new(big.Int).Set(msg.GasPrice()),
58+
BaseFee: header.BaseFee,
5859
}
5960
}
6061

core/state_prefetcher.go

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,11 @@ func (p *statePrefetcher) Prefetch(block *types.Block, statedb *state.StateDB, c
5252
var (
5353
header = block.Header()
5454
gaspool = new(GasPool).AddGas(block.GasLimit())
55+
gp1559 *GasPool
5556
)
57+
if p.config.IsEIP1559(block.Number()) {
58+
gp1559 = new(GasPool).AddGas(params.MaxGasEIP1559)
59+
}
5660
// Iterate over and process the individual transactions
5761
for i, tx := range block.Transactions() {
5862
// If block precaching was interrupted, abort
@@ -61,7 +65,7 @@ func (p *statePrefetcher) Prefetch(block *types.Block, statedb *state.StateDB, c
6165
}
6266
// Block precaching permitted to continue, execute the transaction
6367
statedb.Prepare(tx.Hash(), block.Hash(), i)
64-
if err := precacheTransaction(p.config, p.bc, nil, gaspool, statedb, header, tx, cfg); err != nil {
68+
if err := precacheTransaction(p.config, p.bc, nil, gaspool, gp1559, statedb, header, tx, cfg); err != nil {
6569
return // Ugh, something went horribly wrong, bail out
6670
}
6771
}
@@ -70,7 +74,7 @@ func (p *statePrefetcher) Prefetch(block *types.Block, statedb *state.StateDB, c
7074
// precacheTransaction attempts to apply a transaction to the given state database
7175
// and uses the input parameters for its environment. The goal is not to execute
7276
// the transaction successfully, rather to warm up touched data slots.
73-
func precacheTransaction(config *params.ChainConfig, bc ChainContext, author *common.Address, gaspool *GasPool, statedb *state.StateDB, header *types.Header, tx *types.Transaction, cfg vm.Config) error {
77+
func precacheTransaction(config *params.ChainConfig, bc ChainContext, author *common.Address, gaspool, gp1559 *GasPool, statedb *state.StateDB, header *types.Header, tx *types.Transaction, cfg vm.Config) error {
7478
// Convert the transaction into an executable message and pre-cache its sender
7579
msg, err := tx.AsMessage(types.MakeSigner(config, header.Number))
7680
if err != nil {
@@ -80,6 +84,6 @@ func precacheTransaction(config *params.ChainConfig, bc ChainContext, author *co
8084
context := NewEVMContext(msg, header, bc, author)
8185
vm := vm.NewEVM(context, statedb, config, cfg)
8286

83-
_, _, _, err = ApplyMessage(vm, msg, gaspool)
87+
_, _, _, err = ApplyMessage(vm, msg, gaspool, gp1559)
8488
return err
8589
}

core/state_processor.go

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -60,15 +60,19 @@ func (p *StateProcessor) Process(block *types.Block, statedb *state.StateDB, cfg
6060
header = block.Header()
6161
allLogs []*types.Log
6262
gp = new(GasPool).AddGas(block.GasLimit())
63+
gp1559 *GasPool
6364
)
65+
if p.config.IsEIP1559(block.Number()) {
66+
gp1559 = new(GasPool).AddGas(params.MaxGasEIP1559)
67+
}
6468
// Mutate the block and state according to any hard-fork specs
6569
if p.config.DAOForkSupport && p.config.DAOForkBlock != nil && p.config.DAOForkBlock.Cmp(block.Number()) == 0 {
6670
misc.ApplyDAOHardFork(statedb)
6771
}
6872
// Iterate over and process the individual transactions
6973
for i, tx := range block.Transactions() {
7074
statedb.Prepare(tx.Hash(), block.Hash(), i)
71-
receipt, err := ApplyTransaction(p.config, p.bc, nil, gp, statedb, header, tx, usedGas, cfg)
75+
receipt, err := ApplyTransaction(p.config, p.bc, nil, gp, gp1559, statedb, header, tx, usedGas, cfg)
7276
if err != nil {
7377
return nil, nil, 0, err
7478
}
@@ -85,7 +89,7 @@ func (p *StateProcessor) Process(block *types.Block, statedb *state.StateDB, cfg
8589
// and uses the input parameters for its environment. It returns the receipt
8690
// for the transaction, gas used and an error if the transaction failed,
8791
// indicating the block was invalid.
88-
func ApplyTransaction(config *params.ChainConfig, bc ChainContext, author *common.Address, gp *GasPool, statedb *state.StateDB, header *types.Header, tx *types.Transaction, usedGas *uint64, cfg vm.Config) (*types.Receipt, error) {
92+
func ApplyTransaction(config *params.ChainConfig, bc ChainContext, author *common.Address, gp, gp1559 *GasPool, statedb *state.StateDB, header *types.Header, tx *types.Transaction, usedGas *uint64, cfg vm.Config) (*types.Receipt, error) {
8993
msg, err := tx.AsMessage(types.MakeSigner(config, header.Number))
9094
if err != nil {
9195
return nil, err
@@ -96,7 +100,7 @@ func ApplyTransaction(config *params.ChainConfig, bc ChainContext, author *commo
96100
// about the transaction and calling mechanisms.
97101
vmenv := vm.NewEVM(context, statedb, config, cfg)
98102
// Apply the transaction to the current state (included in the env)
99-
_, gas, failed, err := ApplyMessage(vmenv, msg, gp)
103+
_, gas, failed, err := ApplyMessage(vmenv, msg, gp, gp1559)
100104
if err != nil {
101105
return nil, err
102106
}

0 commit comments

Comments
 (0)