示例#1
0
def test_success_max_per_slot_in_queue(spec, state):
    prepare_withdrawals_queue(spec, state, spec.MAX_WITHDRAWALS_PER_PAYLOAD)

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)

    yield from run_withdrawals_processing(spec, state, execution_payload)
示例#2
0
def test_pending_shard_parent_block(spec, state):
    # Block N
    beacon_state = state.copy()
    transition_to_valid_shard_slot(spec, beacon_state)
    shard = 0
    shard_state = beacon_state.shard_states[shard]
    signed_shard_block_1 = build_shard_block(spec,
                                             beacon_state,
                                             shard,
                                             slot=beacon_state.slot,
                                             signed=True)
    _, _, _, _ = run_shard_blocks(spec, shard_state, signed_shard_block_1,
                                  beacon_state)

    # Block N+1
    next_slot(spec, beacon_state)
    signed_shard_block_2 = build_shard_block(spec,
                                             beacon_state,
                                             shard,
                                             slot=beacon_state.slot,
                                             shard_parent_state=shard_state,
                                             signed=True)

    assert signed_shard_block_2.message.shard_parent_root == shard_state.latest_block_root
    assert signed_shard_block_2.message.slot == signed_shard_block_1.message.slot + 1
    yield from run_shard_blocks(spec, shard_state, signed_shard_block_2,
                                beacon_state)
示例#3
0
def test_success_empty_queue(spec, state):
    assert len(state.withdrawals_queue) == 0

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)

    yield from run_withdrawals_processing(spec, state, execution_payload)
示例#4
0
def test_success_one_in_queue(spec, state):
    prepare_withdrawals_queue(spec, state, 1)

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)

    yield from run_withdrawals_processing(spec, state, execution_payload)
def test_on_attestation_inconsistent_target_and_head(spec, state):
    store = get_genesis_forkchoice_store(spec, state)
    spec.on_tick(store, store.time + 2 * spec.config.SECONDS_PER_SLOT * spec.SLOTS_PER_EPOCH)

    # Create chain 1 as empty chain between genesis and start of 1st epoch
    target_state_1 = state.copy()
    next_epoch(spec, target_state_1)

    # Create chain 2 with different block in chain from chain 1 from chain 1 from chain 1 from chain 1
    target_state_2 = state.copy()
    diff_block = build_empty_block_for_next_slot(spec, target_state_2)
    signed_diff_block = state_transition_and_sign_block(spec, target_state_2, diff_block)
    spec.on_block(store, signed_diff_block)
    next_epoch(spec, target_state_2)
    next_slot(spec, target_state_2)

    # Create and store block new head block on target state 1
    head_block = build_empty_block_for_next_slot(spec, target_state_1)
    signed_head_block = state_transition_and_sign_block(spec, target_state_1, head_block)
    spec.on_block(store, signed_head_block)

    # Attest to head of chain 1
    attestation = get_valid_attestation(spec, target_state_1, slot=head_block.slot, signed=False)
    epoch = spec.compute_epoch_at_slot(attestation.data.slot)

    # Set attestation target to be from chain 2
    attestation.data.target = spec.Checkpoint(epoch=epoch, root=spec.get_block_root(target_state_2, epoch))
    sign_attestation(spec, state, attestation)

    assert attestation.data.target.epoch == spec.GENESIS_EPOCH + 1
    assert spec.compute_epoch_at_slot(attestation.data.slot) == spec.GENESIS_EPOCH + 1
    assert spec.get_block_root(target_state_1, epoch) != attestation.data.target.root

    run_on_attestation(spec, state, store, attestation, False)
