Ethereum Yellow Paper Deciphered | Part 5: Contract Creation
January 10, 2023
Note that this post is updated till the Shanghai version of the ethereum yellow paper.
This part of the series dives into section 7 of the Yellow Paper that describes the contract creation.
Contract Creation
Remember from the previous part we mentioned the contract creation function that took a bunch of parameters to execute the contract creation transaction execution. takes a total of 11 input parameters:
State before execution of (contract-creation) transaction, .
Accrued substate till before execution of transaction, .
Sender of the transaction denoted by . This is msg.sender global variable in Solidity.
Original transactor, the EOA which initiated the transaction, . This is tx.origin global variable in Solidity.
Available gas for the transaction execution, .
The effective gas price, that we saw in previous part.
Endowment value, sent along with this contract creation transaction.
The EVM initialization bytecode .
Present depth of contract-creation stack, .
Salt for deriving new contract's address, . was introduced with the CREATE2 opcode in EIP-1014. If contract is created with older CREATE opcode, is set to i.e. .
Permission to make modification to state, .
With above 11 input parameters, evaluates and outputs a tuple of 5 elements:
Next world state after this contract creation transaction, .
Remaining gas after the execution, .
The accrued substate after this execution, .
The result status (success or fail) of the transaction execution, .
The output bytes data as result of the execution of the transaction, .
can now be mathematically defined as:
where,
Contract Address
The address of a newly created contract is determined by only a few parameters involved in contract creation. These parameters are RLP-encoded by function and rightmost 20-bytes (160 bits) of the hash of this RLP-encoded structure is designated as address, of contract.
The way encodes the parameters depends on whether contract is created via CREATE () or CREATE2.
where is simply concatenation operator that concatenates the provided bytes data and is the nonce of sender account.
The output of is then hashed with keccak-256 and last 20-bytes are sliced. This is done by the function.
function simply slices off the last 20-bytes of 32-bytes result of hash function.
Now, we can formally define the address of newly-created contract as:
You might've noticed that we have given nonce (of sender account) parameter decreased by 1 () instead of simply as . Remember from previous part, Transaction Execution, at equivalence that we had already increased the nonce by 1, updating the state before proceeding for contract creation or message call execution. But expects the sender nonce at the latest finalized world state, which at the time of execution step is actually .
After this, the address of the new contract is added to set of accessed accounts in substate:
State Transition
The state transition in contract creation transaction happens step by step. We describe these steps below:
Step 1: Account Initialization
First step involves initialization of the new contract (account) at address . Changes in world state at transitions it to .
At this point, only account states of and (sender address) in the world state are modified. All else remains same, i.e.:
except, contract's state parameters are initialized as:
Nonce is set to 1.
Balance is set to sum of value (endowment) passed plus pre-existing value if contract at already exists.
Storage set to empty, .
Code hash set to hash of empty string, .
If you're wondering why code hash is empty - its because its just account initialization phase, we have not ran the EVM initialization code yet. That is done in next step.
Step 2: Init Code Execution
In this step we execute the initialization code passed, with EVM. This initialization can state parameters like it can set its storage and the body code of the contract, transitioning state from to .
This state transition happens via the code execution function .
is simply the parameters of execution:
After this initialization code execution, a code-deposit cost, is paid. is proportional to the created contract's code.
If the remaining gas after the code execution (using ) is not enough i.e. - an out-of-gas exception occurs.
If it was successful a new resultant state is reached - .
where is the gas left.
indicates any condition that led to failure of contract creation. is true (creation failed) if:
If account at address did not have empty state - it must have code hash as hash of empty string or nonce set to 0:
State at previous phase was empty and output code was empty:
Remaining gas was less than code-deposit gas required:
Output bytesize was greater than fixed limit of 24576 bytes: