示例#1
0
def test_randao_processing_validates_randao_reveal(sample_beacon_block_params,
                                                   sample_beacon_state_params,
                                                   sample_fork_params, keymap,
                                                   config):
    proposer_pubkey, proposer_privkey = first(keymap.items())
    state = SerenityBeaconState(**sample_beacon_state_params).copy(
        validator_registry=tuple(
            mock_validator_record(proposer_pubkey)
            for _ in range(config.TARGET_COMMITTEE_SIZE)),
        validator_balances=(config.MAX_DEPOSIT_AMOUNT, ) *
        config.TARGET_COMMITTEE_SIZE,
        latest_randao_mixes=tuple(
            ZERO_HASH32 for _ in range(config.LATEST_RANDAO_MIXES_LENGTH)),
    )

    epoch = state.current_epoch(config.EPOCH_LENGTH)
    slot = epoch * config.EPOCH_LENGTH
    message = (epoch + 1).to_bytes(32, byteorder="big")
    fork = Fork(**sample_fork_params)
    domain = get_domain(fork, slot, SignatureDomain.DOMAIN_RANDAO)
    randao_reveal = bls.sign(message, proposer_privkey, domain)

    block = SerenityBeaconBlock(**sample_beacon_block_params).copy(
        randao_reveal=randao_reveal, )

    with pytest.raises(ValidationError):
        process_randao(state, block, config)
def test_activate_validator(is_genesis, filled_beacon_state, genesis_epoch,
                            epoch_length, entry_exit_delay,
                            max_deposit_amount):
    validator_count = 10
    state = filled_beacon_state.copy(
        validator_registry=tuple(
            mock_validator_record(
                pubkey=index.to_bytes(48, 'big'),
                is_active=False,
            ) for index in range(validator_count)),
        validator_balances=(max_deposit_amount, ) * validator_count,
    )
    index = 1
    # Check that the `index`th validator in `state` is inactivated
    assert state.validator_registry[index].activation_epoch == FAR_FUTURE_EPOCH

    result_state = activate_validator(
        state=state,
        index=index,
        is_genesis=is_genesis,
        genesis_epoch=genesis_epoch,
        epoch_length=epoch_length,
        entry_exit_delay=entry_exit_delay,
    )

    if is_genesis:
        assert result_state.validator_registry[
            index].activation_epoch == genesis_epoch
    else:
        assert (result_state.validator_registry[index].activation_epoch ==
                get_entry_exit_effect_epoch(
                    state.current_epoch(epoch_length),
                    entry_exit_delay,
                ))
示例#3
0
def test_randao_processing(sample_beacon_block_params,
                           sample_beacon_state_params, sample_fork_params,
                           keymap, config):
    proposer_pubkey, proposer_privkey = first(keymap.items())
    state = SerenityBeaconState(**sample_beacon_state_params).copy(
        validator_registry=tuple(
            mock_validator_record(proposer_pubkey)
            for _ in range(config.TARGET_COMMITTEE_SIZE)),
        validator_balances=(config.MAX_DEPOSIT_AMOUNT, ) *
        config.TARGET_COMMITTEE_SIZE,
        latest_randao_mixes=tuple(
            ZERO_HASH32 for _ in range(config.LATEST_RANDAO_MIXES_LENGTH)),
    )

    epoch = state.current_epoch(config.EPOCH_LENGTH)
    slot = epoch * config.EPOCH_LENGTH
    message = epoch.to_bytes(32, byteorder="big")
    fork = Fork(**sample_fork_params)
    domain = get_domain(fork, slot, SignatureDomain.DOMAIN_RANDAO)
    randao_reveal = bls.sign(message, proposer_privkey, domain)

    block = SerenityBeaconBlock(**sample_beacon_block_params).copy(
        randao_reveal=randao_reveal, )

    new_state = process_randao(state, block, config)

    updated_index = epoch % config.LATEST_RANDAO_MIXES_LENGTH
    original_mixes = state.latest_randao_mixes
    updated_mixes = new_state.latest_randao_mixes

    assert all(
        updated == original if index != updated_index else updated != original
        for index, (updated,
                    original) in enumerate(zip(updated_mixes, original_mixes)))
示例#4
0
def test_num_validators(expected, max_deposit, filled_beacon_state):
    state = filled_beacon_state.copy(
        validator_registry=tuple(
            mock_validator_record(pubkey, ) for pubkey in range(expected)),
        validator_balances=(max_deposit * GWEI_PER_ETH, ) * expected,
    )

    assert state.num_validators == expected
示例#5
0
def test_validator_registry_and_balances_length(sample_beacon_state_params,
                                                config):
    # When len(BeaconState.validator_registry) != len(BeaconState.validtor_balances)
    with pytest.raises(ValueError):
        BeaconState(**sample_beacon_state_params).copy(
            validator_registry=tuple(
                mock_validator_record(pubkey, config)
                for pubkey in range(10)), )
示例#6
0
def n_validators_state(filled_beacon_state, max_deposit_amount, n):
    validator_count = n
    return filled_beacon_state.copy(
        validator_registry=tuple(
            mock_validator_record(
                pubkey=index.to_bytes(48, "big"),
                is_active=True,
            ) for index in range(validator_count)),
        validator_balances=(max_deposit_amount, ) * validator_count,
    )
示例#7
0
def ten_validators_state(empty_beacon_state, max_deposit):
    validator_count = 10
    return empty_beacon_state.copy(
        validator_registry=tuple(
            mock_validator_record(
                pubkey=pubkey,
                is_active=True,
            )
            for pubkey in range(validator_count)
        ),
        validator_balances=(max_deposit * GWEI_PER_ETH,) * validator_count,
    )
def genesis_validators(init_validator_pubkeys, init_randao, max_deposit_amount,
                       config):
    """
    Inactive
    """
    return tuple(
        mock_validator_record(
            pubkey=pubkey,
            config=config,
            withdrawal_credentials=ZERO_HASH32,
            is_active=False,
        ) for pubkey in init_validator_pubkeys)
示例#9
0
def initial_validators(init_validator_pubkeys, init_randao, max_deposit):
    """
    Inactive
    """
    return tuple(
        mock_validator_record(
            pubkey=pubkey,
            withdrawal_credentials=ZERO_HASH32,
            randao_commitment=init_randao,
            status_flags=0,
            is_active=False,
        ) for pubkey in init_validator_pubkeys)
示例#10
0
def test_validate_serenity_proposer_signature(
        proposer_privkey, proposer_pubkey, is_valid_signature,
        sample_beacon_block_params, sample_beacon_state_params,
        sample_shard_committee_params, beacon_chain_shard_number, epoch_length,
        max_deposit):

    state = BeaconState(**sample_beacon_state_params).copy(
        validator_registry=tuple(
            mock_validator_record(proposer_pubkey) for _ in range(10)),
        validator_balances=(max_deposit * GWEI_PER_ETH, ) * 10,
        shard_committees_at_slots=get_sample_shard_committees_at_slots(
            num_slot=128,
            num_shard_committee_per_slot=10,
            sample_shard_committee_params=sample_shard_committee_params,
        ),
    )

    default_block = BeaconBlock(**sample_beacon_block_params)
    empty_signature_block_root = default_block.block_without_signature_root

    proposal_root = ProposalSignedData(
        state.slot,
        beacon_chain_shard_number,
        empty_signature_block_root,
    ).root

    proposed_block = BeaconBlock(**sample_beacon_block_params).copy(
        signature=bls.sign(
            message=proposal_root,
            privkey=proposer_privkey,
            domain=SignatureDomain.DOMAIN_PROPOSAL,
        ), )

    if is_valid_signature:
        validate_serenity_proposer_signature(
            state,
            proposed_block,
            beacon_chain_shard_number,
            epoch_length,
        )
    else:
        with pytest.raises(ValidationError):
            validate_serenity_proposer_signature(
                state,
                proposed_block,
                beacon_chain_shard_number,
                epoch_length,
            )
