Commit 79ef2f02 authored by smartcontracts's avatar smartcontracts Committed by GitHub

fix: Make ovmSETNONCE monotonic (#312)

* fix: Make ovmSETNONCE monotonic

* Use ovmINCREMENTNONCE instead

* Fix build errors

* fix remaining build errors

* last commit was a lie
parent 015bcd94
......@@ -128,7 +128,7 @@ contract OVM_ECDSAContractAccount is iOVM_ECDSAContractAccount {
// We only want to bump the nonce for `ovmCALL` because `ovmCREATE` automatically bumps
// the nonce of the calling account. Normally an EOA would bump the nonce for both
// cases, but since this is a contract we'd end up bumping the nonce twice.
Lib_SafeExecutionManagerWrapper.safeSETNONCE(decodedTx.nonce + 1);
Lib_SafeExecutionManagerWrapper.safeINCREMENTNONCE();
return Lib_SafeExecutionManagerWrapper.safeCALL(
decodedTx.gasLimit,
......
......@@ -459,17 +459,20 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager, Lib_AddressResolver {
}
/**
* Sets the nonce of the current ovmADDRESS.
* @param _nonce New nonce for the current contract.
* Bumps the nonce of the current ovmADDRESS by one.
*/
function ovmSETNONCE(
uint256 _nonce
)
function ovmINCREMENTNONCE()
override
public
notStatic
{
_setAccountNonce(ovmADDRESS(), _nonce);
address account = ovmADDRESS();
uint256 nonce = _getAccountNonce(account);
// Prevent overflow.
if (nonce + 1 > nonce) {
_setAccountNonce(account, nonce + 1);
}
}
/**
......
......@@ -118,7 +118,7 @@ interface iOVM_ExecutionManager {
******************************/
function ovmGETNONCE() external returns (uint256 _nonce);
function ovmSETNONCE(uint256 _nonce) external;
function ovmINCREMENTNONCE() external;
function ovmCREATEEOA(bytes32 _messageHash, uint8 _v, bytes32 _r, bytes32 _s) external;
......
......@@ -208,18 +208,14 @@ library Lib_SafeExecutionManagerWrapper {
}
/**
* Performs a safe ovmSETNONCE call.
* @param _nonce New account nonce.
* Performs a safe ovmINCREMENTNONCE call.
*/
function safeSETNONCE(
uint256 _nonce
)
function safeINCREMENTNONCE()
internal
{
_safeExecutionManagerInteraction(
abi.encodeWithSignature(
"ovmSETNONCE(uint256)",
_nonce
"ovmINCREMENTNONCE()"
)
);
}
......
......@@ -65,7 +65,7 @@ contract mockOVM_ECDSAContractAccount is iOVM_ECDSAContractAccount {
// We only want to bump the nonce for `ovmCALL` because `ovmCREATE` automatically bumps
// the nonce of the calling account. Normally an EOA would bump the nonce for both
// cases, but since this is a contract we'd end up bumping the nonce twice.
Lib_SafeExecutionManagerWrapper.safeSETNONCE(decodedTx.nonce + 1);
Lib_SafeExecutionManagerWrapper.safeINCREMENTNONCE();
return Lib_SafeExecutionManagerWrapper.safeCALL(
decodedTx.gasLimit,
......
......@@ -109,10 +109,6 @@ describe('OVM_ECDSAContractAccount', () => {
expect(ovmCALL._gasLimit).to.equal(DEFAULT_EIP155_TX.gasLimit)
expect(ovmCALL._address).to.equal(DEFAULT_EIP155_TX.to)
expect(ovmCALL._calldata).to.equal(DEFAULT_EIP155_TX.data)
const ovmSETNONCE: any =
Mock__OVM_ExecutionManager.smocked.ovmSETNONCE.calls[0]
expect(ovmSETNONCE._nonce).to.equal(DEFAULT_EIP155_TX.nonce + 1)
})
it(`should successfully execute an ETHSignedTransaction`, async () => {
......@@ -137,10 +133,6 @@ describe('OVM_ECDSAContractAccount', () => {
expect(ovmCALL._gasLimit).to.equal(DEFAULT_EIP155_TX.gasLimit)
expect(ovmCALL._address).to.equal(DEFAULT_EIP155_TX.to)
expect(ovmCALL._calldata).to.equal(DEFAULT_EIP155_TX.data)
const ovmSETNONCE: any =
Mock__OVM_ExecutionManager.smocked.ovmSETNONCE.calls[0]
expect(ovmSETNONCE._nonce).to.equal(DEFAULT_EIP155_TX.nonce + 1)
})
it(`should ovmCREATE if EIP155Transaction.to is zero address`, async () => {
......
......@@ -98,7 +98,7 @@ const test_ovmCREATEEOA: TestDefinition = {
],
},
{
name: 'ovmCALL(ADDRESS_1) => ovmSETNONCE(3) => ovmGETNONCE',
name: 'ovmCALL(ADDRESS_1) => ovmINCREMENTNONCEx3 => ovmGETNONCE',
steps: [
{
functionName: 'ovmCALL',
......@@ -107,10 +107,15 @@ const test_ovmCREATEEOA: TestDefinition = {
target: '$DUMMY_OVM_ADDRESS_1',
subSteps: [
{
functionName: 'ovmSETNONCE',
functionParams: {
_nonce: '0x03',
},
functionName: 'ovmINCREMENTNONCE',
expectedReturnStatus: true,
},
{
functionName: 'ovmINCREMENTNONCE',
expectedReturnStatus: true,
},
{
functionName: 'ovmINCREMENTNONCE',
expectedReturnStatus: true,
},
{
......
......@@ -28,7 +28,6 @@ import {
isTestStep_EXTCODEHASH,
isTestStep_EXTCODECOPY,
isTestStep_REVERT,
isTestStep_SETNONCE,
} from './test.types'
import { encodeRevertData, REVERT_FLAGS } from '../codec'
import {
......@@ -402,7 +401,6 @@ export class ExecutionManagerTestRunner {
if (
isTestStep_SSTORE(step) ||
isTestStep_SLOAD(step) ||
isTestStep_SETNONCE(step) ||
isTestStep_EXTCODESIZE(step) ||
isTestStep_EXTCODEHASH(step) ||
isTestStep_EXTCODECOPY(step) ||
......
......@@ -87,11 +87,8 @@ interface TestStep_SLOAD {
expectedReturnValue: string | RevertFlagError
}
interface TestStep_SETNONCE {
functionName: 'ovmSETNONCE'
functionParams: {
_nonce: string
}
interface TestStep_INCREMENTNONCE {
functionName: 'ovmINCREMENTNONCE'
expectedReturnStatus: boolean
expectedReturnValue?: RevertFlagError
}
......@@ -176,7 +173,7 @@ export type TestStep =
| TestStep_Context
| TestStep_SSTORE
| TestStep_SLOAD
| TestStep_SETNONCE
| TestStep_INCREMENTNONCE
| TestStep_CALL
| TestStep_CREATE
| TestStep_CREATE2
......@@ -234,10 +231,10 @@ export const isTestStep_SLOAD = (step: TestStep): step is TestStep_SLOAD => {
return step.functionName === 'ovmSLOAD'
}
export const isTestStep_SETNONCE = (
export const isTestStep_INCREMENTNONCE = (
step: TestStep
): step is TestStep_SETNONCE => {
return step.functionName === 'ovmSETNONCE'
): step is TestStep_INCREMENTNONCE => {
return step.functionName === 'ovmINCREMENTNONCE'
}
export const isTestStep_EXTCODESIZE = (
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment