mirror of https://github.com/status-im/EIPs.git
Merge pull request #1702 from sorpaas/sp-account-versioining
EIP-1702: Generalized Account Versioning Scheme
This commit is contained in:
commit
29f9e1842e
|
@ -0,0 +1,129 @@
|
||||||
|
---
|
||||||
|
eip: 1702
|
||||||
|
title: Generalized Account Versioning Scheme
|
||||||
|
author: Wei Tang (@sorpaas)
|
||||||
|
discussions-to: https://github.com/sorpaas/EIPs/issues/2
|
||||||
|
status: Draft
|
||||||
|
type: Standards Track
|
||||||
|
category: Core
|
||||||
|
created: 2017-12-30
|
||||||
|
---
|
||||||
|
|
||||||
|
## Abstract
|
||||||
|
|
||||||
|
This defines a method of hard forking while maintaining the exact
|
||||||
|
functionality of existing account by allowing multiple versions of the
|
||||||
|
virtual machines to execute in the same block. This is also useful to
|
||||||
|
define future account state structures when we introduce the on-chain
|
||||||
|
WebAssembly virtual machine.
|
||||||
|
|
||||||
|
## Motivation
|
||||||
|
|
||||||
|
By allowing account versioning, we can execute different virtual
|
||||||
|
machine for contracts created at different times. This allows breaking
|
||||||
|
features to be implemented while making sure existing contracts work
|
||||||
|
as expected.
|
||||||
|
|
||||||
|
Note that this specification might not apply to all hard forks. We
|
||||||
|
have emergency hard forks in the past due to network attacks. Whether
|
||||||
|
they should maintain existing account compatibility should be
|
||||||
|
evaluated in individual basis. If the attack can only be executed once
|
||||||
|
against some particular contracts, then the scheme defined here might
|
||||||
|
still be applicable. Otherwise, having a plain emergency hard fork
|
||||||
|
might still be a good idea.
|
||||||
|
|
||||||
|
## Specification
|
||||||
|
|
||||||
|
### Account State
|
||||||
|
|
||||||
|
Re-define account state stored in the world state trie to have 5
|
||||||
|
items: `nonce`, `balance`, `storageRoot`, `codeHash`, and
|
||||||
|
`version`. The newly added field `version` is a 256-bit integer. When
|
||||||
|
`version` is zero, the account is RLP-encoded with the first 4
|
||||||
|
items. When `version` is not zero, the account is RLP-encoded with 5
|
||||||
|
items.
|
||||||
|
|
||||||
|
### Contract Deployment
|
||||||
|
|
||||||
|
In Ethereum, a contract has a deployment method, either by a contract
|
||||||
|
creation transaction, or by another contract. If we regard this
|
||||||
|
deployment method a contract's *parent*, then we find them forming a
|
||||||
|
family of contracts, with the *root* being a contract creation
|
||||||
|
transaction.
|
||||||
|
|
||||||
|
We let a family of contracts to always have the same `version`. That
|
||||||
|
is, `CREATE` and `CREATE2` will always deploy contract that has the
|
||||||
|
same `version` as the calling `address`.
|
||||||
|
|
||||||
|
### Validation
|
||||||
|
|
||||||
|
A new phrase, *validation* is added to contract deployment (by
|
||||||
|
`CREATE` / `CREATE2` opcodes, or by contract creation
|
||||||
|
transaction). When `version` is `0`, the phrase does nothing and
|
||||||
|
always succeeds. Future VM versions can define additional validation
|
||||||
|
that has to be passed.
|
||||||
|
|
||||||
|
If the validation phrase fails, deployment does not proceed and return
|
||||||
|
out-of-gas.
|
||||||
|
|
||||||
|
### Contract Execution
|
||||||
|
|
||||||
|
VM version used in contract execution is determined via calling
|
||||||
|
`address` (`I_a` in yellow paper). Precompiled contract does not have
|
||||||
|
version.
|
||||||
|
|
||||||
|
### Contract Creation Transaction
|
||||||
|
|
||||||
|
Define `LATEST_VERSION` in a hard fork to be the latest supported VM
|
||||||
|
version. A contract creation transaction is always executed in
|
||||||
|
`LATEST_VERSION`. Before a contract creation transaction is executed,
|
||||||
|
run *validation* on the contract creation code. If it does not pass,
|
||||||
|
return out-of-gas.
|
||||||
|
|
||||||
|
#### Alternative Design for Contract Creation Transaction
|
||||||
|
|
||||||
|
This provides an alternative design that allows contract to be created
|
||||||
|
in multiple versions.
|
||||||
|
|
||||||
|
Add an additional field `version` (256-bit integer) in contract
|
||||||
|
creation transaction. So it becomes `nonce`, `gasprice`, `startgas`,
|
||||||
|
`to`, `value`, `data`, `v`, `r`, `s`, `version`. When signing or
|
||||||
|
recovering, sign ten items, with `v`, `r`, `s` as defined by EIP-155.
|
||||||
|
|
||||||
|
The transaction would be executed in `version` supplied. If `version`
|
||||||
|
is not supported or *validation* does not pass, return out-of-gas.
|
||||||
|
|
||||||
|
## Discussions
|
||||||
|
|
||||||
|
### Performance
|
||||||
|
|
||||||
|
Currently nearly all full node implementations uses config parameters
|
||||||
|
to decide which virtual machine version to use. Switching vitual
|
||||||
|
machine version is simply an operation that changes a pointer using a
|
||||||
|
different set of config parameters. As a result, this scheme has
|
||||||
|
nearly zero impact to performance.
|
||||||
|
|
||||||
|
### Smart Contract Boundary and Formal Verification
|
||||||
|
|
||||||
|
Many current efforts are on-going for getting smart contracts formally
|
||||||
|
verified. However, for any hard fork that introduces new opcodes or
|
||||||
|
change behaviors of existing opcodes would break the verification of
|
||||||
|
an existing contract has previously be formally verified. Using the
|
||||||
|
scheme described here, we define the boundary of how a smart contract
|
||||||
|
interacts with the blockchain and it might help the formal
|
||||||
|
verification efforts:
|
||||||
|
|
||||||
|
* A smart contract has only immutable access to information of
|
||||||
|
blockchain account balances and codes.
|
||||||
|
* A smart contract has only immutable access of block information.
|
||||||
|
* A smart contract or a contract creation transaction can modify only
|
||||||
|
its own storage and codes.
|
||||||
|
* A smart contract can only interact with the blockchain in a mutable
|
||||||
|
way using `CALL` or `CREATE`.
|
||||||
|
|
||||||
|
### WebAssembly
|
||||||
|
|
||||||
|
This scheme can also be helpful when we deploy on-chain WebAssembly
|
||||||
|
virtual machine. In that case, WASM contracts and EVM contracts can
|
||||||
|
co-exist and the execution boundary and interaction model are clearly
|
||||||
|
defined as above.
|
Loading…
Reference in New Issue