示例#11
0
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(**sample_beacon_state_params).copy(
        validator_registry=tuple(
            mock_validator_record(proposer_pubkey, config)
            for _ in range(config.TARGET_COMMITTEE_SIZE)
        ),
        validator_balances=(config.MAX_DEPOSIT_AMOUNT,) * config.TARGET_COMMITTEE_SIZE,

        latest_randao_mixes=tuple(
            ZERO_HASH32
            for _ in range(config.LATEST_RANDAO_MIXES_LENGTH)
        ),
    )

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

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

    block_body = BeaconBlockBody(**sample_beacon_block_body_params).copy(
        randao_reveal=randao_reveal,
    )

    block = SerenityBeaconBlock(**sample_beacon_block_params).copy(
        body=block_body,
    )

    new_state = process_randao(state, block, config)

    updated_index = epoch % config.LATEST_RANDAO_MIXES_LENGTH
    original_mixes = state.latest_randao_mixes
    updated_mixes = new_state.latest_randao_mixes

    assert all(
        updated == original if index != updated_index else updated != original
        for index, (updated, original) in enumerate(zip(updated_mixes, original_mixes))
    )
示例#12
0
def test_validate_proposer_signature(
        slots_per_epoch, shard_count, proposer_privkey, proposer_pubkey,
        is_valid_signature, sample_beacon_block_params,
        sample_beacon_state_params, beacon_chain_shard_number, genesis_epoch,
        target_committee_size, max_deposit_amount, config):

    state = BeaconState(**sample_beacon_state_params).copy(
        validator_registry=tuple(
            mock_validator_record(proposer_pubkey, config) for _ in range(10)),
        validator_balances=(max_deposit_amount, ) * 10,
    )

    default_block = BeaconBlock(**sample_beacon_block_params)
    empty_signature_block_root = default_block.block_without_signature_root

    proposal_signed_root = Proposal(
        state.slot,
        beacon_chain_shard_number,
        empty_signature_block_root,
    ).signed_root

    proposed_block = BeaconBlock(**sample_beacon_block_params).copy(
        signature=bls.sign(
            message_hash=proposal_signed_root,
            privkey=proposer_privkey,
            domain=SignatureDomain.DOMAIN_PROPOSAL,
        ), )

    if is_valid_signature:
        validate_proposer_signature(
            state,
            proposed_block,
            beacon_chain_shard_number,
            CommitteeConfig(config),
        )
    else:
        with pytest.raises(ValidationError):
            validate_proposer_signature(
                state,
                proposed_block,
                beacon_chain_shard_number,
                CommitteeConfig(config),
            )
示例#13
0
def test_update_validator(ten_validators_state, validator_index, new_pubkey,
                          new_balance):
    state = ten_validators_state
    validator = mock_validator_record(new_pubkey)

    if validator_index < state.num_validators:
        result_state = state.update_validator(
            validator_index=validator_index,
            validator=validator,
            balance=new_balance,
        )
        assert result_state.validator_balances[validator_index] == new_balance
        assert result_state.validator_registry[
            validator_index].pubkey == new_pubkey
        assert state.validator_registry[validator_index].pubkey != new_pubkey
    else:
        with pytest.raises(IndexError):
            state.update_validator(
                validator_index=validator_index,
                validator=validator,
                balance=new_balance,
            )
示例#14
0
def test_activate_validator(genesis, filled_beacon_state, genesis_slot,
                            entry_exit_delay, max_deposit):
    validator_count = 10
    state = filled_beacon_state.copy(
        validator_registry=tuple(
            mock_validator_record(
                pubkey=index.to_bytes(48, 'big'),
                is_active=False,
            ) for index in range(validator_count)),
        validator_balances=(max_deposit * GWEI_PER_ETH, ) * validator_count,
    )
    index = 1
    # Check that the `index`th validator in `state` is inactivated
    assert state.validator_registry[index].activation_slot == FAR_FUTURE_SLOT

    result_state = activate_validator(
        state=state,
        index=index,
        genesis=genesis,
        genesis_slot=genesis_slot,
        entry_exit_delay=entry_exit_delay,
    )
    result_validator = result_state.validator_registry[index]

    new_validator_registry_delta_chain_tip = ValidatorRegistryDeltaBlock(
        latest_registry_delta_root=state.validator_registry_delta_chain_tip,
        validator_index=index,
        pubkey=result_validator.pubkey,
        slot=result_validator.activation_slot,
        flag=ValidatorRegistryDeltaFlag.ACTIVATION,
    ).root

    assert (result_state.validator_registry_delta_chain_tip ==
            new_validator_registry_delta_chain_tip)
    if genesis:
        state.validator_registry[index].activation_slot == genesis_slot
    else:
        state.validator_registry[
            index].activation_slot == state.slot + entry_exit_delay