Пример #1
0
def test_process_voluntary_exits(
    genesis_state,
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    config,
    keymap,
    success,
):
    state = genesis_state.set(
        "slot",
        compute_start_slot_at_epoch(
            config.GENESIS_EPOCH + config.PERSISTENT_COMMITTEE_PERIOD,
            config.SLOTS_PER_EPOCH,
        ),
    )
    validator_index = 0
    validator = state.validators[validator_index].set("activation_epoch",
                                                      config.GENESIS_EPOCH)
    state = state.transform(["validators", validator_index], validator)
    valid_voluntary_exit = create_mock_voluntary_exit(state, config, keymap,
                                                      validator_index)

    if success:
        block_body = BeaconBlockBody.create(
            **sample_beacon_block_body_params).set("voluntary_exits",
                                                   (valid_voluntary_exit, ))
        block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
            "slot", state.slot, "body", block_body)

        new_state = process_voluntary_exits(state, block, config)
        updated_validator = new_state.validators[validator_index]
        assert updated_validator.exit_epoch != FAR_FUTURE_EPOCH
        assert updated_validator.exit_epoch > state.current_epoch(
            config.SLOTS_PER_EPOCH)
        assert updated_validator.withdrawable_epoch == (
            updated_validator.exit_epoch +
            config.MIN_VALIDATOR_WITHDRAWABILITY_DELAY)
    else:
        invalid_voluntary_exit = valid_voluntary_exit.set(
            "signature",
            b"\x12" * 96  # Put wrong signature
        )
        block_body = BeaconBlockBody.create(
            **sample_beacon_block_body_params).set("voluntary_exits",
                                                   (invalid_voluntary_exit, ))
        block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
            "slot", state.slot, "body", block_body)

        with pytest.raises(ValidationError):
            process_voluntary_exits(state, block, config)
Пример #2
0
def test_process_attester_slashings(
    genesis_state,
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    config,
    keymap,
    min_attestation_inclusion_delay,
    success,
):
    attesting_state = genesis_state.mset(
        "slot",
        genesis_state.slot + config.SLOTS_PER_EPOCH,
        "block_roots",
        tuple(
            i.to_bytes(32, "little")
            for i in range(config.SLOTS_PER_HISTORICAL_ROOT)),
    )
    valid_attester_slashing = create_mock_attester_slashing_is_double_vote(
        attesting_state, config, keymap, attestation_epoch=0)
    state = attesting_state.set(
        "slot", attesting_state.slot + min_attestation_inclusion_delay)

    if success:
        block_body = BeaconBlockBody.create(
            **sample_beacon_block_body_params).set("attester_slashings",
                                                   (valid_attester_slashing, ))
        block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
            "slot", state.slot, "body", block_body)

        attester_index = valid_attester_slashing.attestation_1.attesting_indices[
            0]

        new_state = process_attester_slashings(state, block, config)
        # Check if slashed
        assert not state.validators[attester_index].slashed
        assert new_state.validators[attester_index].slashed
    else:
        invalid_attester_slashing = valid_attester_slashing.transform(
            ["attestation_2", "data"],
            valid_attester_slashing.attestation_1.data)
        block_body = BeaconBlockBody.create(
            **sample_beacon_block_body_params).set(
                "attester_slashings", (invalid_attester_slashing, ))
        block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
            "slot", state.slot, "body", block_body)

        with pytest.raises(ValidationError):
            process_attester_slashings(state, block, config)
def test_randao_processing_validates_randao_reveal(
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    sample_beacon_state_params,
    sample_fork_params,
    keymap,
    config,
):
    proposer_pubkey, proposer_privkey = first(keymap.items())
    state = SerenityBeaconState.create(**sample_beacon_state_params).mset(
        "validators",
        tuple(
            create_mock_validator(proposer_pubkey, config)
            for _ in range(config.TARGET_COMMITTEE_SIZE)),
        "balances",
        (config.MAX_EFFECTIVE_BALANCE, ) * config.TARGET_COMMITTEE_SIZE,
        "randao_mixes",
        tuple(ZERO_HASH32 for _ in range(config.EPOCHS_PER_HISTORICAL_VECTOR)),
    )

    epoch = state.current_epoch(config.SLOTS_PER_EPOCH)
    message_hash = (epoch + 1).to_bytes(32, byteorder="little")
    domain = get_domain(state, SignatureDomain.DOMAIN_RANDAO,
                        config.SLOTS_PER_EPOCH)
    randao_reveal = bls.sign(message_hash, proposer_privkey, domain)

    block_body = BeaconBlockBody.create(**sample_beacon_block_body_params).set(
        "randao_reveal", randao_reveal)

    block = SerenityBeaconBlock.create(**sample_beacon_block_params).set(
        "body", block_body)

    with pytest.raises(ValidationError):
        process_randao(state, block, config)
