Skip to content

Commit

Permalink
Merge pull request #562 from ralexstokes/remove-vyper-code
Browse files Browse the repository at this point in the history
Removes the source of the Vyper contract from the spec.
  • Loading branch information
djrtwo committed Feb 3, 2019
2 parents 2ac420c + 8755dc3 commit 3e2eb1c
Showing 1 changed file with 6 additions and 77 deletions.
83 changes: 6 additions & 77 deletions specs/core/0_beacon-chain.md
Original file line number Diff line number Diff line change
Expand Up @@ -1381,86 +1381,15 @@ When sufficiently many full deposits have been made the deposit contract emits t

### Vyper code

```python
## compiled with v0.1.0-beta.6 ##

MIN_DEPOSIT_AMOUNT: constant(uint256) = 1000000000 # Gwei
MAX_DEPOSIT_AMOUNT: constant(uint256) = 32000000000 # Gwei
GWEI_PER_ETH: constant(uint256) = 1000000000 # 10**9
CHAIN_START_FULL_DEPOSIT_THRESHOLD: constant(uint256) = 16384 # 2**14
DEPOSIT_CONTRACT_TREE_DEPTH: constant(uint256) = 32
TWO_TO_POWER_OF_TREE_DEPTH: constant(uint256) = 4294967296 # 2**32
SECONDS_PER_DAY: constant(uint256) = 86400

Deposit: event({deposit_root: bytes32, data: bytes[528], merkle_tree_index: bytes[8], branch: bytes32[32]})
ChainStart: event({deposit_root: bytes32, time: bytes[8]})

zerohashes: bytes32[32]
branch: bytes32[32]
deposit_count: uint256
full_deposit_count: uint256
chainStarted: public(bool)

@public
def __init__():
for i in range(31):
self.zerohashes[i+1] = sha3(concat(self.zerohashes[i], self.zerohashes[i]))
self.branch[i+1] = self.zerohashes[i+1]

@public
@constant
def get_deposit_root() -> bytes32:
root:bytes32 = 0x0000000000000000000000000000000000000000000000000000000000000000
size:uint256 = self.deposit_count
for h in range(32):
if size % 2 == 1:
root = sha3(concat(self.branch[h], root))
else:
root = sha3(concat(root, self.zerohashes[h]))
size /= 2
return root

@payable
@public
def deposit(deposit_input: bytes[512]):
assert msg.value >= as_wei_value(MIN_DEPOSIT_AMOUNT, "gwei")
assert msg.value <= as_wei_value(MAX_DEPOSIT_AMOUNT, "gwei")

index: uint256 = self.deposit_count
deposit_amount: bytes[8] = slice(concat("", convert(msg.value / GWEI_PER_ETH, bytes32)), start=24, len=8)
deposit_timestamp: bytes[8] = slice(concat("", convert(block.timestamp, bytes32)), start=24, len=8)
deposit_data: bytes[528] = concat(deposit_amount, deposit_timestamp, deposit_input)
merkle_tree_index: bytes[8] = slice(concat("", convert(index, bytes32)), start=24, len=8)

# add deposit to merkle tree
i: int128 = 0
power_of_two: uint256 = 2
for _ in range(32):
if (index+1) % power_of_two != 0:
break
i += 1
power_of_two *= 2
value:bytes32 = sha3(deposit_data)
for j in range(32):
if j < i:
value = sha3(concat(self.branch[j], value))
self.branch[i] = value

self.deposit_count += 1
The source for the Vyper contract lives in a [separate repository](https://github.com/ethereum/deposit_contract) at [https://github.com/ethereum/deposit_contract/blob/master/deposit_contract/contracts/validator_registration.v.py](https://github.com/ethereum/deposit_contract/blob/master/deposit_contract/contracts/validator_registration.v.py).

new_deposit_root:bytes32 = self.get_deposit_root()
log.Deposit(new_deposit_root, deposit_data, merkle_tree_index, self.branch)
Note: to save ~10x on gas this contract uses a somewhat unintuitive progressive Merkle root calculation algo that requires only O(log(n)) storage. See https://github.com/ethereum/research/blob/master/beacon_chain_impl/progressive_merkle_tree.py for an implementation of the same algo in python tested for correctness.

if msg.value == as_wei_value(MAX_DEPOSIT_AMOUNT, "gwei"):
self.full_deposit_count += 1
if self.full_deposit_count == CHAIN_START_FULL_DEPOSIT_THRESHOLD:
timestamp_day_boundary: uint256 = as_unitless_number(block.timestamp) - as_unitless_number(block.timestamp) % SECONDS_PER_DAY + SECONDS_PER_DAY
chainstart_time: bytes[8] = slice(concat("", convert(timestamp_day_boundary, bytes32)), start=24, len=8)
log.ChainStart(new_deposit_root, chainstart_time)
self.chainStarted = True
```
For convenience, we provide the interface to the contract here:

Note: to save ~10x on gas this contract uses a somewhat unintuitive progressive Merkle root calculation algo that requires only O(log(n)) storage. See https://github.com/ethereum/research/blob/master/beacon_chain_impl/progressive_merkle_tree.py for an implementation of the same algo in python tested for correctness.
* `__init__()`: initializes the contract
* `get_deposit_root() -> bytes32`: returns the current root of the deposit tree
* `deposit(bytes[512])`: adds a deposit instance to the deposit tree, incorporating the input argument and the value transferred in the given call. Note: the amount of value transferred *must* be within `MIN_DEPOSIT_AMOUNT` and `MAX_DEPOSIT_AMOUNT`, inclusive. Each of these constants are specified in units of Gwei.

## On startup

Expand Down

0 comments on commit 3e2eb1c

Please sign in to comment.