Ejemplo n.º 1
0
def validate_indexed_attestation_aggregate_signature(
        state: BeaconState, indexed_attestation: IndexedAttestation,
        slots_per_epoch: int) -> None:
    bit_0_indices = indexed_attestation.custody_bit_0_indices
    bit_1_indices = indexed_attestation.custody_bit_1_indices

    pubkeys = (
        bls.aggregate_pubkeys(
            tuple(state.validators[i].pubkey for i in bit_0_indices)),
        bls.aggregate_pubkeys(
            tuple(state.validators[i].pubkey for i in bit_1_indices)),
    )

    message_hashes = (
        AttestationDataAndCustodyBit(data=indexed_attestation.data,
                                     custody_bit=False).hash_tree_root,
        AttestationDataAndCustodyBit(data=indexed_attestation.data,
                                     custody_bit=True).hash_tree_root,
    )

    domain = get_domain(
        state,
        SignatureDomain.DOMAIN_ATTESTATION,
        slots_per_epoch,
        indexed_attestation.data.target.epoch,
    )
    bls.validate_multiple(
        pubkeys=pubkeys,
        message_hashes=message_hashes,
        signature=indexed_attestation.signature,
        domain=domain,
    )
Ejemplo n.º 2
0
def test_signature_aggregation(backend, msg, privkeys, domain):
    bls.use(backend)
    sigs = [bls.sign(msg, k, domain=domain) for k in privkeys]
    pubs = [bls.privtopub(k) for k in privkeys]
    aggsig = bls.aggregate_signatures(sigs)
    aggpub = bls.aggregate_pubkeys(pubs)
    assert bls.verify(msg, aggpub, aggsig, domain=domain)
Ejemplo n.º 3
0
def test_multi_aggregation(backend, msg_1, msg_2, privkeys_1, privkeys_2,
                           domain):
    bls.use(backend)

    sigs_1 = [bls.sign(msg_1, k, domain=domain)
              for k in privkeys_1]  # signatures to msg_1
    pubs_1 = [bls.privtopub(k) for k in privkeys_1]
    aggpub_1 = bls.aggregate_pubkeys(pubs_1)  # sig_1 to msg_1

    sigs_2 = [bls.sign(msg_2, k, domain=domain)
              for k in privkeys_2]  # signatures to msg_2
    pubs_2 = [bls.privtopub(k) for k in privkeys_2]
    aggpub_2 = bls.aggregate_pubkeys(pubs_2)  # sig_2 to msg_2

    message_hashes = [msg_1, msg_2]
    pubs = [aggpub_1, aggpub_2]
    aggsig = bls.aggregate_signatures(sigs_1 + sigs_2)

    assert bls.verify_multiple(pubkeys=pubs,
                               message_hashes=message_hashes,
                               signature=aggsig,
                               domain=domain)
Ejemplo n.º 4
0
def test_aggregate_votes(votes_count, random, privkeys, pubkeys):
    bit_count = 10
    pre_bitfield = get_empty_bitfield(bit_count)
    pre_sigs = ()
    domain = compute_domain(SignatureDomain.DOMAIN_ATTESTATION)

    random_votes = random.sample(range(bit_count), votes_count)
    message_hash = b"\x12" * 32

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

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

    # Aggregate the votes
    bitfield, sigs = aggregate_votes(
        bitfield=pre_bitfield,
        sigs=pre_sigs,
        voting_sigs=sigs,
        attesting_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)

    if votes_count == 0 and bls.backend in (ChiaBackend, MilagroBackend):
        with pytest.raises(ValidationError):
            bls.validate(message_hash, aggregated_pubs, sigs, domain)
    else:
        bls.validate(message_hash, aggregated_pubs, sigs, domain)
Ejemplo n.º 5
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_hash = b'\x12' * 32

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

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

    # Aggregate the votes
    bitfield, sigs = aggregate_votes(bitfield=pre_bitfield,
                                     sigs=pre_sigs,
                                     voting_sigs=sigs,
                                     attesting_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)

    if votes_count != 0:
        bls.validate(message_hash, aggregated_pubs, sigs, domain)
    else:
        # EMPTY_SIGNATURE is considered invalid
        with pytest.raises(ValueError):
            bls.validate(message_hash, aggregated_pubs, sigs, domain)
Ejemplo n.º 6
0
def test_sanity(backend):
    bls.use(backend)
    msg_0 = b"\x32" * 32
    domain = 123

    # Test: Verify the basic sign/verify process
    privkey_0 = 5566
    sig_0 = bls.sign(msg_0, privkey_0, domain)
    assert_signature(sig_0)
    pubkey_0 = bls.privtopub(privkey_0)
    assert_pubkey(pubkey_0)
    assert bls.verify(msg_0, pubkey_0, sig_0, domain)

    privkey_1 = 5567
    sig_1 = bls.sign(msg_0, privkey_1, domain)
    pubkey_1 = bls.privtopub(privkey_1)
    assert bls.verify(msg_0, pubkey_1, sig_1, domain)

    # Test: Verify signatures are correctly aggregated
    aggregated_signature = bls.aggregate_signatures([sig_0, sig_1])
    assert_signature(aggregated_signature)

    # Test: Verify pubkeys are correctly aggregated
    aggregated_pubkey = bls.aggregate_pubkeys([pubkey_0, pubkey_1])
    assert_pubkey(aggregated_pubkey)

    # Test: Verify with `aggregated_signature` and `aggregated_pubkey`
    assert bls.verify(msg_0, aggregated_pubkey, aggregated_signature, domain)

    # Test: `verify_multiple`
    msg_1 = b"x22" * 32
    privkey_2 = 55688
    sig_2 = bls.sign(msg_1, privkey_2, domain)
    assert_signature(sig_2)
    pubkey_2 = bls.privtopub(privkey_2)
    assert_pubkey(pubkey_2)
    sig_1_2 = bls.aggregate_signatures([sig_1, sig_2])
    assert bls.verify_multiple(
        pubkeys=[pubkey_1, pubkey_2],
        message_hashes=[msg_0, msg_1],
        signature=sig_1_2,
        domain=domain,
    )
Ejemplo n.º 7
0
def validate_indexed_attestation_aggregate_signature(
        state: BeaconState, indexed_attestation: IndexedAttestation,
        slots_per_epoch: int) -> None:
    attesting_indices = indexed_attestation.attesting_indices
    pubkey = bls.aggregate_pubkeys(
        tuple(state.validators[i].pubkey for i in attesting_indices))

    message_hash = indexed_attestation.data.hash_tree_root
    domain = get_domain(
        state,
        SignatureDomain.DOMAIN_BEACON_ATTESTER,
        slots_per_epoch,
        indexed_attestation.data.target.epoch,
    )
    bls.validate(
        pubkey=pubkey,
        message_hash=message_hash,
        signature=indexed_attestation.signature,
        domain=domain,
    )
Ejemplo n.º 8
0
    def run_with(_cls, inputs: SequenceOfBLSPubkey,
                 _config: Optional[Eth2Config]) -> BLSPubkey:
        # BLS override
        bls.use(MilagroBackend)

        return bls.aggregate_pubkeys(inputs)
Ejemplo n.º 9
0
def test_empty_aggregation(backend):
    bls.use(backend)
    assert bls.aggregate_pubkeys([]) == EMPTY_PUBKEY
    assert bls.aggregate_signatures([]) == EMPTY_SIGNATURE