mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-07-25 14:16:44 +00:00
core, miner: polish
This commit is contained in:
parent
af879b0ebf
commit
e2420abbc3
8 changed files with 42 additions and 64 deletions
|
|
@ -85,7 +85,7 @@ func (v *BlockValidator) ValidateBody(block *types.Block) error {
|
|||
var blobs int
|
||||
for i, tx := range block.Transactions() {
|
||||
if v.config.IsOsaka(block.Number(), block.Time()) && tx.Gas() > params.MaxTxGas {
|
||||
return fmt.Errorf("transaction exceeds maximum allowed gas limit (has %d gas)", tx.Gas())
|
||||
return fmt.Errorf("%w (cap: %d, tx: %d)", ErrGasLimitTooHigh, params.MaxTxGas, tx.Gas())
|
||||
}
|
||||
|
||||
// Count the number of blobs to validate against the header's blobGasUsed
|
||||
|
|
|
|||
|
|
@ -122,6 +122,9 @@ var (
|
|||
// Message validation errors:
|
||||
ErrEmptyAuthList = errors.New("EIP-7702 transaction with empty auth list")
|
||||
ErrSetCodeTxCreate = errors.New("EIP-7702 transaction cannot be used to create contract")
|
||||
|
||||
// -- EIP-7825 errors --
|
||||
ErrGasLimitTooHigh = errors.New("transaction gas limit too high")
|
||||
)
|
||||
|
||||
// EIP-7702 state transition errors.
|
||||
|
|
|
|||
|
|
@ -1638,6 +1638,11 @@ func (p *BlobPool) Pending(filter txpool.PendingFilter) map[common.Address][]*tx
|
|||
break // blobfee too low, cannot be included, discard rest of txs from the account
|
||||
}
|
||||
}
|
||||
if filter.GasLimitCap != 0 {
|
||||
if tx.execGas > filter.GasLimitCap {
|
||||
break // execution gas limit is too high
|
||||
}
|
||||
}
|
||||
// Transaction was accepted according to the filter, append to the pending list
|
||||
lazies = append(lazies, &txpool.LazyTransaction{
|
||||
Pool: p,
|
||||
|
|
|
|||
|
|
@ -531,13 +531,21 @@ func (pool *LegacyPool) Pending(filter txpool.PendingFilter) map[common.Address]
|
|||
txs := list.Flatten()
|
||||
|
||||
// If the miner requests tip enforcement, cap the lists now
|
||||
if minTipBig != nil {
|
||||
if minTipBig != nil || filter.GasLimitCap != 0 {
|
||||
for i, tx := range txs {
|
||||
if minTipBig != nil {
|
||||
if tx.EffectiveGasTipIntCmp(minTipBig, baseFeeBig) < 0 {
|
||||
txs = txs[:i]
|
||||
break
|
||||
}
|
||||
}
|
||||
if filter.GasLimitCap != 0 {
|
||||
if tx.Gas() > filter.GasLimitCap {
|
||||
txs = txs[:i]
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if len(txs) > 0 {
|
||||
lazies := make([]*txpool.LazyTransaction, len(txs))
|
||||
|
|
@ -1263,16 +1271,17 @@ func (pool *LegacyPool) runReorg(done chan struct{}, reset *txpoolResetRequest,
|
|||
pool.mu.Lock()
|
||||
if reset != nil {
|
||||
if reset.newHead != nil && reset.oldHead != nil {
|
||||
// Discard the transactions with the gas limit higher than the cap.
|
||||
if pool.chainconfig.IsOsaka(reset.newHead.Number, reset.newHead.Time) && !pool.chainconfig.IsOsaka(reset.oldHead.Number, reset.oldHead.Time) {
|
||||
var removeHashes []common.Hash
|
||||
var hashes []common.Hash
|
||||
pool.all.Range(func(hash common.Hash, tx *types.Transaction) bool {
|
||||
if tx.Gas() > params.MaxTxGas {
|
||||
removeHashes = append(removeHashes, hash)
|
||||
hashes = append(hashes, hash)
|
||||
}
|
||||
return true
|
||||
})
|
||||
for _, hash := range removeHashes {
|
||||
pool.all.Remove(hash)
|
||||
for _, hash := range hashes {
|
||||
pool.removeTx(hash, true, true)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -77,6 +77,7 @@ type PendingFilter struct {
|
|||
MinTip *uint256.Int // Minimum miner tip required to include a transaction
|
||||
BaseFee *uint256.Int // Minimum 1559 basefee needed to include a transaction
|
||||
BlobFee *uint256.Int // Minimum 4844 blobfee needed to include a blob transaction
|
||||
GasLimitCap uint64 // Maximum gas can be used for a single transaction execution (0 means no limit)
|
||||
|
||||
OnlyPlainTxs bool // Return only plain EVM transactions (peer-join announces, block space filling)
|
||||
OnlyBlobTxs bool // Return only blob transactions (block blob-space filling)
|
||||
|
|
|
|||
|
|
@ -76,9 +76,6 @@ type TxPool struct {
|
|||
term chan struct{} // Termination channel to detect a closed pool
|
||||
|
||||
sync chan chan error // Testing / simulator channel to block until internal reset is done
|
||||
|
||||
headLock sync.RWMutex
|
||||
head *types.Header // this reflects the state from the latest pool reset
|
||||
}
|
||||
|
||||
// New creates a new transaction pool to gather, sort and filter inbound
|
||||
|
|
@ -107,7 +104,6 @@ func New(gasTip uint64, chain BlockChain, subpools []SubPool) (*TxPool, error) {
|
|||
quit: make(chan chan error),
|
||||
term: make(chan struct{}),
|
||||
sync: make(chan chan error),
|
||||
head: head,
|
||||
}
|
||||
reserver := NewReservationTracker()
|
||||
for i, subpool := range subpools {
|
||||
|
|
@ -207,9 +203,6 @@ func (p *TxPool) loop(head *types.Header) {
|
|||
}
|
||||
select {
|
||||
case resetDone <- newHead:
|
||||
p.headLock.Lock()
|
||||
p.head = newHead
|
||||
p.headLock.Unlock()
|
||||
case <-p.term:
|
||||
}
|
||||
}(oldHead, newHead)
|
||||
|
|
@ -264,14 +257,6 @@ func (p *TxPool) loop(head *types.Header) {
|
|||
errc <- nil
|
||||
}
|
||||
|
||||
// Head returns the header which corresponds to the most recent successful pool
|
||||
// reset.
|
||||
func (p *TxPool) Head() *types.Header {
|
||||
p.headLock.RLock()
|
||||
defer p.headLock.RUnlock()
|
||||
return types.CopyHeader(p.head)
|
||||
}
|
||||
|
||||
// SetGasTip updates the minimum gas tip required by the transaction pool for a
|
||||
// new transaction, and drops all transactions below this threshold.
|
||||
func (p *TxPool) SetGasTip(tip *big.Int) {
|
||||
|
|
|
|||
|
|
@ -87,7 +87,7 @@ func ValidateTransaction(tx *types.Transaction, head *types.Header, signer types
|
|||
return fmt.Errorf("%w: code size %v, limit %v", core.ErrMaxInitCodeSizeExceeded, len(tx.Data()), params.MaxInitCodeSize)
|
||||
}
|
||||
if rules.IsOsaka && tx.Gas() > params.MaxTxGas {
|
||||
return fmt.Errorf("transaction gas exceeded max allowed (%d): %d", params.MaxTxGas, tx.Gas())
|
||||
return fmt.Errorf("%w (cap: %d, tx: %d)", core.ErrGasLimitTooHigh, params.MaxTxGas, tx.Gas())
|
||||
}
|
||||
// Transactions can't be negative. This may never happen using RLP decoded
|
||||
// transactions but may occur for transactions created using the RPC.
|
||||
|
|
|
|||
|
|
@ -60,7 +60,6 @@ type environment struct {
|
|||
blobs int
|
||||
|
||||
witness *stateless.Witness
|
||||
chainConfig *params.ChainConfig
|
||||
}
|
||||
|
||||
const (
|
||||
|
|
@ -260,7 +259,6 @@ func (miner *Miner) makeEnv(parent *types.Header, header *types.Header, coinbase
|
|||
header: header,
|
||||
witness: state.Witness(),
|
||||
evm: vm.NewEVM(core.NewEVMBlockContext(header, miner.chain, &coinbase), state, miner.chainConfig, vm.Config{}),
|
||||
chainConfig: miner.chainConfig,
|
||||
}, nil
|
||||
}
|
||||
|
||||
|
|
@ -427,23 +425,6 @@ func (miner *Miner) commitTransactions(env *environment, plainTxs, blobTxs *tran
|
|||
return nil
|
||||
}
|
||||
|
||||
// fiterTxsAboveGas removes any transactions from the set which exceed a gas threshold.
|
||||
// If a transaction is removed, all higher-nonce transactions from the same account
|
||||
// will also be filtered out.
|
||||
func filterTxsAboveGas(txs map[common.Address][]*txpool.LazyTransaction, maxGas uint64) {
|
||||
for sender, senderTxs := range txs {
|
||||
for i, tx := range senderTxs {
|
||||
if tx.Gas > maxGas {
|
||||
if i == 0 {
|
||||
delete(txs, sender)
|
||||
} else {
|
||||
txs[sender] = txs[sender][:i]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// fillTransactions retrieves the pending transactions from the txpool and fills them
|
||||
// into the given sealing block. The transaction selection and ordering strategy can
|
||||
// be customized with the plugin in the future.
|
||||
|
|
@ -463,7 +444,11 @@ func (miner *Miner) fillTransactions(interrupt *atomic.Int32, env *environment)
|
|||
if env.header.ExcessBlobGas != nil {
|
||||
filter.BlobFee = uint256.MustFromBig(eip4844.CalcBlobFee(miner.chainConfig, env.header))
|
||||
}
|
||||
if miner.chainConfig.IsOsaka(env.header.Number, env.header.Time) {
|
||||
filter.GasLimitCap = params.MaxTxGas
|
||||
}
|
||||
filter.OnlyPlainTxs, filter.OnlyBlobTxs = true, false
|
||||
|
||||
pendingPlainTxs := miner.txpool.Pending(filter)
|
||||
|
||||
filter.OnlyPlainTxs, filter.OnlyBlobTxs = false, true
|
||||
|
|
@ -473,16 +458,6 @@ func (miner *Miner) fillTransactions(interrupt *atomic.Int32, env *environment)
|
|||
prioPlainTxs, normalPlainTxs := make(map[common.Address][]*txpool.LazyTransaction), pendingPlainTxs
|
||||
prioBlobTxs, normalBlobTxs := make(map[common.Address][]*txpool.LazyTransaction), pendingBlobTxs
|
||||
|
||||
// if we have just entered the Osaka fork, it is possible due to the async
|
||||
// nature of txpool resets that the state of the pool has not finished resetting
|
||||
// to a post-fork block. If so, it may not have removed txs that exceed the
|
||||
// eip-7825 transaction maximum gas limit.
|
||||
poolHead := miner.txpool.Head()
|
||||
if env.chainConfig.IsOsaka(env.header.Number, env.header.Time) && !env.chainConfig.IsOsaka(poolHead.Number, poolHead.Time) {
|
||||
filterTxsAboveGas(prioPlainTxs, params.MaxTxGas)
|
||||
filterTxsAboveGas(prioBlobTxs, params.MaxTxGas)
|
||||
}
|
||||
|
||||
for _, account := range prio {
|
||||
if txs := normalPlainTxs[account]; len(txs) > 0 {
|
||||
delete(normalPlainTxs, account)
|
||||
|
|
|
|||
Loading…
Reference in a new issue