示例#6
0
def run_generated_randomized_test(spec, state, scenario):
    stats = _compute_statistics(scenario)
    if "setup" not in scenario:
        state_randomizer = _resolve_ref(scenario.get("state_randomizer", randomize_state))
        scenario["setup"] = _randomized_scenario_setup(state_randomizer)

    scenario_state = {}
    for mutation, validation in scenario["setup"]:
        additional_state = mutation(spec, state, stats)
        validation(spec, state)
        if additional_state:
            scenario_state.update(additional_state)

    yield "pre", state

    blocks = []
    for transition in scenario["transitions"]:
        epochs_to_skip = _iter_temporal(spec, transition["epochs_to_skip"])
        for _ in epochs_to_skip:
            next_epoch(spec, state)
        slots_to_skip = _iter_temporal(spec, transition["slots_to_skip"])
        for _ in slots_to_skip:
            next_slot(spec, state)

        block_producer = _resolve_ref(transition["block_producer"])
        block = block_producer(spec, state, blocks, scenario_state)
        if block:
            signed_block = state_transition_and_sign_block(spec, state, block)
            blocks.append(signed_block)

        validation = _resolve_ref(transition["validation"])
        assert validation(spec, state)

    yield "blocks", blocks
    yield "post", state
示例#7
0
def test_attestations_some_slashed(spec, state):
    attestations = []
    for slot in range(spec.SLOTS_PER_EPOCH + spec.MIN_ATTESTATION_INCLUSION_DELAY):
        # create an attestation for each slot in epoch
        if slot < spec.SLOTS_PER_EPOCH:
            attestation = get_valid_attestation(spec, state, signed=True)
            attestations.append(attestation)
        # fill each created slot in state after inclusion delay
        if slot - spec.MIN_ATTESTATION_INCLUSION_DELAY >= 0:
            include_att = attestations[slot - spec.MIN_ATTESTATION_INCLUSION_DELAY]
            add_attestations_to_state(spec, state, [include_att], state.slot)
        next_slot(spec, state)

    attesting_indices_before_slashings = list(spec.get_unslashed_attesting_indices(state, attestations))

    # Slash maximum amount of validators allowed per epoch.
    for i in range(spec.MIN_PER_EPOCH_CHURN_LIMIT):
        spec.slash_validator(state, attesting_indices_before_slashings[i])

    assert spec.compute_epoch_at_slot(state.slot) == spec.GENESIS_EPOCH + 1
    assert len(state.previous_epoch_attestations) == spec.SLOTS_PER_EPOCH

    pre_state = deepcopy(state)

    yield from run_process_rewards_and_penalties(spec, state)

    attesting_indices = spec.get_unslashed_attesting_indices(state, attestations)
    assert len(attesting_indices) > 0
    assert len(attesting_indices_before_slashings) - len(attesting_indices) == spec.MIN_PER_EPOCH_CHURN_LIMIT
    for index in range(len(pre_state.validators)):
        if index in attesting_indices:
            assert state.balances[index] > pre_state.balances[index]
        else:
            assert state.balances[index] < pre_state.balances[index]
示例#8
0
def prepare_state_with_full_attestations(spec, state, empty=False):
    # Go to start of next epoch to ensure can have full participation
    next_epoch(spec, state)

    start_slot = state.slot
    start_epoch = spec.get_current_epoch(state)
    next_epoch_start_slot = spec.compute_start_slot_at_epoch(start_epoch + 1)
    attestations = []
    for _ in range(spec.SLOTS_PER_EPOCH +
                   spec.MIN_ATTESTATION_INCLUSION_DELAY):
        # create an attestation for each index in each slot in epoch
        if state.slot < next_epoch_start_slot:
            for committee_index in range(
                    spec.get_committee_count_at_slot(state, state.slot)):
                attestation = get_valid_attestation(spec,
                                                    state,
                                                    index=committee_index,
                                                    empty=empty,
                                                    signed=True)
                attestations.append(attestation)
        # fill each created slot in state after inclusion delay
        if state.slot >= start_slot + spec.MIN_ATTESTATION_INCLUSION_DELAY:
            inclusion_slot = state.slot - spec.MIN_ATTESTATION_INCLUSION_DELAY
            include_attestations = [
                att for att in attestations if att.data.slot == inclusion_slot
            ]
            add_attestations_to_state(spec, state, include_attestations,
                                      state.slot)
        next_slot(spec, state)

    assert state.slot == next_epoch_start_slot + spec.MIN_ATTESTATION_INCLUSION_DELAY
    assert len(state.previous_epoch_attestations) == len(attestations)

    return attestations
