mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-06-19 21:31:37 +00:00
core/vm: implement EIP-2681: Limit account nonce to 2^64-1 (#23853)
This commit is contained in:
parent
7aeb9bd8f9
commit
6f1d1b6688
4 changed files with 20 additions and 9 deletions
|
|
@ -37,6 +37,10 @@ var (
|
|||
// next one expected based on the local chain.
|
||||
ErrNonceTooHigh = errors.New("nonce too high")
|
||||
|
||||
// ErrNonceMax is returned if the nonce of a transaction sender account has
|
||||
// maximum allowed value and would become invalid if incremented.
|
||||
ErrNonceMax = errors.New("nonce has max value")
|
||||
|
||||
ErrNotXDPoS = errors.New("XDPoS not found in config")
|
||||
|
||||
ErrNotFoundM1 = errors.New("list M1 not found ")
|
||||
|
|
|
|||
|
|
@ -197,16 +197,19 @@ func (st *StateTransition) buyGas() error {
|
|||
}
|
||||
|
||||
func (st *StateTransition) preCheck() error {
|
||||
msg := st.msg
|
||||
sender := st.from()
|
||||
|
||||
// Make sure this transaction's nonce is correct
|
||||
if msg.CheckNonce() {
|
||||
nonce := st.state.GetNonce(sender.Address())
|
||||
if nonce < msg.Nonce() {
|
||||
return ErrNonceTooHigh
|
||||
} else if nonce > msg.Nonce() {
|
||||
return ErrNonceTooLow
|
||||
if st.msg.CheckNonce() {
|
||||
// Make sure this transaction's nonce is correct.
|
||||
stNonce := st.state.GetNonce(st.from().Address())
|
||||
if msgNonce := st.msg.Nonce(); stNonce < msgNonce {
|
||||
return fmt.Errorf("%w: address %v, tx: %d state: %d", ErrNonceTooHigh,
|
||||
st.msg.From().Hex(), msgNonce, stNonce)
|
||||
} else if stNonce > msgNonce {
|
||||
return fmt.Errorf("%w: address %v, tx: %d state: %d", ErrNonceTooLow,
|
||||
st.msg.From().Hex(), msgNonce, stNonce)
|
||||
} else if stNonce+1 < stNonce {
|
||||
return fmt.Errorf("%w: address %v, nonce: %d", ErrNonceMax,
|
||||
st.msg.From().Hex(), stNonce)
|
||||
}
|
||||
}
|
||||
return st.buyGas()
|
||||
|
|
|
|||
|
|
@ -34,6 +34,7 @@ var (
|
|||
ErrWriteProtection = errors.New("write protection")
|
||||
ErrReturnDataOutOfBounds = errors.New("return data out of bounds")
|
||||
ErrGasUintOverflow = errors.New("gas uint64 overflow")
|
||||
ErrNonceUintOverflow = errors.New("nonce uint64 overflow")
|
||||
|
||||
// errStopToken is an internal token indicating interpreter loop termination,
|
||||
// never returned to outside callers.
|
||||
|
|
|
|||
|
|
@ -443,6 +443,9 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
|
|||
return nil, common.Address{}, gas, ErrInsufficientBalance
|
||||
}
|
||||
nonce := evm.StateDB.GetNonce(caller.Address())
|
||||
if nonce+1 < nonce {
|
||||
return nil, common.Address{}, gas, ErrNonceUintOverflow
|
||||
}
|
||||
evm.StateDB.SetNonce(caller.Address(), nonce+1)
|
||||
// We add this to the access list _before_ taking a snapshot. Even if the creation fails,
|
||||
// the access-list change should not be rolled back
|
||||
|
|
|
|||
Loading…
Reference in a new issue