Пример #4
0
def test_process_attestations(
    genesis_state,
    genesis_block,
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    config,
    keymap,
    fixture_sm_class,
    chaindb,
    genesis_fork_choice_context,
    success,
):

    attestation_slot = 0
    current_slot = attestation_slot + config.MIN_ATTESTATION_INCLUSION_DELAY
    state = genesis_state.set("slot", current_slot)

    attestations = create_mock_signed_attestations_at_slot(
        state=state,
        config=config,
        state_machine=fixture_sm_class(chaindb, genesis_fork_choice_context),
        attestation_slot=attestation_slot,
        beacon_block_root=genesis_block.message.hash_tree_root,
        keymap=keymap,
        voted_attesters_ratio=1.0,
    )

    assert len(attestations) > 0

    if not success:
        # create invalid attestation
        # i.e. wrong slot
        invalid_attestation_data = attestations[-1].data.set(
            "slot", state.slot + 1)
        invalid_attestation = attestations[-1].set("data",
                                                   invalid_attestation_data)
        attestations = attestations[:-1] + (invalid_attestation, )

    block_body = BeaconBlockBody.create(**sample_beacon_block_body_params).set(
        "attestations", attestations)
    block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
        "slot", current_slot, "body", block_body)

    if success:
        new_state = process_attestations(state, block, config)

        assert len(new_state.current_epoch_attestations) == len(attestations)
    else:
        with pytest.raises(ValidationError):
            process_attestations(state, block, config)
def test_randao_processing(
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    sample_beacon_state_params,
    keymap,
    config,
):
    proposer_pubkey, proposer_privkey = first(keymap.items())
    state = SerenityBeaconState.create(**sample_beacon_state_params).mset(
        "validators",
        tuple(
            create_mock_validator(proposer_pubkey, config)
            for _ in range(config.TARGET_COMMITTEE_SIZE)),
        "balances",
        (config.MAX_EFFECTIVE_BALANCE, ) * config.TARGET_COMMITTEE_SIZE,
        "randao_mixes",
        tuple(ZERO_HASH32 for _ in range(config.EPOCHS_PER_HISTORICAL_VECTOR)),
    )

    epoch = state.current_epoch(config.SLOTS_PER_EPOCH)
    slot = compute_start_slot_at_epoch(epoch, config.SLOTS_PER_EPOCH)

    randao_reveal = _generate_randao_reveal(privkey=proposer_privkey,
                                            slot=slot,
                                            state=state,
                                            config=config)

    block_body = BeaconBlockBody.create(**sample_beacon_block_body_params).set(
        "randao_reveal", randao_reveal)

    block = SerenityBeaconBlock.create(**sample_beacon_block_params).set(
        "body", block_body)

    new_state = process_randao(state, block, config)

    updated_index = epoch % config.EPOCHS_PER_HISTORICAL_VECTOR
    original_mixes = state.randao_mixes
    updated_mixes = new_state.randao_mixes

    assert all(
        updated == original if index != updated_index else updated != original
        for index, (updated,
                    original) in enumerate(zip(updated_mixes, original_mixes)))
def test_process_proposer_slashings(
    genesis_state,
    sample_beacon_block_params,
    sample_beacon_block_body_params,
    config,
    keymap,
    block_root_1,
    block_root_2,
    success,
):
    current_slot = config.GENESIS_SLOT + 1
    state = genesis_state.set("slot", current_slot)
    whistleblower_index = get_beacon_proposer_index(state,
                                                    CommitteeConfig(config))
    slashing_proposer_index = (whistleblower_index + 1) % len(state.validators)
    proposer_slashing = create_mock_proposer_slashing_at_block(
        state,
        config,
        keymap,
        block_root_1=block_root_1,
        block_root_2=block_root_2,
        proposer_index=slashing_proposer_index,
    )
    proposer_slashings = (proposer_slashing, )

    block_body = BeaconBlockBody.create(**sample_beacon_block_body_params).set(
        "proposer_slashings", proposer_slashings)
    block = SerenityBeaconBlock.create(**sample_beacon_block_params).mset(
        "slot", current_slot, "body", block_body)

    if success:
        new_state = process_proposer_slashings(state, block, config)
        # Check if slashed
        assert (new_state.balances[slashing_proposer_index] <
                state.balances[slashing_proposer_index])
    else:
        with pytest.raises(ValidationError):
            process_proposer_slashings(state, block, config)