From c443db01bf43ef733e409ed9edb646e790d9e7db Mon Sep 17 00:00:00 2001 From: terence tsao Date: Tue, 19 Nov 2024 07:46:32 -0800 Subject: [PATCH] Add get attester head --- specs/_features/eip7805/beacon-chain.md | 18 ---------- specs/_features/eip7805/fork-choice.md | 38 +++++++++++++++++++++ specs/_features/eip7805/validator.md | 44 ++++++++++++++++++++----- 3 files changed, 73 insertions(+), 27 deletions(-) diff --git a/specs/_features/eip7805/beacon-chain.md b/specs/_features/eip7805/beacon-chain.md index f128bab7b2..a6b4c3a915 100644 --- a/specs/_features/eip7805/beacon-chain.md +++ b/specs/_features/eip7805/beacon-chain.md @@ -24,7 +24,6 @@ - [Request data](#request-data) - [Modified `NewPayloadRequest`](#modified-newpayloadrequest) - [Engine APIs](#engine-apis) - - [Modified `notify_new_payload`](#modified-notify_new_payload) - [Modified `verify_and_notify_new_payload`](#modified-verify_and_notify_new_payload) @@ -132,23 +131,6 @@ class NewPayloadRequest(object): #### Engine APIs -##### Modified `notify_new_payload` - -*Note*: The function `notify_new_payload` is modified to include the additional `il_transactions` parameter in EIP-7805. - -```python -def notify_new_payload(self: ExecutionEngine, - execution_payload: ExecutionPayload, - execution_requests: ExecutionRequests, - parent_beacon_block_root: Root, - il_transactions: List[Transaction, MAX_TRANSACTIONS_PER_INCLUSION_LIST] ) -> bool: - """ - Return ``True`` if and only if ``execution_payload`` and ``execution_requests`` - are valid with respect to ``self.execution_state``. - """ - ... -``` - ##### Modified `verify_and_notify_new_payload` *Note*: The function `verify_and_notify_new_payload` is modified to pass the additional parameter `il_transactions` diff --git a/specs/_features/eip7805/fork-choice.md b/specs/_features/eip7805/fork-choice.md index 8ffb738849..065a84e886 100644 --- a/specs/_features/eip7805/fork-choice.md +++ b/specs/_features/eip7805/fork-choice.md @@ -6,9 +6,13 @@ - [Introduction](#introduction) +- [Configuration](#configuration) - [Helpers](#helpers) - [New `validate_inclusion_lists`](#new-validate_inclusion_lists) - [Modified `Store`](#modified-store) + - [Modified `notify_new_payload`](#modified-notify_new_payload) + - [`get_attester_head`](#get_attester_head) + - [New `on_inclusion_list`](#new-on_inclusion_list) @@ -60,6 +64,40 @@ class Store(object): unrealized_justifications: Dict[Root, Checkpoint] = field(default_factory=dict) inclusion_lists: Dict[Tuple[Slot, Root], List[InclusionList]] = field(default_factory=dict) # [New in EIP-7805] inclusion_list_equivocators: Dict[Tuple[Slot, Root], Set[ValidatorIndex]] = field(default_factory=dict) # [New in EIP-7805] + unsatisfied_inclusion_list_blocks: Set[Root] # [New in EIP-7805] +``` + +##### Modified `notify_new_payload` + +*Note*: The function `notify_new_payload` is modified to include the additional `il_transactions` parameter in EIP-7805. + +```python +def notify_new_payload(self: ExecutionEngine, + execution_payload: ExecutionPayload, + execution_requests: ExecutionRequests, + parent_beacon_block_root: Root, + il_transactions: List[Transaction, MAX_TRANSACTIONS_PER_INCLUSION_LIST], + store: Store) -> bool: + """ + Return ``True`` if and only if ``execution_payload`` and ``execution_requests`` + are valid with respect to ``self.execution_state``. + """ + + # If execution client returns block does not satisfy inclusion list transactions, cache the block + store.unsatisfied_inclusion_list_blocks.add(execution_payload.block_root) + ... +``` + +##### `get_attester_head` + +```python +def get_attester_head(store: Store, head_root: Root) -> Root: + head_block = store.blocks[head_root] + + if head_root in store.unsatisfied_inclusion_list_blocks: + return head_block.parent_root + return head_root + ``` ### New `on_inclusion_list` diff --git a/specs/_features/eip7805/validator.md b/specs/_features/eip7805/validator.md index c857936ee0..b71d3e44ee 100644 --- a/specs/_features/eip7805/validator.md +++ b/specs/_features/eip7805/validator.md @@ -19,6 +19,9 @@ - [New inclusion list committee duty](#new-inclusion-list-committee-duty) - [Constructing a signed inclusion list](#constructing-a-signed-inclusion-list) - [Modified attester duty](#modified-attester-duty) + - [Modified LMD GHOST vote](#modified-lmd-ghost-vote) +- [Modified sync committee duty](#modified-sync-committee-duty) + - [Modified beacon block root](#modified-beacon-block-root) @@ -51,12 +54,12 @@ The body of these function is implementation dependent. The Engine API may be us ## New inclusion list committee assignment -A validator may be a member of the new Inclusion List Committee (ILC) for a given slot. To check for ILC assignments the validator uses the helper `get_ilc_assignment(state, epoch, validator_index)` where `epoch <= next_epoch`. +A validator may be a member of the new Inclusion List Committee (ILC) for a given slot. To check for ILC assignments the validator uses the helper `get_inclusion_committee_assignment(state, epoch, validator_index)` where `epoch <= next_epoch`. -ILC selection is only stable within the context of the current and next epoch. +Inclusion list committee selection is only stable within the context of the current and next epoch. ```python -def get_ilc_assignment( +def get_inclusion_committee_assignment( state: BeaconState, epoch: Epoch, validator_index: ValidatorIndex) -> Optional[Slot]: @@ -76,7 +79,7 @@ def get_ilc_assignment( ### Lookahead -`get_ilc_assignment` should be called at the start of each epoch to get the assignment for the next epoch (`current_epoch + 1`). A validator should plan for future assignments by noting their assigned ILC slot. +`get_inclusion_committee_assignment` should be called at the start of each epoch to get the assignment for the next epoch (`current_epoch + 1`). A validator should plan for future assignments by noting their assigned ILC slot. ## New proposer duty @@ -91,7 +94,7 @@ The proposer should call `engine_updateInclusionListV1` at `PROPOSER_INCLUSION_L ## New inclusion list committee duty -Some validators are selected to submit signed inclusion list. Validators should call `get_ilc_assignment` at the beginning of an epoch to be prepared to submit their inclusion list during the next epoch. +Some validators are selected to submit signed inclusion list. Validators should call `get_inclusion_committee_assignment` at the beginning of an epoch to be prepared to submit their inclusion list during the next epoch. A validator should create and broadcast the `signed_inclusion_list` to the global `inclusion_list` subnet by `PROPOSER_INCLUSION_LIST_CUT_OFF` seconds into the slot, unless a block for the current slot has been processed and is the head of the chain and broadcast to the network. @@ -99,10 +102,9 @@ A validator should create and broadcast the `signed_inclusion_list` to the globa The validator creates the `signed_inclusion_list` as follows: - First, the validator creates the `inclusion_list`. -- Set `inclusion_list.slot` to the assigned slot returned by `get_ilc_assignment`. +- Set `inclusion_list.slot` to the assigned slot returned by `get_inclusion_committee_assignment`. - Set `inclusion_list.validator_index` to the validator's index. -- Set `inclusion_list.parent_hash` to the block hash of the fork choice head. -- Set `inclusion_list.parent_root` to the block root of the fork choice head. +- Set `inclusion_list.inclusion_list_committee_root` to the hash tree root of the committee that the validator is a member of. - Set `inclusion_list.transactions` using the response from `engine_getInclusionListV1` from the execution layer client. - Sign the `inclusion_list` using the helper `get_inclusion_list_signature` and obtain the `signature`. - Set `signed_inclusion_list.message` to `inclusion_list`. @@ -118,4 +120,28 @@ def get_inclusion_list_signature( ## Modified attester duty -Attesters should not vote for the head block if `validate_inclusion_lists` of the head block returns false. \ No newline at end of file +#### Modified LMD GHOST vote + +Set `attestation_data.beacon_block_root = get_attester_head(store, head_root)`. + +## Modified sync committee duty + +#### Modified beacon block root + +```python +def get_sync_committee_message(state: BeaconState, + block_root: Root, + validator_index: ValidatorIndex, + privkey: int) -> SyncCommitteeMessage: + epoch = get_current_epoch(state) + domain = get_domain(state, DOMAIN_SYNC_COMMITTEE, epoch) + signing_root = compute_signing_root(block_root, domain) + signature = bls.Sign(privkey, signing_root) + + return SyncCommitteeMessage( + slot=state.slot, + beacon_block_root=get_attester_head(store, block_root), + validator_index=validator_index, + signature=signature, + ) +```