def test_empty_aggregation_bits(spec, state):
    next_slot(spec, state)
    attestation = get_valid_attestation(spec, state, empty=True)
    next_slots(spec, state, spec.MIN_ATTESTATION_INCLUSION_DELAY)

    assert attestation.aggregation_bits == Bitlist[spec.MAX_VALIDATORS_PER_COMMITTEE](
        *([0b0] * len(attestation.aggregation_bits)))

    yield from run_attestation_processing(spec, state, attestation)
def test_success_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)

    yield from run_execution_payload_processing(spec, state, execution_payload)
def test_no_winning_root(spec, state):
    if not is_full_crosslink(spec, state):
        # Skip this test
        return

    state, shard, target_shard_slot = get_initial_env(spec,
                                                      state,
                                                      target_len_offset_slot=1)
    init_slot = state.slot

    # Create SignedShardBlock at init_slot
    shard_block = build_shard_block(spec,
                                    state,
                                    shard,
                                    slot=init_slot,
                                    body=get_sample_shard_block_body(
                                        spec, is_max=True),
                                    signed=True)

    # Transition state to target shard slot
    transition_to(spec, state, target_shard_slot)

    # Create a shard_transitions that would be included at beacon block `target_shard_slot + 1`
    shard_transitions = get_shard_transitions(spec, state,
                                              {shard: [shard_block]})
    shard_transition = shard_transitions[shard]
    committee_index = get_committee_index_of_shard(spec, state, state.slot,
                                                   shard)
    attestation = get_valid_attestation(
        spec,
        state,
        index=committee_index,
        shard_transition=shard_transition,
        # Decrease attested participants to 1/3 committee
        filter_participant_set=lambda committee: set(
            list(committee)[:len(committee) // 3]),
        signed=True,
        on_time=True,
    )

    next_slot(spec, state)

    _, _, _ = run_attestation_processing(spec, state, attestation)

    _, winning_roots = spec.get_shard_winning_roots(state, [attestation])
    assert len(winning_roots) == 0

    # No winning root, shard_transitions[shard] is empty
    shard_transitions = [spec.ShardTransition()] * spec.MAX_SHARDS
    pre_shard_states = state.shard_states.copy()
    yield from run_shard_transitions_processing(spec, state, shard_transitions,
                                                [attestation])

    for pending_attestation in state.current_epoch_attestations:
        assert bool(pending_attestation.crosslink_success) is False

    assert state.shard_states == pre_shard_states
def test_wrong_shard_transition_root(spec, state):
    if not is_full_crosslink(spec, state):
        # Skip this test
        return

    state, shard, target_shard_slot = get_initial_env(spec,
                                                      state,
                                                      target_len_offset_slot=1)
    init_slot = state.slot

    # Create SignedShardBlock at init_slot
    shard_block = build_shard_block(spec,
                                    state,
                                    shard,
                                    slot=init_slot,
                                    body=get_sample_shard_block_body(
                                        spec, is_max=True),
                                    signed=True)

    # Transition state to target shard slot
    transition_to(spec, state, target_shard_slot)

    # Create a shard_transitions that would be included at beacon block `target_shard_slot + 1`
    shard_transitions = get_shard_transitions(spec, state,
                                              {shard: [shard_block]})
    shard_transition = shard_transitions[shard]
    wrong_shard_transition = shard_transition.copy()
    wrong_shard_transition.shard_states[
        shard].gasprice = shard_transition.shard_states[shard].gasprice + 1
    committee_index = get_committee_index_of_shard(spec, state, state.slot,
                                                   shard)
    attestation = get_valid_attestation(
        spec,
        state,
        index=committee_index,
        shard_transition=wrong_shard_transition,
        signed=True,
        on_time=True,
    )
    attestations = [attestation]

    next_slot(spec, state)

    run_attestation_processing(spec, state, attestation)

    # Check if winning root != shard_transition.hash_tree_root()
    _, winning_roots = spec.get_shard_winning_roots(state, attestations)
    assert len(winning_roots) == 1
    shard_transition = shard_transitions[shard]
    assert winning_roots[0] != shard_transition.hash_tree_root()

    yield from run_shard_transitions_processing(spec,
                                                state,
                                                shard_transitions,
                                                attestations,
                                                valid=False)
示例#13
0
def test_bad_random_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.random = b'\x04' * 32

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False)
示例#14
0
def test_gaslimit_max_first_payload(spec, state):
    # pre-state
    state = build_state_with_incomplete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.gas_limit = uint64(2**64 - 1)

    yield from run_execution_payload_processing(spec, state, execution_payload)
示例#15
0
def test_bad_parent_hash_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.parent_hash = spec.Hash32()

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False)
示例#16
0
def test_bad_timestamp_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.timestamp = execution_payload.timestamp + 1

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False)
示例#17
0
def test_gasused_gaslimit_plus_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.gas_used = execution_payload.gas_limit + uint64(1)

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False)
示例#18
0
def test_bad_execution_regular_payload(spec, state):
    # completely valid payload, but execution itself fails (e.g. block exceeds gas limit)

    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False, execution_valid=False)
