mirror of
https://github.com/status-im/eth2.0-specs.git
synced 2025-02-10 01:34:29 +00:00
Merge pull request #3984 from mkalinin/epoch-processing-tests
electra: Epoch processing tests
This commit is contained in:
commit
b4311fe591
@ -792,23 +792,25 @@ def process_epoch(state: BeaconState) -> None:
|
|||||||
|
|
||||||
#### Modified `process_registry_updates`
|
#### Modified `process_registry_updates`
|
||||||
|
|
||||||
*Note*: The function `process_registry_updates` is modified to use the updated definition of `initiate_validator_exit`
|
*Note*: The function `process_registry_updates` is modified to
|
||||||
|
use the updated definitions of `initiate_validator_exit` and `is_eligible_for_activation_queue`
|
||||||
and changes how the activation epochs are computed for eligible validators.
|
and changes how the activation epochs are computed for eligible validators.
|
||||||
|
|
||||||
```python
|
```python
|
||||||
def process_registry_updates(state: BeaconState) -> None:
|
def process_registry_updates(state: BeaconState) -> None:
|
||||||
# Process activation eligibility and ejections
|
# Process activation eligibility and ejections
|
||||||
for index, validator in enumerate(state.validators):
|
for index, validator in enumerate(state.validators):
|
||||||
if is_eligible_for_activation_queue(validator):
|
if is_eligible_for_activation_queue(validator): # [Modified in Electra:EIP7251]
|
||||||
validator.activation_eligibility_epoch = get_current_epoch(state) + 1
|
validator.activation_eligibility_epoch = get_current_epoch(state) + 1
|
||||||
|
|
||||||
if (
|
if (
|
||||||
is_active_validator(validator, get_current_epoch(state))
|
is_active_validator(validator, get_current_epoch(state))
|
||||||
and validator.effective_balance <= EJECTION_BALANCE
|
and validator.effective_balance <= EJECTION_BALANCE
|
||||||
):
|
):
|
||||||
initiate_validator_exit(state, ValidatorIndex(index))
|
initiate_validator_exit(state, ValidatorIndex(index)) # [Modified in Electra:EIP7251]
|
||||||
|
|
||||||
# Activate all eligible validators
|
# Activate all eligible validators
|
||||||
|
# [Modified in Electra:EIP7251]
|
||||||
activation_epoch = compute_activation_exit_epoch(get_current_epoch(state))
|
activation_epoch = compute_activation_exit_epoch(get_current_epoch(state))
|
||||||
for validator in state.validators:
|
for validator in state.validators:
|
||||||
if is_eligible_for_activation(state, validator):
|
if is_eligible_for_activation(state, validator):
|
||||||
|
@ -23,6 +23,8 @@ def run_test_activation_churn_limit(spec, state):
|
|||||||
|
|
||||||
validator_count_0 = len(state.validators)
|
validator_count_0 = len(state.validators)
|
||||||
|
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE if is_post_electra(spec) else spec.MAX_EFFECTIVE_BALANCE
|
||||||
|
|
||||||
for i in range(mock_activations):
|
for i in range(mock_activations):
|
||||||
index = validator_count_0 + i
|
index = validator_count_0 + i
|
||||||
validator = spec.Validator(
|
validator = spec.Validator(
|
||||||
@ -32,10 +34,10 @@ def run_test_activation_churn_limit(spec, state):
|
|||||||
activation_epoch=spec.FAR_FUTURE_EPOCH,
|
activation_epoch=spec.FAR_FUTURE_EPOCH,
|
||||||
exit_epoch=spec.FAR_FUTURE_EPOCH,
|
exit_epoch=spec.FAR_FUTURE_EPOCH,
|
||||||
withdrawable_epoch=spec.FAR_FUTURE_EPOCH,
|
withdrawable_epoch=spec.FAR_FUTURE_EPOCH,
|
||||||
effective_balance=spec.MAX_EFFECTIVE_BALANCE,
|
effective_balance=balance,
|
||||||
)
|
)
|
||||||
state.validators.append(validator)
|
state.validators.append(validator)
|
||||||
state.balances.append(spec.MAX_EFFECTIVE_BALANCE)
|
state.balances.append(balance)
|
||||||
state.previous_epoch_participation.append(spec.ParticipationFlags(0b0000_0000))
|
state.previous_epoch_participation.append(spec.ParticipationFlags(0b0000_0000))
|
||||||
state.current_epoch_participation.append(spec.ParticipationFlags(0b0000_0000))
|
state.current_epoch_participation.append(spec.ParticipationFlags(0b0000_0000))
|
||||||
state.inactivity_scores.append(0)
|
state.inactivity_scores.append(0)
|
||||||
|
@ -2,6 +2,12 @@ from eth2spec.test.helpers.epoch_processing import run_epoch_processing_with
|
|||||||
from eth2spec.test.context import (
|
from eth2spec.test.context import (
|
||||||
spec_state_test,
|
spec_state_test,
|
||||||
with_electra_and_later,
|
with_electra_and_later,
|
||||||
|
with_presets,
|
||||||
|
spec_test,
|
||||||
|
single_phase,
|
||||||
|
with_custom_state,
|
||||||
|
scaled_churn_balances_exceed_activation_exit_churn_limit,
|
||||||
|
default_activation_threshold,
|
||||||
)
|
)
|
||||||
from eth2spec.test.helpers.deposits import prepare_pending_deposit
|
from eth2spec.test.helpers.deposits import prepare_pending_deposit
|
||||||
from eth2spec.test.helpers.state import (
|
from eth2spec.test.helpers.state import (
|
||||||
@ -9,6 +15,7 @@ from eth2spec.test.helpers.state import (
|
|||||||
advance_finality_to,
|
advance_finality_to,
|
||||||
set_full_participation,
|
set_full_participation,
|
||||||
)
|
)
|
||||||
|
from eth2spec.test.helpers.constants import MINIMAL
|
||||||
|
|
||||||
|
|
||||||
def run_process_pending_deposits(spec, state):
|
def run_process_pending_deposits(spec, state):
|
||||||
@ -488,3 +495,26 @@ def test_process_pending_deposits_withdrawable_validator_not_churned(spec, state
|
|||||||
assert state.pending_deposits == [
|
assert state.pending_deposits == [
|
||||||
prepare_pending_deposit(spec, validator_index=1, amount=amount)
|
prepare_pending_deposit(spec, validator_index=1, amount=amount)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@with_presets([MINIMAL], "need sufficient consolidation churn limit")
|
||||||
|
@with_custom_state(
|
||||||
|
balances_fn=scaled_churn_balances_exceed_activation_exit_churn_limit,
|
||||||
|
threshold_fn=default_activation_threshold,
|
||||||
|
)
|
||||||
|
@spec_test
|
||||||
|
@single_phase
|
||||||
|
def test_process_pending_deposits_scaled_churn(spec, state):
|
||||||
|
index = 0
|
||||||
|
amount = spec.get_activation_exit_churn_limit(state)
|
||||||
|
state.pending_deposits.append(
|
||||||
|
prepare_pending_deposit(spec, index, amount)
|
||||||
|
)
|
||||||
|
pre_balance = state.balances[index]
|
||||||
|
|
||||||
|
yield from run_process_pending_deposits(spec, state)
|
||||||
|
|
||||||
|
assert state.balances[index] == pre_balance + amount
|
||||||
|
assert state.deposit_balance_to_consume == 0
|
||||||
|
assert state.pending_deposits == []
|
||||||
|
@ -9,6 +9,10 @@ from eth2spec.test.context import (
|
|||||||
from eth2spec.test.helpers.state import (
|
from eth2spec.test.helpers.state import (
|
||||||
next_epoch_with_full_participation,
|
next_epoch_with_full_participation,
|
||||||
)
|
)
|
||||||
|
from eth2spec.test.helpers.withdrawals import (
|
||||||
|
set_eth1_withdrawal_credential_with_balance,
|
||||||
|
set_compounding_withdrawal_credential_with_balance,
|
||||||
|
)
|
||||||
|
|
||||||
# ***********************
|
# ***********************
|
||||||
# * CONSOLIDATION TESTS *
|
# * CONSOLIDATION TESTS *
|
||||||
@ -302,3 +306,131 @@ def test_pending_consolidation_with_pending_deposit(spec, state):
|
|||||||
# Pending deposit to the source was not processed.
|
# Pending deposit to the source was not processed.
|
||||||
# It should only be processed in the next epoch transition
|
# It should only be processed in the next epoch transition
|
||||||
assert state.pending_deposits == [pending_deposit]
|
assert state.pending_deposits == [pending_deposit]
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_pending_consolidation_source_balance_less_than_max_effective(spec, state):
|
||||||
|
current_epoch = spec.get_current_epoch(state)
|
||||||
|
source_index = spec.get_active_validator_indices(state, current_epoch)[0]
|
||||||
|
target_index = spec.get_active_validator_indices(state, current_epoch)[1]
|
||||||
|
# append pending consolidation
|
||||||
|
state.pending_consolidations.append(
|
||||||
|
spec.PendingConsolidation(source_index=source_index, target_index=target_index)
|
||||||
|
)
|
||||||
|
# Set withdrawable epoch to current epoch to allow processing
|
||||||
|
state.validators[source_index].withdrawable_epoch = current_epoch
|
||||||
|
# Set source and target withdrawal credential to eth1
|
||||||
|
set_eth1_withdrawal_credential_with_balance(spec, state, source_index)
|
||||||
|
set_eth1_withdrawal_credential_with_balance(spec, state, target_index)
|
||||||
|
# Set the source balance to be less than effective_balance
|
||||||
|
pre_balance_source = state.validators[source_index].effective_balance - spec.EFFECTIVE_BALANCE_INCREMENT // 8
|
||||||
|
state.balances[source_index] = pre_balance_source
|
||||||
|
|
||||||
|
pre_balance_target = state.balances[target_index]
|
||||||
|
|
||||||
|
assert state.balances[source_index] < spec.get_max_effective_balance(state.validators[source_index])
|
||||||
|
|
||||||
|
yield from run_epoch_processing_with(spec, state, "process_pending_consolidations")
|
||||||
|
|
||||||
|
# Pending consolidation was successfully processed
|
||||||
|
assert state.balances[target_index] == pre_balance_target + pre_balance_source
|
||||||
|
assert state.balances[source_index] == 0
|
||||||
|
assert state.pending_consolidations == []
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_pending_consolidation_source_balance_greater_than_max_effective(spec, state):
|
||||||
|
current_epoch = spec.get_current_epoch(state)
|
||||||
|
source_index = spec.get_active_validator_indices(state, current_epoch)[0]
|
||||||
|
target_index = spec.get_active_validator_indices(state, current_epoch)[1]
|
||||||
|
# append pending consolidation
|
||||||
|
state.pending_consolidations.append(
|
||||||
|
spec.PendingConsolidation(source_index=source_index, target_index=target_index)
|
||||||
|
)
|
||||||
|
# Set withdrawable epoch to current epoch to allow processing
|
||||||
|
state.validators[source_index].withdrawable_epoch = current_epoch
|
||||||
|
# Set source and target withdrawal credential to eth1
|
||||||
|
set_eth1_withdrawal_credential_with_balance(spec, state, source_index)
|
||||||
|
set_eth1_withdrawal_credential_with_balance(spec, state, target_index)
|
||||||
|
# Set the source balance to be greater than effective_balance
|
||||||
|
excess_source_balance = spec.EFFECTIVE_BALANCE_INCREMENT // 8
|
||||||
|
pre_balance_source = state.validators[source_index].effective_balance + excess_source_balance
|
||||||
|
state.balances[source_index] = pre_balance_source
|
||||||
|
|
||||||
|
pre_balance_target = state.balances[target_index]
|
||||||
|
|
||||||
|
source_max_effective_balance = spec.get_max_effective_balance(state.validators[source_index])
|
||||||
|
assert state.balances[source_index] > source_max_effective_balance
|
||||||
|
|
||||||
|
yield from run_epoch_processing_with(spec, state, "process_pending_consolidations")
|
||||||
|
|
||||||
|
# Pending consolidation was successfully processed
|
||||||
|
assert state.balances[target_index] == pre_balance_target + source_max_effective_balance
|
||||||
|
assert state.balances[source_index] == excess_source_balance
|
||||||
|
assert state.pending_consolidations == []
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_pending_consolidation_source_balance_less_than_max_effective_compounding(spec, state):
|
||||||
|
current_epoch = spec.get_current_epoch(state)
|
||||||
|
source_index = spec.get_active_validator_indices(state, current_epoch)[0]
|
||||||
|
target_index = spec.get_active_validator_indices(state, current_epoch)[1]
|
||||||
|
# append pending consolidation
|
||||||
|
state.pending_consolidations.append(
|
||||||
|
spec.PendingConsolidation(source_index=source_index, target_index=target_index)
|
||||||
|
)
|
||||||
|
# Set withdrawable epoch to current epoch to allow processing
|
||||||
|
state.validators[source_index].withdrawable_epoch = current_epoch
|
||||||
|
# Set source and target withdrawal credential to compounding
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, source_index)
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, target_index)
|
||||||
|
# Set the source balance to be less than effective_balance
|
||||||
|
pre_balance_source = state.validators[source_index].effective_balance - spec.EFFECTIVE_BALANCE_INCREMENT // 8
|
||||||
|
state.balances[source_index] = pre_balance_source
|
||||||
|
|
||||||
|
pre_balance_target = state.balances[target_index]
|
||||||
|
|
||||||
|
assert state.balances[source_index] < spec.get_max_effective_balance(state.validators[source_index])
|
||||||
|
|
||||||
|
yield from run_epoch_processing_with(spec, state, "process_pending_consolidations")
|
||||||
|
|
||||||
|
# Pending consolidation was successfully processed
|
||||||
|
assert state.balances[target_index] == pre_balance_target + pre_balance_source
|
||||||
|
assert state.balances[source_index] == 0
|
||||||
|
assert state.pending_consolidations == []
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_pending_consolidation_source_balance_greater_than_max_effective_compounding(spec, state):
|
||||||
|
current_epoch = spec.get_current_epoch(state)
|
||||||
|
source_index = spec.get_active_validator_indices(state, current_epoch)[0]
|
||||||
|
target_index = spec.get_active_validator_indices(state, current_epoch)[1]
|
||||||
|
# append pending consolidation
|
||||||
|
state.pending_consolidations.append(
|
||||||
|
spec.PendingConsolidation(source_index=source_index, target_index=target_index)
|
||||||
|
)
|
||||||
|
# Set withdrawable epoch to current epoch to allow processing
|
||||||
|
state.validators[source_index].withdrawable_epoch = current_epoch
|
||||||
|
# Set source and target withdrawal credential to compounding
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, source_index)
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, target_index)
|
||||||
|
# Set the source balance to be greater than effective_balance
|
||||||
|
excess_source_balance = spec.EFFECTIVE_BALANCE_INCREMENT // 8
|
||||||
|
pre_balance_source = state.validators[source_index].effective_balance + excess_source_balance
|
||||||
|
state.balances[source_index] = pre_balance_source
|
||||||
|
|
||||||
|
pre_balance_target = state.balances[target_index]
|
||||||
|
|
||||||
|
source_max_effective_balance = spec.get_max_effective_balance(state.validators[source_index])
|
||||||
|
assert state.balances[source_index] > source_max_effective_balance
|
||||||
|
|
||||||
|
yield from run_epoch_processing_with(spec, state, "process_pending_consolidations")
|
||||||
|
|
||||||
|
# Pending consolidation was successfully processed
|
||||||
|
assert state.balances[target_index] == pre_balance_target + source_max_effective_balance
|
||||||
|
assert state.balances[source_index] == excess_source_balance
|
||||||
|
assert state.pending_consolidations == []
|
||||||
|
@ -0,0 +1,72 @@
|
|||||||
|
from eth2spec.test.helpers.deposits import mock_deposit
|
||||||
|
from eth2spec.test.helpers.state import next_epoch
|
||||||
|
from eth2spec.test.context import spec_state_test, with_electra_and_later
|
||||||
|
from eth2spec.test.helpers.epoch_processing import run_epoch_processing_with
|
||||||
|
from eth2spec.test.helpers.withdrawals import (
|
||||||
|
set_eth1_withdrawal_credential_with_balance,
|
||||||
|
set_compounding_withdrawal_credential_with_balance
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def run_test_activation_queue_eligibility(spec, state, validator_index, balance):
|
||||||
|
# move past first two irregular epochs wrt finality
|
||||||
|
next_epoch(spec, state)
|
||||||
|
next_epoch(spec, state)
|
||||||
|
|
||||||
|
state.balances[validator_index] = balance
|
||||||
|
state.validators[validator_index].effective_balance = balance
|
||||||
|
|
||||||
|
# ready for entrance into activation queue
|
||||||
|
mock_deposit(spec, state, validator_index)
|
||||||
|
|
||||||
|
yield from run_epoch_processing_with(spec, state, 'process_registry_updates')
|
||||||
|
|
||||||
|
# validator moved into activation queue if eligible
|
||||||
|
validator = state.validators[validator_index]
|
||||||
|
if validator.effective_balance < spec.MIN_ACTIVATION_BALANCE:
|
||||||
|
assert validator.activation_eligibility_epoch == spec.FAR_FUTURE_EPOCH
|
||||||
|
else:
|
||||||
|
assert validator.activation_eligibility_epoch < spec.FAR_FUTURE_EPOCH
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_activation_queue_eligibility__less_than_min_activation_balance(spec, state):
|
||||||
|
index = 3
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE - spec.EFFECTIVE_BALANCE_INCREMENT
|
||||||
|
yield from run_test_activation_queue_eligibility(spec, state, index, balance)
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_activation_queue_eligibility__min_activation_balance(spec, state):
|
||||||
|
index = 5
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE
|
||||||
|
yield from run_test_activation_queue_eligibility(spec, state, index, balance)
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_activation_queue_eligibility__min_activation_balance_eth1_creds(spec, state):
|
||||||
|
index = 7
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE
|
||||||
|
set_eth1_withdrawal_credential_with_balance(spec, state, index)
|
||||||
|
yield from run_test_activation_queue_eligibility(spec, state, index, balance)
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_activation_queue_eligibility__min_activation_balance_compounding_creds(spec, state):
|
||||||
|
index = 11
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, index)
|
||||||
|
yield from run_test_activation_queue_eligibility(spec, state, index, balance)
|
||||||
|
|
||||||
|
|
||||||
|
@with_electra_and_later
|
||||||
|
@spec_state_test
|
||||||
|
def test_activation_queue_eligibility__greater_than_min_activation_balance(spec, state):
|
||||||
|
index = 13
|
||||||
|
balance = spec.MIN_ACTIVATION_BALANCE + spec.EFFECTIVE_BALANCE_INCREMENT
|
||||||
|
set_compounding_withdrawal_credential_with_balance(spec, state, index)
|
||||||
|
yield from run_test_activation_queue_eligibility(spec, state, index, balance)
|
@ -40,6 +40,7 @@ if __name__ == "__main__":
|
|||||||
_new_electra_mods_1 = {key: 'eth2spec.test.electra.epoch_processing.test_process_' + key for key in [
|
_new_electra_mods_1 = {key: 'eth2spec.test.electra.epoch_processing.test_process_' + key for key in [
|
||||||
'effective_balance_updates',
|
'effective_balance_updates',
|
||||||
'pending_consolidations',
|
'pending_consolidations',
|
||||||
|
'registry_updates',
|
||||||
]}
|
]}
|
||||||
# This is a trick to allow tests be split into multiple files and use the same test format.
|
# This is a trick to allow tests be split into multiple files and use the same test format.
|
||||||
_new_electra_mods_2 = {key: 'eth2spec.test.electra.epoch_processing.' + key for key in [
|
_new_electra_mods_2 = {key: 'eth2spec.test.electra.epoch_processing.' + key for key in [
|
||||||
|
Loading…
x
Reference in New Issue
Block a user