Commit 7b3a9894 authored by Kelvin Fichter's avatar Kelvin Fichter

Added CREATE fix

parent 73da687e
...@@ -34,7 +34,6 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -34,7 +34,6 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
GlobalContext internal globalContext; GlobalContext internal globalContext;
TransactionContext internal transactionContext; TransactionContext internal transactionContext;
MessageContext internal messageContext; MessageContext internal messageContext;
TransactionRecord internal transactionRecord; TransactionRecord internal transactionRecord;
MessageRecord internal messageRecord; MessageRecord internal messageRecord;
...@@ -117,6 +116,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -117,6 +116,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmCALLER() function ovmCALLER()
override override
public public
view
returns ( returns (
address _CALLER address _CALLER
) )
...@@ -131,6 +131,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -131,6 +131,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmADDRESS() function ovmADDRESS()
override override
public public
view
returns ( returns (
address _ADDRESS address _ADDRESS
) )
...@@ -145,6 +146,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -145,6 +146,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmORIGIN() function ovmORIGIN()
override override
public public
view
returns ( returns (
address _ORIGIN address _ORIGIN
) )
...@@ -159,6 +161,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -159,6 +161,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmTIMESTAMP() function ovmTIMESTAMP()
override override
public public
view
returns ( returns (
uint256 _TIMESTAMP uint256 _TIMESTAMP
) )
...@@ -173,6 +176,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -173,6 +176,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmGASLIMIT() function ovmGASLIMIT()
override override
public public
view
returns ( returns (
uint256 _GASLIMIT uint256 _GASLIMIT
) )
...@@ -187,6 +191,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -187,6 +191,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
function ovmCHAINID() function ovmCHAINID()
override override
public public
view
returns ( returns (
uint256 _CHAINID uint256 _CHAINID
) )
...@@ -359,7 +364,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -359,7 +364,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
} }
// If the user already has an EOA account, then there's no need to perform this operation. // If the user already has an EOA account, then there's no need to perform this operation.
if (_hasAccount(eoa) == true) { if (_hasEmptyAccount(eoa) == false) {
return; return;
} }
...@@ -570,7 +575,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -570,7 +575,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
return Lib_EthUtils.getCode( return Lib_EthUtils.getCode(
_getAccountEthAddress(_contract), _getAccountEthAddress(_contract),
_offset, _offset,
_length length
); );
} }
...@@ -643,6 +648,14 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -643,6 +648,14 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
return; return;
} }
// We need to be sure that the user isn't trying to use a contract creation to overwrite
// some existing contract. On L1, users will prove that no contract exists at the address
// and the OVM_FraudVerifier will populate the code hash of this address with a special
// value that represents "known to be an empty account."
if (_hasEmptyAccount(_address) == false) {
_revertWithFlag(RevertFlag.CREATE_COLLISION);
}
// Check the creation bytecode against the OVM_SafetyChecker. // Check the creation bytecode against the OVM_SafetyChecker.
if (ovmSafetyChecker.isBytecodeSafe(_bytecode) == false) { if (ovmSafetyChecker.isBytecodeSafe(_bytecode) == false) {
_revertWithFlag(RevertFlag.UNSAFE_BYTECODE); _revertWithFlag(RevertFlag.UNSAFE_BYTECODE);
...@@ -863,6 +876,23 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -863,6 +876,23 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
return ovmStateManager.hasAccount(_address); return ovmStateManager.hasAccount(_address);
} }
/**
* Checks whether a known empty account exists within the OVM_StateManager.
* @param _address Address of the account to check.
* @return _exists Whether or not the account empty exists.
*/
function _hasEmptyAccount(
address _address
)
internal
returns (
bool _exists
)
{
_checkAccountLoad(_address);
return ovmStateManager.hasEmptyAccount(_address);
}
/** /**
* Sets the nonce of an account. * Sets the nonce of an account.
* @param _address Address of the account to modify. * @param _address Address of the account to modify.
...@@ -921,7 +951,10 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -921,7 +951,10 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
) )
internal internal
{ {
_checkAccountChange(_address); // Although it seems like `_checkAccountChange` would be more appropriate here, we don't
// actually consider an account "changed" until it's inserted into the state (in this case
// by `_commitPendingAccount`).
_checkAccountLoad(_address);
ovmStateManager.initPendingAccount(_address); ovmStateManager.initPendingAccount(_address);
} }
...@@ -1034,6 +1067,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -1034,6 +1067,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
// If we hadn't already changed the account, then we'll need to charge "nuisance gas" based // If we hadn't already changed the account, then we'll need to charge "nuisance gas" based
// on the size of the contract code. // on the size of the contract code.
if (_wasAccountAlreadyChanged == false) { if (_wasAccountAlreadyChanged == false) {
ovmStateManager.incrementTotalUncommittedAccounts();
_useNuisanceGas( _useNuisanceGas(
Lib_EthUtils.getCodeSize(_getAccountEthAddress(_address)) * NUISANCE_GAS_PER_CONTRACT_BYTE Lib_EthUtils.getCodeSize(_getAccountEthAddress(_address)) * NUISANCE_GAS_PER_CONTRACT_BYTE
); );
...@@ -1092,6 +1126,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager { ...@@ -1092,6 +1126,7 @@ contract OVM_ExecutionManager is iOVM_ExecutionManager {
// If we hadn't already changed the account, then we'll need to charge some fixed amount of // If we hadn't already changed the account, then we'll need to charge some fixed amount of
// "nuisance gas". // "nuisance gas".
if (_wasContractStorageAlreadyChanged == false) { if (_wasContractStorageAlreadyChanged == false) {
ovmStateManager.incrementTotalUncommittedContractStorage();
_useNuisanceGas(NUISANCE_GAS_SSTORE); _useNuisanceGas(NUISANCE_GAS_SSTORE);
} }
} }
......
...@@ -13,6 +13,13 @@ import { iOVM_StateManager } from "../../iOVM/execution/iOVM_StateManager.sol"; ...@@ -13,6 +13,13 @@ import { iOVM_StateManager } from "../../iOVM/execution/iOVM_StateManager.sol";
*/ */
contract OVM_StateManager is iOVM_StateManager { contract OVM_StateManager is iOVM_StateManager {
/**********************
* Contract Constants *
**********************/
bytes32 constant internal EMPTY_ACCOUNT_CODE_HASH = 0x6969696969696969696969696969696969696969696969696969696969696969;
/******************************************* /*******************************************
* Contract Variables: Contract References * * Contract Variables: Contract References *
*******************************************/ *******************************************/
...@@ -111,7 +118,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -111,7 +118,7 @@ contract OVM_StateManager is iOVM_StateManager {
function getAccount(address _address) function getAccount(address _address)
override override
public public
authenticated view
returns ( returns (
Lib_OVMCodec.Account memory _account Lib_OVMCodec.Account memory _account
) )
...@@ -129,7 +136,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -129,7 +136,7 @@ contract OVM_StateManager is iOVM_StateManager {
) )
override override
public public
authenticated view
returns ( returns (
bool _exists bool _exists
) )
...@@ -137,6 +144,24 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -137,6 +144,24 @@ contract OVM_StateManager is iOVM_StateManager {
return accounts[_address].codeHash != bytes32(0); return accounts[_address].codeHash != bytes32(0);
} }
/**
* Checks whether the state has a given known empty account.
* @param _address Address of the account to check.
* @return _exists Whether or not the state has the empty account.
*/
function hasEmptyAccount(
address _address
)
override
public
view
returns (
bool _exists
)
{
return accounts[_address].codeHash == EMPTY_ACCOUNT_CODE_HASH;
}
/** /**
* Sets the nonce of an account. * Sets the nonce of an account.
* @param _address Address of the account to modify. * @param _address Address of the account to modify.
...@@ -163,7 +188,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -163,7 +188,7 @@ contract OVM_StateManager is iOVM_StateManager {
) )
override override
public public
authenticated view
returns ( returns (
uint256 _nonce uint256 _nonce
) )
...@@ -181,7 +206,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -181,7 +206,7 @@ contract OVM_StateManager is iOVM_StateManager {
) )
override override
public public
authenticated view
returns ( returns (
address _ethAddress address _ethAddress
) )
...@@ -261,16 +286,10 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -261,16 +286,10 @@ contract OVM_StateManager is iOVM_StateManager {
bool _wasAccountAlreadyChanged bool _wasAccountAlreadyChanged
) )
{ {
bool wasAccountAlreadyChanged = _testAndSetItemState( return _testAndSetItemState(
keccak256(abi.encodePacked(_address)), keccak256(abi.encodePacked(_address)),
ItemState.ITEM_CHANGED ItemState.ITEM_CHANGED
); );
if (!wasAccountAlreadyChanged) {
totalUncommittedAccounts += 1;
}
return wasAccountAlreadyChanged;
} }
/** /**
...@@ -299,6 +318,17 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -299,6 +318,17 @@ contract OVM_StateManager is iOVM_StateManager {
return true; return true;
} }
/**
* Increments the total number of uncommitted accounts.
*/
function incrementTotalUncommittedAccounts()
override
public
authenticated
{
totalUncommittedAccounts += 1;
}
/** /**
* Gets the total number of uncommitted accounts. * Gets the total number of uncommitted accounts.
* @return _total Total uncommitted accounts. * @return _total Total uncommitted accounts.
...@@ -306,7 +336,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -306,7 +336,7 @@ contract OVM_StateManager is iOVM_StateManager {
function getTotalUncommittedAccounts() function getTotalUncommittedAccounts()
override override
public public
authenticated view
returns ( returns (
uint256 _total uint256 _total
) )
...@@ -350,7 +380,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -350,7 +380,7 @@ contract OVM_StateManager is iOVM_StateManager {
) )
override override
public public
authenticated view
returns ( returns (
bytes32 _value bytes32 _value
) )
...@@ -370,7 +400,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -370,7 +400,7 @@ contract OVM_StateManager is iOVM_StateManager {
) )
override override
public public
authenticated view
returns ( returns (
bool _exists bool _exists
) )
...@@ -418,16 +448,10 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -418,16 +448,10 @@ contract OVM_StateManager is iOVM_StateManager {
bool _wasContractStorageAlreadyChanged bool _wasContractStorageAlreadyChanged
) )
{ {
bool wasContractStorageAlreadyChanged = _testAndSetItemState( return _testAndSetItemState(
keccak256(abi.encodePacked(_contract, _key)), keccak256(abi.encodePacked(_contract, _key)),
ItemState.ITEM_CHANGED ItemState.ITEM_CHANGED
); );
if (!wasContractStorageAlreadyChanged) {
totalUncommittedContractStorage += 1;
}
return wasContractStorageAlreadyChanged;
} }
/** /**
...@@ -458,6 +482,17 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -458,6 +482,17 @@ contract OVM_StateManager is iOVM_StateManager {
return true; return true;
} }
/**
* Increments the total number of uncommitted storage slots.
*/
function incrementTotalUncommittedContractStorage()
override
public
authenticated
{
totalUncommittedContractStorage += 1;
}
/** /**
* Gets the total number of uncommitted storage slots. * Gets the total number of uncommitted storage slots.
* @return _total Total uncommitted storage slots. * @return _total Total uncommitted storage slots.
...@@ -465,7 +500,7 @@ contract OVM_StateManager is iOVM_StateManager { ...@@ -465,7 +500,7 @@ contract OVM_StateManager is iOVM_StateManager {
function getTotalUncommittedContractStorage() function getTotalUncommittedContractStorage()
override override
public public
authenticated view
returns ( returns (
uint256 _total uint256 _total
) )
......
...@@ -16,7 +16,8 @@ interface iOVM_ExecutionManager { ...@@ -16,7 +16,8 @@ interface iOVM_ExecutionManager {
INTENTIONAL_REVERT, INTENTIONAL_REVERT,
EXCEEDS_NUISANCE_GAS, EXCEEDS_NUISANCE_GAS,
INVALID_STATE_ACCESS, INVALID_STATE_ACCESS,
UNSAFE_BYTECODE UNSAFE_BYTECODE,
CREATE_COLLISION
} }
struct GlobalContext { struct GlobalContext {
...@@ -61,12 +62,12 @@ interface iOVM_ExecutionManager { ...@@ -61,12 +62,12 @@ interface iOVM_ExecutionManager {
* Context Opcodes * * Context Opcodes *
*******************/ *******************/
function ovmCALLER() external returns (address _caller); function ovmCALLER() external view returns (address _caller);
function ovmADDRESS() external returns (address _address); function ovmADDRESS() external view returns (address _address);
function ovmORIGIN() external returns (address _origin); function ovmORIGIN() external view returns (address _origin);
function ovmTIMESTAMP() external returns (uint256 _timestamp); function ovmTIMESTAMP() external view returns (uint256 _timestamp);
function ovmGASLIMIT() external returns (uint256 _gasLimit); function ovmGASLIMIT() external view returns (uint256 _gasLimit);
function ovmCHAINID() external returns (uint256 _chainId); function ovmCHAINID() external view returns (uint256 _chainId);
/******************* /*******************
......
...@@ -34,17 +34,19 @@ interface iOVM_StateManager { ...@@ -34,17 +34,19 @@ interface iOVM_StateManager {
************************************/ ************************************/
function putAccount(address _address, Lib_OVMCodec.Account memory _account) external; function putAccount(address _address, Lib_OVMCodec.Account memory _account) external;
function getAccount(address _address) external returns (Lib_OVMCodec.Account memory _account); function getAccount(address _address) external view returns (Lib_OVMCodec.Account memory _account);
function hasAccount(address _address) external returns (bool _exists); function hasAccount(address _address) external view returns (bool _exists);
function hasEmptyAccount(address _address) external view returns (bool _exists);
function setAccountNonce(address _address, uint256 _nonce) external; function setAccountNonce(address _address, uint256 _nonce) external;
function getAccountNonce(address _address) external returns (uint256 _nonce); function getAccountNonce(address _address) external view returns (uint256 _nonce);
function getAccountEthAddress(address _address) external returns (address _ethAddress); function getAccountEthAddress(address _address) external view returns (address _ethAddress);
function initPendingAccount(address _address) external; function initPendingAccount(address _address) external;
function commitPendingAccount(address _address, address _ethAddress, bytes32 _codeHash) external; function commitPendingAccount(address _address, address _ethAddress, bytes32 _codeHash) external;
function testAndSetAccountLoaded(address _address) external returns (bool _wasAccountAlreadyLoaded); function testAndSetAccountLoaded(address _address) external returns (bool _wasAccountAlreadyLoaded);
function testAndSetAccountChanged(address _address) external returns (bool _wasAccountAlreadyChanged); function testAndSetAccountChanged(address _address) external returns (bool _wasAccountAlreadyChanged);
function commitAccount(address _address) external returns (bool _wasAccountCommitted); function commitAccount(address _address) external returns (bool _wasAccountCommitted);
function getTotalUncommittedAccounts() external returns (uint256 _total); function incrementTotalUncommittedAccounts() external;
function getTotalUncommittedAccounts() external view returns (uint256 _total);
/************************************ /************************************
...@@ -52,10 +54,11 @@ interface iOVM_StateManager { ...@@ -52,10 +54,11 @@ interface iOVM_StateManager {
************************************/ ************************************/
function putContractStorage(address _contract, bytes32 _key, bytes32 _value) external; function putContractStorage(address _contract, bytes32 _key, bytes32 _value) external;
function getContractStorage(address _contract, bytes32 _key) external returns (bytes32 _value); function getContractStorage(address _contract, bytes32 _key) external view returns (bytes32 _value);
function hasContractStorage(address _contract, bytes32 _key) external returns (bool _exists); function hasContractStorage(address _contract, bytes32 _key) external returns (bool _exists);
function testAndSetContractStorageLoaded(address _contract, bytes32 _key) external returns (bool _wasContractStorageAlreadyLoaded); function testAndSetContractStorageLoaded(address _contract, bytes32 _key) external returns (bool _wasContractStorageAlreadyLoaded);
function testAndSetContractStorageChanged(address _contract, bytes32 _key) external returns (bool _wasContractStorageAlreadyChanged); function testAndSetContractStorageChanged(address _contract, bytes32 _key) external returns (bool _wasContractStorageAlreadyChanged);
function commitContractStorage(address _contract, bytes32 _key) external returns (bool _wasContractStorageCommitted); function commitContractStorage(address _contract, bytes32 _key) external returns (bool _wasContractStorageCommitted);
function getTotalUncommittedContractStorage() external returns (uint256 _total); function incrementTotalUncommittedContractStorage() external;
function getTotalUncommittedContractStorage() external view returns (uint256 _total);
} }
...@@ -106,6 +106,11 @@ library Lib_OVMCodec { ...@@ -106,6 +106,11 @@ library Lib_OVMCodec {
}); });
} }
/**
* Encodes a standard OVM transaction.
* @param _transaction OVM transaction to encode.
* @return _encoded Encoded transaction bytes.
*/
function encodeTransaction( function encodeTransaction(
Transaction memory _transaction Transaction memory _transaction
) )
...@@ -126,6 +131,11 @@ library Lib_OVMCodec { ...@@ -126,6 +131,11 @@ library Lib_OVMCodec {
); );
} }
/**
* Hashes a standard OVM transaction.
* @param _transaction OVM transaction to encode.
* @return _hash Hashed transaction
*/
function hashTransaction( function hashTransaction(
Transaction memory _transaction Transaction memory _transaction
) )
......
...@@ -81,7 +81,7 @@ library Lib_MerkleTrie { ...@@ -81,7 +81,7 @@ library Lib_MerkleTrie {
bool bool
) )
{ {
return verifyProof(_key, _value, _proof, _root, true); return _verifyProof(_key, _value, _proof, _root, true);
} }
/** /**
...@@ -108,7 +108,7 @@ library Lib_MerkleTrie { ...@@ -108,7 +108,7 @@ library Lib_MerkleTrie {
bool bool
) )
{ {
return verifyProof(_key, _value, _proof, _root, false); return _verifyProof(_key, _value, _proof, _root, false);
} }
/** /**
...@@ -134,12 +134,12 @@ library Lib_MerkleTrie { ...@@ -134,12 +134,12 @@ library Lib_MerkleTrie {
bytes32 bytes32
) )
{ {
TrieNode[] memory proof = parseProof(_proof); TrieNode[] memory proof = _parseProof(_proof);
(uint256 pathLength, bytes memory keyRemainder, ) = walkNodePath(proof, _key, _root); (uint256 pathLength, bytes memory keyRemainder, ) = _walkNodePath(proof, _key, _root);
TrieNode[] memory newPath = getNewPath(proof, pathLength, keyRemainder, _value); TrieNode[] memory newPath = _getNewPath(proof, pathLength, keyRemainder, _value);
return getUpdatedTrieRoot(newPath, _key); return _getUpdatedTrieRoot(newPath, _key);
} }
/** /**
...@@ -161,11 +161,11 @@ library Lib_MerkleTrie { ...@@ -161,11 +161,11 @@ library Lib_MerkleTrie {
bytes memory bytes memory
) )
{ {
TrieNode[] memory proof = parseProof(_proof); TrieNode[] memory proof = _parseProof(_proof);
(uint256 pathLength, bytes memory keyRemainder, ) = walkNodePath(proof, _key, _root); (uint256 pathLength, bytes memory keyRemainder, ) = _walkNodePath(proof, _key, _root);
bool exists = keyRemainder.length == 0; bool exists = keyRemainder.length == 0;
bytes memory value = exists ? getNodeValue(proof[pathLength - 1]) : bytes(''); bytes memory value = exists ? _getNodeValue(proof[pathLength - 1]) : bytes('');
return ( return (
exists, exists,
...@@ -189,7 +189,7 @@ library Lib_MerkleTrie { ...@@ -189,7 +189,7 @@ library Lib_MerkleTrie {
bytes32 bytes32
) )
{ {
return keccak256(makeLeafNode( return keccak256(_makeLeafNode(
_key, _key,
_value _value
).encoded); ).encoded);
...@@ -214,7 +214,7 @@ library Lib_MerkleTrie { ...@@ -214,7 +214,7 @@ library Lib_MerkleTrie {
* @param _inclusion Whether to check for inclusion or exclusion. * @param _inclusion Whether to check for inclusion or exclusion.
* @return `true` if the k/v pair is (in/not in) the trie, `false` otherwise. * @return `true` if the k/v pair is (in/not in) the trie, `false` otherwise.
*/ */
function verifyProof( function _verifyProof(
bytes memory _key, bytes memory _key,
bytes memory _value, bytes memory _value,
bytes memory _proof, bytes memory _proof,
...@@ -227,20 +227,20 @@ library Lib_MerkleTrie { ...@@ -227,20 +227,20 @@ library Lib_MerkleTrie {
bool bool
) )
{ {
TrieNode[] memory proof = parseProof(_proof); TrieNode[] memory proof = _parseProof(_proof);
(uint256 pathLength, bytes memory keyRemainder, bool isFinalNode) = walkNodePath(proof, _key, _root); (uint256 pathLength, bytes memory keyRemainder, bool isFinalNode) = _walkNodePath(proof, _key, _root);
if (_inclusion) { if (_inclusion) {
// Included leaf nodes should have no key remainder, values should match. // Included leaf nodes should have no key remainder, values should match.
return ( return (
keyRemainder.length == 0 && keyRemainder.length == 0 &&
Lib_ByteUtils.equal(getNodeValue(proof[pathLength - 1]), _value) Lib_ByteUtils.equal(_getNodeValue(proof[pathLength - 1]), _value)
); );
} else { } else {
// If there's no key remainder then a leaf with the given key exists and the value should differ. // If there's no key remainder then a leaf with the given key exists and the value should differ.
// Otherwise, we need to make sure that we've hit a dead end. // Otherwise, we need to make sure that we've hit a dead end.
return ( return (
(keyRemainder.length == 0 && !Lib_ByteUtils.equal(getNodeValue(proof[pathLength - 1]), _value)) || (keyRemainder.length == 0 && !Lib_ByteUtils.equal(_getNodeValue(proof[pathLength - 1]), _value)) ||
(keyRemainder.length != 0 && isFinalNode) (keyRemainder.length != 0 && isFinalNode)
); );
} }
...@@ -257,7 +257,7 @@ library Lib_MerkleTrie { ...@@ -257,7 +257,7 @@ library Lib_MerkleTrie {
* Whether or not we've hit a dead end; * Whether or not we've hit a dead end;
* ) * )
*/ */
function walkNodePath( function _walkNodePath(
TrieNode[] memory _proof, TrieNode[] memory _proof,
bytes memory _key, bytes memory _key,
bytes32 _root bytes32 _root
...@@ -316,17 +316,17 @@ library Lib_MerkleTrie { ...@@ -316,17 +316,17 @@ library Lib_MerkleTrie {
// Figure out what the next node ID should be and continue. // Figure out what the next node ID should be and continue.
uint8 branchKey = uint8(key[currentKeyIndex]); uint8 branchKey = uint8(key[currentKeyIndex]);
Lib_RLPReader.RLPItem memory nextNode = currentNode.decoded[branchKey]; Lib_RLPReader.RLPItem memory nextNode = currentNode.decoded[branchKey];
currentNodeID = getNodeID(nextNode); currentNodeID = _getNodeID(nextNode);
currentKeyIncrement = 1; currentKeyIncrement = 1;
continue; continue;
} }
} else if (currentNode.decoded.length == LEAF_OR_EXTENSION_NODE_LENGTH) { } else if (currentNode.decoded.length == LEAF_OR_EXTENSION_NODE_LENGTH) {
bytes memory path = getNodePath(currentNode); bytes memory path = _getNodePath(currentNode);
uint8 prefix = uint8(path[0]); uint8 prefix = uint8(path[0]);
uint8 offset = 2 - prefix % 2; uint8 offset = 2 - prefix % 2;
bytes memory pathRemainder = Lib_ByteUtils.slice(path, offset); bytes memory pathRemainder = Lib_ByteUtils.slice(path, offset);
bytes memory keyRemainder = Lib_ByteUtils.slice(key, currentKeyIndex); bytes memory keyRemainder = Lib_ByteUtils.slice(key, currentKeyIndex);
uint256 sharedNibbleLength = getSharedNibbleLength(pathRemainder, keyRemainder); uint256 sharedNibbleLength = _getSharedNibbleLength(pathRemainder, keyRemainder);
if (prefix == PREFIX_LEAF_EVEN || prefix == PREFIX_LEAF_ODD) { if (prefix == PREFIX_LEAF_EVEN || prefix == PREFIX_LEAF_ODD) {
if ( if (
...@@ -350,7 +350,7 @@ library Lib_MerkleTrie { ...@@ -350,7 +350,7 @@ library Lib_MerkleTrie {
} else { } else {
// Our extension shares some nibbles. // Our extension shares some nibbles.
// Carry on to the next node. // Carry on to the next node.
currentNodeID = getNodeID(currentNode.decoded[1]); currentNodeID = _getNodeID(currentNode.decoded[1]);
currentKeyIncrement = sharedNibbleLength; currentKeyIncrement = sharedNibbleLength;
continue; continue;
} }
...@@ -375,7 +375,7 @@ library Lib_MerkleTrie { ...@@ -375,7 +375,7 @@ library Lib_MerkleTrie {
* @param _value Value to insert at the given key. * @param _value Value to insert at the given key.
* @return A new path with the inserted k/v pair and extra supporting nodes. * @return A new path with the inserted k/v pair and extra supporting nodes.
*/ */
function getNewPath( function _getNewPath(
TrieNode[] memory _path, TrieNode[] memory _path,
uint256 _pathLength, uint256 _pathLength,
bytes memory _keyRemainder, bytes memory _keyRemainder,
...@@ -391,7 +391,7 @@ library Lib_MerkleTrie { ...@@ -391,7 +391,7 @@ library Lib_MerkleTrie {
// Most of our logic depends on the status of the last node in the path. // Most of our logic depends on the status of the last node in the path.
TrieNode memory lastNode = _path[_pathLength - 1]; TrieNode memory lastNode = _path[_pathLength - 1];
NodeType lastNodeType = getNodeType(lastNode); NodeType lastNodeType = _getNodeType(lastNode);
// Create an array for newly created nodes. // Create an array for newly created nodes.
// We need up to three new nodes, depending on the contents of the last node. // We need up to three new nodes, depending on the contents of the last node.
...@@ -403,13 +403,13 @@ library Lib_MerkleTrie { ...@@ -403,13 +403,13 @@ library Lib_MerkleTrie {
if (keyRemainder.length == 0 && lastNodeType == NodeType.LeafNode) { if (keyRemainder.length == 0 && lastNodeType == NodeType.LeafNode) {
// We've found a leaf node with the given key. // We've found a leaf node with the given key.
// Simply need to update the value of the node to match. // Simply need to update the value of the node to match.
newNodes[totalNewNodes] = makeLeafNode(getNodeKey(lastNode), _value); newNodes[totalNewNodes] = _makeLeafNode(_getNodeKey(lastNode), _value);
totalNewNodes += 1; totalNewNodes += 1;
} else if (lastNodeType == NodeType.BranchNode) { } else if (lastNodeType == NodeType.BranchNode) {
if (keyRemainder.length == 0) { if (keyRemainder.length == 0) {
// We've found a branch node with the given key. // We've found a branch node with the given key.
// Simply need to update the value of the node to match. // Simply need to update the value of the node to match.
newNodes[totalNewNodes] = editBranchValue(lastNode, _value); newNodes[totalNewNodes] = _editBranchValue(lastNode, _value);
totalNewNodes += 1; totalNewNodes += 1;
} else { } else {
// We've found a branch node, but it doesn't contain our key. // We've found a branch node, but it doesn't contain our key.
...@@ -418,19 +418,19 @@ library Lib_MerkleTrie { ...@@ -418,19 +418,19 @@ library Lib_MerkleTrie {
totalNewNodes += 1; totalNewNodes += 1;
// Create a new leaf node, slicing our remainder since the first byte points // Create a new leaf node, slicing our remainder since the first byte points
// to our branch node. // to our branch node.
newNodes[totalNewNodes] = makeLeafNode(Lib_ByteUtils.slice(keyRemainder, 1), _value); newNodes[totalNewNodes] = _makeLeafNode(Lib_ByteUtils.slice(keyRemainder, 1), _value);
totalNewNodes += 1; totalNewNodes += 1;
} }
} else { } else {
// Our last node is either an extension node or a leaf node with a different key. // Our last node is either an extension node or a leaf node with a different key.
bytes memory lastNodeKey = getNodeKey(lastNode); bytes memory lastNodeKey = _getNodeKey(lastNode);
uint256 sharedNibbleLength = getSharedNibbleLength(lastNodeKey, keyRemainder); uint256 sharedNibbleLength = _getSharedNibbleLength(lastNodeKey, keyRemainder);
if (sharedNibbleLength != 0) { if (sharedNibbleLength != 0) {
// We've got some shared nibbles between the last node and our key remainder. // We've got some shared nibbles between the last node and our key remainder.
// We'll need to insert an extension node that covers these shared nibbles. // We'll need to insert an extension node that covers these shared nibbles.
bytes memory nextNodeKey = Lib_ByteUtils.slice(lastNodeKey, 0, sharedNibbleLength); bytes memory nextNodeKey = Lib_ByteUtils.slice(lastNodeKey, 0, sharedNibbleLength);
newNodes[totalNewNodes] = makeExtensionNode(nextNodeKey, getNodeHash(_value)); newNodes[totalNewNodes] = _makeExtensionNode(nextNodeKey, _getNodeHash(_value));
totalNewNodes += 1; totalNewNodes += 1;
// Cut down the keys since we've just covered these shared nibbles. // Cut down the keys since we've just covered these shared nibbles.
...@@ -439,13 +439,13 @@ library Lib_MerkleTrie { ...@@ -439,13 +439,13 @@ library Lib_MerkleTrie {
} }
// Create an empty branch to fill in. // Create an empty branch to fill in.
TrieNode memory newBranch = makeEmptyBranchNode(); TrieNode memory newBranch = _makeEmptyBranchNode();
if (lastNodeKey.length == 0) { if (lastNodeKey.length == 0) {
// Key remainder was larger than the key for our last node. // Key remainder was larger than the key for our last node.
// The value within our last node is therefore going to be shifted into // The value within our last node is therefore going to be shifted into
// a branch value slot. // a branch value slot.
newBranch = editBranchValue(newBranch, getNodeValue(lastNode)); newBranch = _editBranchValue(newBranch, _getNodeValue(lastNode));
} else { } else {
// Last node key was larger than the key remainder. // Last node key was larger than the key remainder.
// We're going to modify some index of our branch. // We're going to modify some index of our branch.
...@@ -456,25 +456,25 @@ library Lib_MerkleTrie { ...@@ -456,25 +456,25 @@ library Lib_MerkleTrie {
if (lastNodeType == NodeType.LeafNode) { if (lastNodeType == NodeType.LeafNode) {
// We're dealing with a leaf node. // We're dealing with a leaf node.
// We'll modify the key and insert the old leaf node into the branch index. // We'll modify the key and insert the old leaf node into the branch index.
TrieNode memory modifiedLastNode = makeLeafNode(lastNodeKey, getNodeValue(lastNode)); TrieNode memory modifiedLastNode = _makeLeafNode(lastNodeKey, _getNodeValue(lastNode));
newBranch = editBranchIndex(newBranch, branchKey, getNodeHash(modifiedLastNode.encoded)); newBranch = _editBranchIndex(newBranch, branchKey, _getNodeHash(modifiedLastNode.encoded));
} else if (lastNodeKey.length != 0) { } else if (lastNodeKey.length != 0) {
// We're dealing with a shrinking extension node. // We're dealing with a shrinking extension node.
// We need to modify the node to decrease the size of the key. // We need to modify the node to decrease the size of the key.
TrieNode memory modifiedLastNode = makeExtensionNode(lastNodeKey, getNodeValue(lastNode)); TrieNode memory modifiedLastNode = _makeExtensionNode(lastNodeKey, _getNodeValue(lastNode));
newBranch = editBranchIndex(newBranch, branchKey, getNodeHash(modifiedLastNode.encoded)); newBranch = _editBranchIndex(newBranch, branchKey, _getNodeHash(modifiedLastNode.encoded));
} else { } else {
// We're dealing with an unnecessary extension node. // We're dealing with an unnecessary extension node.
// We're going to delete the node entirely. // We're going to delete the node entirely.
// Simply insert its current value into the branch index. // Simply insert its current value into the branch index.
newBranch = editBranchIndex(newBranch, branchKey, getNodeValue(lastNode)); newBranch = _editBranchIndex(newBranch, branchKey, _getNodeValue(lastNode));
} }
} }
if (keyRemainder.length == 0) { if (keyRemainder.length == 0) {
// We've got nothing left in the key remainder. // We've got nothing left in the key remainder.
// Simply insert the value into the branch value slot. // Simply insert the value into the branch value slot.
newBranch = editBranchValue(newBranch, _value); newBranch = _editBranchValue(newBranch, _value);
// Push the branch into the list of new nodes. // Push the branch into the list of new nodes.
newNodes[totalNewNodes] = newBranch; newNodes[totalNewNodes] = newBranch;
totalNewNodes += 1; totalNewNodes += 1;
...@@ -487,14 +487,14 @@ library Lib_MerkleTrie { ...@@ -487,14 +487,14 @@ library Lib_MerkleTrie {
newNodes[totalNewNodes] = newBranch; newNodes[totalNewNodes] = newBranch;
totalNewNodes += 1; totalNewNodes += 1;
// Push a new leaf node for our k/v pair. // Push a new leaf node for our k/v pair.
newNodes[totalNewNodes] = makeLeafNode(keyRemainder, _value); newNodes[totalNewNodes] = _makeLeafNode(keyRemainder, _value);
totalNewNodes += 1; totalNewNodes += 1;
} }
} }
// Finally, join the old path with our newly created nodes. // Finally, join the old path with our newly created nodes.
// Since we're overwriting the last node in the path, we use `_pathLength - 1`. // Since we're overwriting the last node in the path, we use `_pathLength - 1`.
return joinNodeArrays(_path, _pathLength - 1, newNodes, totalNewNodes); return _joinNodeArrays(_path, _pathLength - 1, newNodes, totalNewNodes);
} }
/** /**
...@@ -503,7 +503,7 @@ library Lib_MerkleTrie { ...@@ -503,7 +503,7 @@ library Lib_MerkleTrie {
* @param _key Key for the k/v pair. * @param _key Key for the k/v pair.
* @return Root hash for the updated trie. * @return Root hash for the updated trie.
*/ */
function getUpdatedTrieRoot( function _getUpdatedTrieRoot(
TrieNode[] memory _nodes, TrieNode[] memory _nodes,
bytes memory _key bytes memory _key
) )
...@@ -524,23 +524,23 @@ library Lib_MerkleTrie { ...@@ -524,23 +524,23 @@ library Lib_MerkleTrie {
for (uint256 i = _nodes.length; i > 0; i--) { for (uint256 i = _nodes.length; i > 0; i--) {
// Pick out the current node. // Pick out the current node.
currentNode = _nodes[i - 1]; currentNode = _nodes[i - 1];
currentNodeType = getNodeType(currentNode); currentNodeType = _getNodeType(currentNode);
if (currentNodeType == NodeType.LeafNode) { if (currentNodeType == NodeType.LeafNode) {
// Leaf nodes are already correctly encoded. // Leaf nodes are already correctly encoded.
// Shift the key over to account for the nodes key. // Shift the key over to account for the nodes key.
bytes memory nodeKey = getNodeKey(currentNode); bytes memory nodeKey = _getNodeKey(currentNode);
key = Lib_ByteUtils.slice(key, 0, key.length - nodeKey.length); key = Lib_ByteUtils.slice(key, 0, key.length - nodeKey.length);
} else if (currentNodeType == NodeType.ExtensionNode) { } else if (currentNodeType == NodeType.ExtensionNode) {
// Shift the key over to account for the nodes key. // Shift the key over to account for the nodes key.
bytes memory nodeKey = getNodeKey(currentNode); bytes memory nodeKey = _getNodeKey(currentNode);
key = Lib_ByteUtils.slice(key, 0, key.length - nodeKey.length); key = Lib_ByteUtils.slice(key, 0, key.length - nodeKey.length);
// If this node is the last element in the path, it'll be correctly encoded // If this node is the last element in the path, it'll be correctly encoded
// and we can skip this part. // and we can skip this part.
if (previousNodeHash.length > 0) { if (previousNodeHash.length > 0) {
// Re-encode the node based on the previous node. // Re-encode the node based on the previous node.
currentNode = makeExtensionNode(nodeKey, previousNodeHash); currentNode = _makeExtensionNode(nodeKey, previousNodeHash);
} }
} else if (currentNodeType == NodeType.BranchNode) { } else if (currentNodeType == NodeType.BranchNode) {
// If this node is the last element in the path, it'll be correctly encoded // If this node is the last element in the path, it'll be correctly encoded
...@@ -549,12 +549,12 @@ library Lib_MerkleTrie { ...@@ -549,12 +549,12 @@ library Lib_MerkleTrie {
// Re-encode the node based on the previous node. // Re-encode the node based on the previous node.
uint8 branchKey = uint8(key[key.length - 1]); uint8 branchKey = uint8(key[key.length - 1]);
key = Lib_ByteUtils.slice(key, 0, key.length - 1); key = Lib_ByteUtils.slice(key, 0, key.length - 1);
currentNode = editBranchIndex(currentNode, branchKey, previousNodeHash); currentNode = _editBranchIndex(currentNode, branchKey, previousNodeHash);
} }
} }
// Compute the node hash for the next iteration. // Compute the node hash for the next iteration.
previousNodeHash = getNodeHash(currentNode.encoded); previousNodeHash = _getNodeHash(currentNode.encoded);
} }
// Current node should be the root at this point. // Current node should be the root at this point.
...@@ -567,7 +567,7 @@ library Lib_MerkleTrie { ...@@ -567,7 +567,7 @@ library Lib_MerkleTrie {
* @param _proof RLP-encoded proof to parse. * @param _proof RLP-encoded proof to parse.
* @return Proof parsed into easily accessible structs. * @return Proof parsed into easily accessible structs.
*/ */
function parseProof( function _parseProof(
bytes memory _proof bytes memory _proof
) )
private private
...@@ -597,7 +597,7 @@ library Lib_MerkleTrie { ...@@ -597,7 +597,7 @@ library Lib_MerkleTrie {
* @param _node Node to pull an ID for. * @param _node Node to pull an ID for.
* @return ID for the node, depending on the size of its contents. * @return ID for the node, depending on the size of its contents.
*/ */
function getNodeID( function _getNodeID(
Lib_RLPReader.RLPItem memory _node Lib_RLPReader.RLPItem memory _node
) )
private private
...@@ -624,7 +624,7 @@ library Lib_MerkleTrie { ...@@ -624,7 +624,7 @@ library Lib_MerkleTrie {
* @param _node Node to get a path for. * @param _node Node to get a path for.
* @return Node path, converted to an array of nibbles. * @return Node path, converted to an array of nibbles.
*/ */
function getNodePath( function _getNodePath(
TrieNode memory _node TrieNode memory _node
) )
private private
...@@ -642,7 +642,7 @@ library Lib_MerkleTrie { ...@@ -642,7 +642,7 @@ library Lib_MerkleTrie {
* @param _node Node to get a key for. * @param _node Node to get a key for.
* @return Node key, converted to an array of nibbles. * @return Node key, converted to an array of nibbles.
*/ */
function getNodeKey( function _getNodeKey(
TrieNode memory _node TrieNode memory _node
) )
private private
...@@ -651,7 +651,7 @@ library Lib_MerkleTrie { ...@@ -651,7 +651,7 @@ library Lib_MerkleTrie {
bytes memory bytes memory
) )
{ {
return removeHexPrefix(getNodePath(_node)); return _removeHexPrefix(_getNodePath(_node));
} }
/** /**
...@@ -659,7 +659,7 @@ library Lib_MerkleTrie { ...@@ -659,7 +659,7 @@ library Lib_MerkleTrie {
* @param _node Node to get a value for. * @param _node Node to get a value for.
* @return Node value, as hex bytes. * @return Node value, as hex bytes.
*/ */
function getNodeValue( function _getNodeValue(
TrieNode memory _node TrieNode memory _node
) )
private private
...@@ -677,11 +677,11 @@ library Lib_MerkleTrie { ...@@ -677,11 +677,11 @@ library Lib_MerkleTrie {
* @param _encoded Encoded node to hash. * @param _encoded Encoded node to hash.
* @return Hash of the encoded node. Simply the input if < 32 bytes. * @return Hash of the encoded node. Simply the input if < 32 bytes.
*/ */
function getNodeHash( function _getNodeHash(
bytes memory _encoded bytes memory _encoded
) )
private private
view pure
returns ( returns (
bytes memory bytes memory
) )
...@@ -698,7 +698,7 @@ library Lib_MerkleTrie { ...@@ -698,7 +698,7 @@ library Lib_MerkleTrie {
* @param _node Node to determine a type for. * @param _node Node to determine a type for.
* @return Type of the node; BranchNode/ExtensionNode/LeafNode. * @return Type of the node; BranchNode/ExtensionNode/LeafNode.
*/ */
function getNodeType( function _getNodeType(
TrieNode memory _node TrieNode memory _node
) )
private private
...@@ -710,7 +710,7 @@ library Lib_MerkleTrie { ...@@ -710,7 +710,7 @@ library Lib_MerkleTrie {
if (_node.decoded.length == BRANCH_NODE_LENGTH) { if (_node.decoded.length == BRANCH_NODE_LENGTH) {
return NodeType.BranchNode; return NodeType.BranchNode;
} else if (_node.decoded.length == LEAF_OR_EXTENSION_NODE_LENGTH) { } else if (_node.decoded.length == LEAF_OR_EXTENSION_NODE_LENGTH) {
bytes memory path = getNodePath(_node); bytes memory path = _getNodePath(_node);
uint8 prefix = uint8(path[0]); uint8 prefix = uint8(path[0]);
if (prefix == PREFIX_LEAF_EVEN || prefix == PREFIX_LEAF_ODD) { if (prefix == PREFIX_LEAF_EVEN || prefix == PREFIX_LEAF_ODD) {
...@@ -730,7 +730,7 @@ library Lib_MerkleTrie { ...@@ -730,7 +730,7 @@ library Lib_MerkleTrie {
* @param _b Second nibble array. * @param _b Second nibble array.
* @return Number of shared nibbles. * @return Number of shared nibbles.
*/ */
function getSharedNibbleLength( function _getSharedNibbleLength(
bytes memory _a, bytes memory _a,
bytes memory _b bytes memory _b
) )
...@@ -752,7 +752,7 @@ library Lib_MerkleTrie { ...@@ -752,7 +752,7 @@ library Lib_MerkleTrie {
* @param _raw RLP-encoded node to convert. * @param _raw RLP-encoded node to convert.
* @return Node as a TrieNode struct. * @return Node as a TrieNode struct.
*/ */
function makeNode( function _makeNode(
bytes[] memory _raw bytes[] memory _raw
) )
private private
...@@ -774,7 +774,7 @@ library Lib_MerkleTrie { ...@@ -774,7 +774,7 @@ library Lib_MerkleTrie {
* @param _items RLP-decoded node to convert. * @param _items RLP-decoded node to convert.
* @return Node as a TrieNode struct. * @return Node as a TrieNode struct.
*/ */
function makeNode( function _makeNode(
Lib_RLPReader.RLPItem[] memory _items Lib_RLPReader.RLPItem[] memory _items
) )
private private
...@@ -787,7 +787,7 @@ library Lib_MerkleTrie { ...@@ -787,7 +787,7 @@ library Lib_MerkleTrie {
for (uint256 i = 0; i < _items.length; i++) { for (uint256 i = 0; i < _items.length; i++) {
raw[i] = Lib_RLPReader.toRlpBytes(_items[i]); raw[i] = Lib_RLPReader.toRlpBytes(_items[i]);
} }
return makeNode(raw); return _makeNode(raw);
} }
/** /**
...@@ -796,7 +796,7 @@ library Lib_MerkleTrie { ...@@ -796,7 +796,7 @@ library Lib_MerkleTrie {
* @param _value Value for the extension node. * @param _value Value for the extension node.
* @return New extension node with the given k/v pair. * @return New extension node with the given k/v pair.
*/ */
function makeExtensionNode( function _makeExtensionNode(
bytes memory _key, bytes memory _key,
bytes memory _value bytes memory _value
) )
...@@ -807,22 +807,22 @@ library Lib_MerkleTrie { ...@@ -807,22 +807,22 @@ library Lib_MerkleTrie {
) )
{ {
bytes[] memory raw = new bytes[](2); bytes[] memory raw = new bytes[](2);
bytes memory key = addHexPrefix(_key, false); bytes memory key = _addHexPrefix(_key, false);
raw[0] = Lib_RLPWriter.encodeBytes(Lib_ByteUtils.fromNibbles(key)); raw[0] = Lib_RLPWriter.encodeBytes(Lib_ByteUtils.fromNibbles(key));
raw[1] = Lib_RLPWriter.encodeBytes(_value); raw[1] = Lib_RLPWriter.encodeBytes(_value);
return makeNode(raw); return _makeNode(raw);
} }
/** /**
* @notice Creates a new leaf node. * @notice Creates a new leaf node.
* @dev This function is essentially identical to `makeExtensionNode`. * @dev This function is essentially identical to `_makeExtensionNode`.
* Although we could route both to a single method with a flag, it's * Although we could route both to a single method with a flag, it's
* more gas efficient to keep them separate and duplicate the logic. * more gas efficient to keep them separate and duplicate the logic.
* @param _key Key for the leaf node, unprefixed. * @param _key Key for the leaf node, unprefixed.
* @param _value Value for the leaf node. * @param _value Value for the leaf node.
* @return New leaf node with the given k/v pair. * @return New leaf node with the given k/v pair.
*/ */
function makeLeafNode( function _makeLeafNode(
bytes memory _key, bytes memory _key,
bytes memory _value bytes memory _value
) )
...@@ -833,17 +833,17 @@ library Lib_MerkleTrie { ...@@ -833,17 +833,17 @@ library Lib_MerkleTrie {
) )
{ {
bytes[] memory raw = new bytes[](2); bytes[] memory raw = new bytes[](2);
bytes memory key = addHexPrefix(_key, true); bytes memory key = _addHexPrefix(_key, true);
raw[0] = Lib_RLPWriter.encodeBytes(Lib_ByteUtils.fromNibbles(key)); raw[0] = Lib_RLPWriter.encodeBytes(Lib_ByteUtils.fromNibbles(key));
raw[1] = Lib_RLPWriter.encodeBytes(_value); raw[1] = Lib_RLPWriter.encodeBytes(_value);
return makeNode(raw); return _makeNode(raw);
} }
/** /**
* @notice Creates an empty branch node. * @notice Creates an empty branch node.
* @return Empty branch node as a TrieNode stuct. * @return Empty branch node as a TrieNode stuct.
*/ */
function makeEmptyBranchNode() function _makeEmptyBranchNode()
private private
view view
returns ( returns (
...@@ -854,7 +854,7 @@ library Lib_MerkleTrie { ...@@ -854,7 +854,7 @@ library Lib_MerkleTrie {
for (uint256 i = 0; i < raw.length; i++) { for (uint256 i = 0; i < raw.length; i++) {
raw[i] = RLP_NULL_BYTES; raw[i] = RLP_NULL_BYTES;
} }
return makeNode(raw); return _makeNode(raw);
} }
/** /**
...@@ -863,7 +863,7 @@ library Lib_MerkleTrie { ...@@ -863,7 +863,7 @@ library Lib_MerkleTrie {
* @param _value Value to insert into the branch. * @param _value Value to insert into the branch.
* @return Modified branch node. * @return Modified branch node.
*/ */
function editBranchValue( function _editBranchValue(
TrieNode memory _branch, TrieNode memory _branch,
bytes memory _value bytes memory _value
) )
...@@ -875,7 +875,7 @@ library Lib_MerkleTrie { ...@@ -875,7 +875,7 @@ library Lib_MerkleTrie {
{ {
bytes memory encoded = Lib_RLPWriter.encodeBytes(_value); bytes memory encoded = Lib_RLPWriter.encodeBytes(_value);
_branch.decoded[_branch.decoded.length - 1] = Lib_RLPReader.toRlpItem(encoded); _branch.decoded[_branch.decoded.length - 1] = Lib_RLPReader.toRlpItem(encoded);
return makeNode(_branch.decoded); return _makeNode(_branch.decoded);
} }
/** /**
...@@ -885,7 +885,7 @@ library Lib_MerkleTrie { ...@@ -885,7 +885,7 @@ library Lib_MerkleTrie {
* @param _value Value to insert into the slot. * @param _value Value to insert into the slot.
* @return Modified branch node. * @return Modified branch node.
*/ */
function editBranchIndex( function _editBranchIndex(
TrieNode memory _branch, TrieNode memory _branch,
uint8 _index, uint8 _index,
bytes memory _value bytes memory _value
...@@ -898,7 +898,7 @@ library Lib_MerkleTrie { ...@@ -898,7 +898,7 @@ library Lib_MerkleTrie {
{ {
bytes memory encoded = _value.length < 32 ? _value : Lib_RLPWriter.encodeBytes(_value); bytes memory encoded = _value.length < 32 ? _value : Lib_RLPWriter.encodeBytes(_value);
_branch.decoded[_index] = Lib_RLPReader.toRlpItem(encoded); _branch.decoded[_index] = Lib_RLPReader.toRlpItem(encoded);
return makeNode(_branch.decoded); return _makeNode(_branch.decoded);
} }
/** /**
...@@ -907,7 +907,7 @@ library Lib_MerkleTrie { ...@@ -907,7 +907,7 @@ library Lib_MerkleTrie {
* @param _isLeaf Whether or not the key belongs to a leaf. * @param _isLeaf Whether or not the key belongs to a leaf.
* @return Prefixed key. * @return Prefixed key.
*/ */
function addHexPrefix( function _addHexPrefix(
bytes memory _key, bytes memory _key,
bool _isLeaf bool _isLeaf
) )
...@@ -929,7 +929,7 @@ library Lib_MerkleTrie { ...@@ -929,7 +929,7 @@ library Lib_MerkleTrie {
* @param _path Path to remove the prefix from. * @param _path Path to remove the prefix from.
* @return Unprefixed key. * @return Unprefixed key.
*/ */
function removeHexPrefix( function _removeHexPrefix(
bytes memory _path bytes memory _path
) )
private private
...@@ -955,14 +955,14 @@ library Lib_MerkleTrie { ...@@ -955,14 +955,14 @@ library Lib_MerkleTrie {
* @param _bLength Length of the second array. * @param _bLength Length of the second array.
* @return Combined node array. * @return Combined node array.
*/ */
function joinNodeArrays( function _joinNodeArrays(
TrieNode[] memory _a, TrieNode[] memory _a,
uint256 _aLength, uint256 _aLength,
TrieNode[] memory _b, TrieNode[] memory _b,
uint256 _bLength uint256 _bLength
) )
private private
view pure
returns ( returns (
TrieNode[] memory TrieNode[] memory
) )
......
import { expect } from '../../../setup'
describe('OVM_ECDSAContractAccount', () => {
describe('execute', () => {
describe('when provided an invalid signature', () => {
it('should revert', async () => {
})
})
describe('when provided a valid signature', () => {
describe('when provided an invalid nonce', () => {
it('should revert', async () => {
})
})
describe('when provided a valid nonce', () => {
describe('when executing ovmCREATE', () => {
it('should return the address of the created contract', async () => {
})
})
describe('when executing ovmCALL', () => {
it('should return the result of the call', async () => {
})
})
})
})
})
})
import { expect } from '../../../setup'
describe('OVM_StateTransitioner', () => {
describe('proveContractState', () => {
describe('when provided an invalid code hash', () => {
it('should revert', async () => {
})
})
describe('when provided a valid code hash', () => {
describe('when provided an invalid account inclusion proof', () => {
it('should revert', async () => {
})
})
describe('when provided a valid account inclusion proof', () => {
})
})
})
describe('proveStorageSlot', () => {
describe('when the corresponding account is not proven', () => {
it('should revert', async () => {
})
})
describe('when the corresponding account is proven', () => {
describe('when provided an invalid slot inclusion proof', () => {
it('should revert', async () => {
})
})
describe('when provided a valid slot inclusion proof', () => {
})
})
})
describe('applyTransaction', () => {
// TODO
})
describe('commitContractState', () => {
describe('when the account was not changed', () => {
it('should revert', async () => {
})
})
describe('when the account was changed', () => {
describe('when the account has not been committed', () => {
it('should commit the account and update the state', async () => {
})
})
describe('when the account was already committed', () => {
it('should revert', () => {
})
})
})
})
describe('commitStorageSlot', () => {
describe('when the slot was not changed', () => {
it('should revert', async () => {
})
})
describe('when the slot was changed', () => {
describe('when the slot has not been committed', () => {
it('should commit the slot and update the state', async () => {
})
})
describe('when the slot was already committed', () => {
it('should revert', () => {
})
})
})
})
describe('completeTransition', () => {
describe('when there are uncommitted accounts', () => {
it('should revert', async () => {
})
})
describe('when there are uncommitted storage slots', () => {
it('should revert', async () => {
})
})
describe('when all state changes are committed', () => {
})
})
})
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