Example #1
0
def validate_proof_of_possession(state: BeaconState, pubkey: BLSPubkey,
                                 proof_of_possession: BLSSignature,
                                 withdrawal_credentials: Hash32,
                                 randao_commitment: Hash32) -> None:
    deposit_input = DepositInput(
        pubkey=pubkey,
        withdrawal_credentials=withdrawal_credentials,
        randao_commitment=randao_commitment,
        proof_of_possession=EMPTY_SIGNATURE,
    )

    is_valid_signature = bls.verify(
        pubkey=pubkey,
        # TODO: change to hash_tree_root(deposit_input) when we have SSZ tree hashing
        message=deposit_input.root,
        signature=proof_of_possession,
        domain=get_domain(
            state.fork_data,
            state.slot,
            SignatureDomain.DOMAIN_DEPOSIT,
        ),
    )

    if not is_valid_signature:
        raise ValidationError("BLS signature verification error")
Example #2
0
def validate_serenity_proposer_signature(
        state: BeaconState, block: BaseBeaconBlock,
        beacon_chain_shard_number: ShardNumber, epoch_length: int) -> None:
    block_without_signature_root = block.block_without_signature_root

    # TODO: Replace this root with tree hash root
    proposal_root = ProposalSignedData(
        state.slot,
        beacon_chain_shard_number,
        block_without_signature_root,
    ).root

    # Get the public key of proposer
    beacon_proposer_index = get_beacon_proposer_index(state, state.slot,
                                                      epoch_length)
    proposer_pubkey = state.validator_registry[beacon_proposer_index].pubkey

    is_valid_signature = bls.verify(
        pubkey=proposer_pubkey,
        message=proposal_root,
        signature=block.signature,
        domain=get_domain(state.fork_data, state.slot,
                          SignatureDomain.DOMAIN_PROPOSAL),
    )

    if not is_valid_signature:
        raise ValidationError("Invalid Proposer Signature on block")
Example #3
0
def test_signature_aggregation(msg, privkeys):
    domain = 0
    sigs = [sign(msg, k, domain=domain) for k in privkeys]
    pubs = [privtopub(k) for k in privkeys]
    aggsig = aggregate_signatures(sigs)
    aggpub = aggregate_pubkeys(pubs)
    assert verify(msg, aggpub, aggsig, domain=domain)
Example #4
0
def test_bls_core(privkey):
    domain = 0
    p1 = multiply(G1, privkey)
    p2 = multiply(G2, privkey)
    msg = str(privkey).encode('utf-8')
    msghash = hash_to_G2(msg, domain=domain)

    assert normalize(decompress_G1(compress_G1(p1))) == normalize(p1)
    assert normalize(decompress_G2(compress_G2(p2))) == normalize(p2)
    assert normalize(decompress_G2(compress_G2(msghash))) == normalize(msghash)
    sig = sign(msg, privkey, domain=domain)
    pub = privtopub(privkey)
    assert verify(msg, pub, sig, domain=domain)
Example #5
0
def verify_votes(
    message: bytes, votes: Iterable[Tuple[CommitteeIndex, BLSSignature,
                                          BLSPubkey]], domain: SignatureDomain
) -> Tuple[Tuple[BLSSignature, ...], Tuple[CommitteeIndex, ...]]:
    """
    Verify the given votes.

    vote: (committee_index, sig, public_key)
    """
    sigs_with_committe_info = tuple(
        (sig, committee_index) for (committee_index, sig, public_key) in votes
        if bls.verify(message, public_key, sig, domain))
    try:
        sigs, committee_indices = zip(*sigs_with_committe_info)
    except ValueError:
        sigs = tuple()
        committee_indices = tuple()

    return sigs, committee_indices
Example #6
0
def validate_serenity_attestation_aggregate_signature(
        state: BeaconState, attestation: Attestation,
        epoch_length: int) -> None:
    """
    Validate ``aggregate_signature`` field of ``attestation``.
    Raise ``ValidationError`` if it's invalid.

    Note: This is the phase 0 version of `aggregate_signature`` validation.
    All proof of custody bits are assumed to be 0 within the signed data.
    This will change to reflect real proof of custody bits in the Phase 1.
    """
    participant_indices = get_attestation_participants(
        state=state,
        slot=attestation.data.slot,
        shard=attestation.data.shard,
        participation_bitfield=attestation.participation_bitfield,
        epoch_length=epoch_length,
    )

    pubkeys = tuple(state.validator_registry[validator_index].pubkey
                    for validator_index in participant_indices)
    group_public_key = bls.aggregate_pubkeys(pubkeys)

    # TODO: change to tree hashing when we have SSZ
    # TODO: Replace with AttestationAndCustodyBit data structure
    message = hash_eth2(rlp.encode(attestation.data) + (0).to_bytes(1, "big"))

    is_valid_signature = bls.verify(
        message=message,
        pubkey=group_public_key,
        signature=attestation.aggregate_signature,
        domain=get_domain(
            fork_data=state.fork_data,
            slot=attestation.data.slot,
            domain_type=SignatureDomain.DOMAIN_ATTESTATION,
        ),
    )
    if not is_valid_signature:
        raise ValidationError(
            "Attestation ``aggregate_signature`` is invalid.")
Example #7
0
def test_aggregate_votes(votes_count, random, privkeys, pubkeys):
    bit_count = 10
    pre_bitfield = get_empty_bitfield(bit_count)
    pre_sigs = ()
    domain = 0

    random_votes = random.sample(range(bit_count), votes_count)
    message = b'hello'

    # Get votes: (committee_index, sig, public_key)
    votes = [(
        committee_index,
        bls.sign(message, privkeys[committee_index], domain),
        pubkeys[committee_index],
    ) for committee_index in random_votes]

    # Verify
    sigs, committee_indices = verify_votes(message, votes, domain)

    # Aggregate the votes
    bitfield, sigs = aggregate_votes(
        bitfield=pre_bitfield,
        sigs=pre_sigs,
        voting_sigs=sigs,
        voting_committee_indices=committee_indices)

    try:
        _, _, pubs = zip(*votes)
    except ValueError:
        pubs = ()

    voted_index = [
        committee_index for committee_index in random_votes
        if has_voted(bitfield, committee_index)
    ]
    assert len(voted_index) == len(votes)

    aggregated_pubs = bls.aggregate_pubkeys(pubs)
    assert bls.verify(message, aggregated_pubs, sigs, domain)