示例#19
0
def test_fail_incorrect_dequeue_amount(spec, state):
    prepare_withdrawals_queue(spec, state, 1)

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.withdrawals[0].amount += 1

    yield from run_withdrawals_processing(spec,
                                          state,
                                          execution_payload,
                                          valid=False)
示例#20
0
def test_fail_max_per_slot_in_queue_one_less_in_withdrawals(spec, state):
    prepare_withdrawals_queue(spec, state, spec.MAX_WITHDRAWALS_PER_PAYLOAD)

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.withdrawals = execution_payload.withdrawals[:-1]

    yield from run_withdrawals_processing(spec,
                                          state,
                                          execution_payload,
                                          valid=False)
示例#21
0
def test_gaslimit_minimum_minus_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)
    state.latest_execution_payload_header.gas_limit = spec.MIN_GAS_LIMIT

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.gas_limit = execution_payload.gas_limit - uint64(1)

    yield from run_execution_payload_processing(spec, state, execution_payload, valid=False)
示例#22
0
def test_fail_one_in_queue_none_in_withdrawals(spec, state):
    prepare_withdrawals_queue(spec, state, 1)

    next_slot(spec, state)
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.withdrawals = []

    yield from run_withdrawals_processing(spec,
                                          state,
                                          execution_payload,
                                          valid=False)
示例#23
0
def test_on_attestation_same_slot(spec, state):
    store = spec.get_genesis_store(state)
    time = 1 * spec.SECONDS_PER_SLOT
    spec.on_tick(store, time)

    block = build_empty_block_for_next_slot(spec, state, signed=True)

    spec.on_block(store, block)
    next_slot(spec, state)

    attestation = get_valid_attestation(spec, state, slot=block.slot)
    run_on_attestation(spec, state, store, attestation, False)
def test_proposer_slashed(spec, state):
    # use stub state to get proposer index of next slot
    stub_state = deepcopy(state)
    next_slot(spec, stub_state)
    proposer_index = spec.get_beacon_proposer_index(stub_state)

    # set proposer to slashed
    state.validators[proposer_index].slashed = True

    block = build_empty_block_for_next_slot(spec, state)

    yield from run_block_header_processing(spec, state, block, valid=False)
示例#25
0
def prepare_state_with_attestations(spec, state, participation_fn=None):
    """
    Prepare state with attestations according to the ``participation_fn``.
    If no ``participation_fn``, default to "full" -- max committee participation at each slot.

    participation_fn: (slot, committee_index, committee_indices_set) -> participants_indices_set
    """
    # Go to start of next epoch to ensure can have full participation
    next_epoch(spec, state)

    start_slot = state.slot
    start_epoch = spec.get_current_epoch(state)
    next_epoch_start_slot = spec.compute_start_slot_at_epoch(start_epoch + 1)
    attestations = []
    for _ in range(spec.SLOTS_PER_EPOCH +
                   spec.MIN_ATTESTATION_INCLUSION_DELAY):
        # create an attestation for each index in each slot in epoch
        if state.slot < next_epoch_start_slot:
            for committee_index in range(
                    spec.get_committee_count_per_slot(
                        state, spec.get_current_epoch(state))):

                def temp_participants_filter(comm):
                    if participation_fn is None:
                        return comm
                    else:
                        return participation_fn(state.slot, committee_index,
                                                comm)

                attestation = get_valid_attestation(
                    spec,
                    state,
                    index=committee_index,
                    filter_participant_set=temp_participants_filter,
                    signed=True)
                if any(attestation.aggregation_bits
                       ):  # Only if there is at least 1 participant.
                    attestations.append(attestation)
        # fill each created slot in state after inclusion delay
        if state.slot >= start_slot + spec.MIN_ATTESTATION_INCLUSION_DELAY:
            inclusion_slot = state.slot - spec.MIN_ATTESTATION_INCLUSION_DELAY
            include_attestations = [
                att for att in attestations if att.data.slot == inclusion_slot
            ]
            add_attestations_to_state(spec, state, include_attestations,
                                      state.slot)
        next_slot(spec, state)

    assert state.slot == next_epoch_start_slot + spec.MIN_ATTESTATION_INCLUSION_DELAY
    if not is_post_altair(spec):
        assert len(state.previous_epoch_attestations) == len(attestations)

    return attestations
def test_non_empty_extra_data_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.extra_data = b'\x45' * 12

    yield from run_execution_payload_processing(spec, state, execution_payload)

    assert state.latest_execution_payload_header.extra_data == execution_payload.extra_data
示例#27
0
def test_bad_crosslink_end_epoch(spec, state):
    next_epoch(spec, state)
    apply_empty_block(spec, state)

    attestation = get_valid_attestation(spec, state, signed=True)
    for _ in range(spec.MIN_ATTESTATION_INCLUSION_DELAY):
        next_slot(spec, state)
    apply_empty_block(spec, state)

    attestation.data.crosslink.end_epoch += 1

    yield from run_attestation_processing(spec, state, attestation, False)
示例#28
0
def test_bad_previous_crosslink(state):
    next_epoch(state)
    apply_empty_block(state)

    attestation = get_valid_attestation(state, signed=True)
    for _ in range(spec.MIN_ATTESTATION_INCLUSION_DELAY):
        next_slot(state)
    apply_empty_block(state)

    state.current_crosslinks[attestation.data.shard].epoch += 10

    yield from run_attestation_processing(state, attestation, False)
示例#29
0
def test_gaslimit_lower_regular_payload(spec, state):
    # pre-state
    state = build_state_with_complete_transition(spec, state)
    next_slot(spec, state)

    # execution payload
    execution_payload = build_empty_execution_payload(spec, state)
    execution_payload.gas_limit = (
        execution_payload.gas_limit -
        execution_payload.gas_limit // spec.GAS_LIMIT_DENOMINATOR + uint64(1)
    )

    yield from run_execution_payload_processing(spec, state, execution_payload)
示例#30
0
def _state_transition_across_slots(spec,
                                   state,
                                   to_slot,
                                   block_filter=_all_blocks):
    assert state.slot < to_slot
    while state.slot < to_slot:
        should_make_block = block_filter(state)
        if should_make_block:
            block = build_empty_block_for_next_slot(spec, state)
            signed_block = state_transition_and_sign_block(spec, state, block)
            yield signed_block
        else:
            next_slot(spec, state)