Search in sources :

Example 1 with SyncCommittee

use of tech.pegasys.teku.spec.datastructures.state.SyncCommittee in project teku by ConsenSys.

the class ChainDataProvider method getSyncCommitteesFromState.

private StateSyncCommittees getSyncCommitteesFromState(final tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState state, final Optional<UInt64> epochQueryParam) {
    final UInt64 epoch = epochQueryParam.orElse(spec.computeEpochAtSlot(state.getSlot()));
    final UInt64 slot = spec.computeStartSlotAtEpoch(epoch);
    final Optional<SyncCommittee> maybeCommittee = spec.getSyncCommitteeUtil(slot).map(util -> util.getSyncCommittee(state, epoch));
    // returned
    if (maybeCommittee.isEmpty()) {
        return new StateSyncCommittees(List.of(), List.of());
    }
    final SyncCommittee committee = maybeCommittee.get();
    final List<UInt64> committeeIndices = committee.getPubkeys().stream().flatMap(pubkey -> spec.getValidatorIndex(state, pubkey.getBLSPublicKey()).stream()).map(UInt64::valueOf).collect(toList());
    return new StateSyncCommittees(committeeIndices, Lists.partition(committeeIndices, spec.atEpoch(epoch).getConfig().getTargetCommitteeSize()));
}
Also used : UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) StateSyncCommittees(tech.pegasys.teku.api.response.v1.beacon.StateSyncCommittees)

Example 2 with SyncCommittee

use of tech.pegasys.teku.spec.datastructures.state.SyncCommittee in project teku by ConsenSys.

the class SyncCommitteeUtil method getSyncSubcommittees.

public Map<UInt64, SyncSubcommitteeAssignments> getSyncSubcommittees(final BeaconState state, final UInt64 epoch) {
    final UInt64 syncCommitteePeriod = computeSyncCommitteePeriod(epoch);
    final UInt64 currentEpoch = beaconStateAccessors.getCurrentEpoch(state);
    final UInt64 currentSyncCommitteePeriod = computeSyncCommitteePeriod(currentEpoch);
    checkArgument(isStateUsableForCommitteeCalculationAtEpoch(state, epoch), "State must be in the same or previous sync committee period. Cannot calculate epoch %s from state at slot %s", epoch, state.getSlot());
    final BeaconStateAltair altairState = BeaconStateAltair.required(state);
    return BeaconStateCache.getTransitionCaches(altairState).getSyncCommitteeCache().get(syncCommitteePeriod, period -> {
        final SyncCommittee syncCommittee;
        if (syncCommitteePeriod.equals(currentSyncCommitteePeriod)) {
            syncCommittee = altairState.getCurrentSyncCommittee();
        } else {
            syncCommittee = altairState.getNextSyncCommittee();
        }
        final int subcommitteeSize = getSubcommitteeSize();
        final SszVector<SszPublicKey> pubkeys = syncCommittee.getPubkeys();
        final Map<UInt64, SyncSubcommitteeAssignments.Builder> subcommitteeAssignments = new HashMap<>();
        for (int index = 0; index < pubkeys.size(); index++) {
            final BLSPublicKey pubkey = pubkeys.get(index).getBLSPublicKey();
            final UInt64 validatorIndex = UInt64.valueOf(validatorsUtil.getValidatorIndex(altairState, pubkey).orElseThrow(() -> new IllegalStateException("Unknown validator assigned to sync committee: " + pubkey)));
            final int subcommitteeIndex = index / subcommitteeSize;
            final int subcommitteeParticipationIndex = index - (subcommitteeIndex * subcommitteeSize);
            // Note we're using plain HashMap here instead of a concurrent alternative as they
            // are created once here and then never modified so safe to access from multiple
            // threads.
            subcommitteeAssignments.computeIfAbsent(validatorIndex, __ -> SyncSubcommitteeAssignments.builder()).addAssignment(subcommitteeIndex, subcommitteeParticipationIndex).addCommitteeIndex(index);
        }
        return subcommitteeAssignments.entrySet().stream().collect(toUnmodifiableMap(Map.Entry::getKey, entry -> entry.getValue().build()));
    });
}
Also used : BeaconBlockBodySchemaAltair(tech.pegasys.teku.spec.datastructures.blocks.blockbody.versions.altair.BeaconBlockBodySchemaAltair) HashMap(java.util.HashMap) SszPublicKey(tech.pegasys.teku.spec.datastructures.type.SszPublicKey) Bytes(org.apache.tuweni.bytes.Bytes) SchemaDefinitionsAltair(tech.pegasys.teku.spec.schemas.SchemaDefinitionsAltair) ContributionAndProof(tech.pegasys.teku.spec.datastructures.operations.versions.altair.ContributionAndProof) SYNC_COMMITTEE_SUBNET_COUNT(tech.pegasys.teku.spec.constants.NetworkConstants.SYNC_COMMITTEE_SUBNET_COUNT) ArrayList(java.util.ArrayList) Collectors.toUnmodifiableMap(java.util.stream.Collectors.toUnmodifiableMap) Preconditions.checkArgument(com.google.common.base.Preconditions.checkArgument) ValidatorConstants(tech.pegasys.teku.spec.constants.ValidatorConstants) IntIterable(it.unimi.dsi.fastutil.ints.IntIterable) Map(java.util.Map) UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) ForkInfo(tech.pegasys.teku.spec.datastructures.state.ForkInfo) SyncCommitteeContributionSchema(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SyncCommitteeContributionSchema) Bytes32(org.apache.tuweni.bytes.Bytes32) SyncAggregateSchema(tech.pegasys.teku.spec.datastructures.blocks.blockbody.versions.altair.SyncAggregateSchema) Domain(tech.pegasys.teku.spec.constants.Domain) SyncCommitteeContribution(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SyncCommitteeContribution) BeaconStateAccessorsAltair(tech.pegasys.teku.spec.logic.versions.altair.helpers.BeaconStateAccessorsAltair) MiscHelpers(tech.pegasys.teku.spec.logic.common.helpers.MiscHelpers) BLS(tech.pegasys.teku.bls.BLS) BLSSignature(tech.pegasys.teku.bls.BLSSignature) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) SyncAggregatorSelectionData(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SyncAggregatorSelectionData) SyncSubcommitteeAssignments(tech.pegasys.teku.spec.datastructures.util.SyncSubcommitteeAssignments) MutableBeaconStateAltair(tech.pegasys.teku.spec.datastructures.state.beaconstate.versions.altair.MutableBeaconStateAltair) SignedContributionAndProof(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SignedContributionAndProof) Hash(tech.pegasys.teku.infrastructure.crypto.Hash) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) MutableBeaconState(tech.pegasys.teku.spec.datastructures.state.beaconstate.MutableBeaconState) List(java.util.List) IntList(it.unimi.dsi.fastutil.ints.IntList) MathHelpers.bytesToUInt64(tech.pegasys.teku.spec.logic.common.helpers.MathHelpers.bytesToUInt64) IntOpenHashSet(it.unimi.dsi.fastutil.ints.IntOpenHashSet) SszVector(tech.pegasys.teku.infrastructure.ssz.SszVector) IntSet(it.unimi.dsi.fastutil.ints.IntSet) BeaconStateCache(tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconStateCache) BeaconStateAltair(tech.pegasys.teku.spec.datastructures.state.beaconstate.versions.altair.BeaconStateAltair) IntArrayList(it.unimi.dsi.fastutil.ints.IntArrayList) SpecConfigAltair(tech.pegasys.teku.spec.config.SpecConfigAltair) SyncAggregate(tech.pegasys.teku.spec.datastructures.blocks.blockbody.versions.altair.SyncAggregate) BeaconState(tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState) HashMap(java.util.HashMap) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) SszPublicKey(tech.pegasys.teku.spec.datastructures.type.SszPublicKey) UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) MathHelpers.bytesToUInt64(tech.pegasys.teku.spec.logic.common.helpers.MathHelpers.bytesToUInt64) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) HashMap(java.util.HashMap) Collectors.toUnmodifiableMap(java.util.stream.Collectors.toUnmodifiableMap) Map(java.util.Map) MutableBeaconStateAltair(tech.pegasys.teku.spec.datastructures.state.beaconstate.versions.altair.MutableBeaconStateAltair) BeaconStateAltair(tech.pegasys.teku.spec.datastructures.state.beaconstate.versions.altair.BeaconStateAltair)

Example 3 with SyncCommittee

use of tech.pegasys.teku.spec.datastructures.state.SyncCommittee in project teku by ConsenSys.

the class BeaconStateAccessorsAltair method getNextSyncCommittee.

/**
 * Return the *next* sync committee for a given state.
 *
 * <p>SyncCommittee contains an aggregate pubkey that enables resource-constrained clients to save
 * some computation when verifying the sync committee's signature.
 *
 * <p>SyncCommittee can also contain duplicate pubkeys, when {@link
 * #getNextSyncCommitteeIndices(BeaconState)} returns duplicate indices. Implementations must take
 * care when handling optimizations relating to aggregation and verification in the presence of
 * duplicates.
 *
 * <p>Note: This function should only be called at sync committee period boundaries by {@link
 * tech.pegasys.teku.spec.logic.common.statetransition.epoch.EpochProcessor#processSyncCommitteeUpdates(MutableBeaconState)}
 * as {@link #getNextSyncCommitteeIndices(BeaconState)} is not stable within a given period.
 *
 * @param state the state to get the sync committee for
 * @return the SyncCommittee
 */
public SyncCommittee getNextSyncCommittee(final BeaconState state) {
    final IntList indices = getNextSyncCommitteeIndices(state);
    final List<BLSPublicKey> pubkeys = indices.intStream().mapToObj(index -> getValidatorPubKey(state, UInt64.valueOf(index)).orElseThrow()).collect(toList());
    final BLSPublicKey aggregatePubkey = BLSPublicKey.aggregate(pubkeys);
    return state.getBeaconStateSchema().getNextSyncCommitteeSchemaOrThrow().create(pubkeys.stream().map(SszPublicKey::new).collect(toList()), new SszPublicKey(aggregatePubkey));
}
Also used : SszList(tech.pegasys.teku.infrastructure.ssz.SszList) ParticipationFlags(tech.pegasys.teku.spec.constants.ParticipationFlags) SszPublicKey(tech.pegasys.teku.spec.datastructures.type.SszPublicKey) BeaconStateAccessors(tech.pegasys.teku.spec.logic.common.helpers.BeaconStateAccessors) ArrayList(java.util.ArrayList) AttestationData(tech.pegasys.teku.spec.datastructures.operations.AttestationData) UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) Bytes32(org.apache.tuweni.bytes.Bytes32) ByteUtil(tech.pegasys.teku.infrastructure.unsigned.ByteUtil) Domain(tech.pegasys.teku.spec.constants.Domain) Validator(tech.pegasys.teku.spec.datastructures.state.Validator) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) MathHelpers.integerSquareRoot(tech.pegasys.teku.spec.logic.common.helpers.MathHelpers.integerSquareRoot) Predicates(tech.pegasys.teku.spec.logic.common.helpers.Predicates) Hash(tech.pegasys.teku.infrastructure.crypto.Hash) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) MutableBeaconState(tech.pegasys.teku.spec.datastructures.state.beaconstate.MutableBeaconState) Collectors.toList(java.util.stream.Collectors.toList) MathHelpers.uint64ToBytes(tech.pegasys.teku.spec.logic.common.helpers.MathHelpers.uint64ToBytes) List(java.util.List) IntList(it.unimi.dsi.fastutil.ints.IntList) BeaconStateCache(tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconStateCache) Checkpoint(tech.pegasys.teku.spec.datastructures.state.Checkpoint) IntArrayList(it.unimi.dsi.fastutil.ints.IntArrayList) SpecConfigAltair(tech.pegasys.teku.spec.config.SpecConfigAltair) BeaconState(tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState) SszPublicKey(tech.pegasys.teku.spec.datastructures.type.SszPublicKey) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) IntList(it.unimi.dsi.fastutil.ints.IntList)

Example 4 with SyncCommittee

use of tech.pegasys.teku.spec.datastructures.state.SyncCommittee in project teku by ConsenSys.

the class ChainDataProviderTest method setupAltairState.

private ChainDataProvider setupAltairState() {
    final Spec altair = TestSpecFactory.createMinimalAltair();
    final DataStructureUtil dataStructureUtil = new DataStructureUtil(altair);
    final ChainDataProvider provider = new ChainDataProvider(altair, recentChainData, mockCombinedChainDataClient);
    final SszList<tech.pegasys.teku.spec.datastructures.state.Validator> validators = dataStructureUtil.randomSszList(dataStructureUtil.getBeaconStateSchema().getValidatorsSchema(), 16, dataStructureUtil::randomValidator);
    final SyncCommittee currentSyncCommittee = dataStructureUtil.randomSyncCommittee(validators);
    final tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState internalState = dataStructureUtil.stateBuilderAltair().validators(validators).currentSyncCommittee(currentSyncCommittee).build();
    final tech.pegasys.teku.storage.client.ChainHead chainHead = tech.pegasys.teku.storage.client.ChainHead.create(StateAndBlockSummary.create(internalState));
    when(mockCombinedChainDataClient.getChainHead()).thenReturn(Optional.of(chainHead));
    return provider;
}
Also used : SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) Spec(tech.pegasys.teku.spec.Spec) DataStructureUtil(tech.pegasys.teku.spec.util.DataStructureUtil)

Example 5 with SyncCommittee

use of tech.pegasys.teku.spec.datastructures.state.SyncCommittee in project teku by ConsenSys.

the class SignedContributionAndProofValidator method validateWithState.

private SafeFuture<InternalValidationResult> validateWithState(final SignedContributionAndProof proof, final ContributionAndProof contributionAndProof, final SyncCommitteeContribution contribution, final SyncCommitteeUtil syncCommitteeUtil, final UniquenessKey uniquenessKey, final BeaconStateAltair state) {
    final BeaconStateAccessors beaconStateAccessors = spec.atSlot(contribution.getSlot()).beaconStateAccessors();
    final Optional<BLSPublicKey> aggregatorPublicKey = beaconStateAccessors.getValidatorPubKey(state, contributionAndProof.getAggregatorIndex());
    if (aggregatorPublicKey.isEmpty()) {
        return futureFailureResult("Rejecting proof because aggregator index %s is an unknown validator", contributionAndProof.getAggregatorIndex());
    }
    final UInt64 contributionEpoch = syncCommitteeUtil.getEpochForDutiesAtSlot(contribution.getSlot());
    // state.current_sync_committee.pubkeys.
    if (!isInSyncSubcommittee(syncCommitteeUtil, contribution, state, contributionEpoch, contributionAndProof.getAggregatorIndex())) {
        return futureFailureResult("Rejecting proof because aggregator index %s is not in the current sync subcommittee", contributionAndProof.getAggregatorIndex());
    }
    // contribution.slot, contribution_and_proof.selection_proof) returns True.
    if (!syncCommitteeUtil.isSyncCommitteeAggregator(contributionAndProof.getSelectionProof())) {
        return futureFailureResult("Rejecting proof because selection proof %s is not an aggregator", contributionAndProof.getSelectionProof());
    }
    final AsyncBatchBLSSignatureVerifier signatureVerifier = new AsyncBatchBLSSignatureVerifier(this.signatureVerifier);
    // [REJECT] The contribution_and_proof.selection_proof is a valid signature of the
    // contribution.slot by the validator with index
    // contribution_and_proof.aggregator_index.
    final Bytes signingRoot = syncCommitteeUtil.getSyncAggregatorSelectionDataSigningRoot(syncCommitteeUtil.createSyncAggregatorSelectionData(contribution.getSlot(), contribution.getSubcommitteeIndex()), state.getForkInfo());
    if (!signatureVerifier.verify(aggregatorPublicKey.get(), signingRoot, contributionAndProof.getSelectionProof())) {
        return futureFailureResult("Rejecting proof at slot %s for subcommittee index %s because selection proof is invalid", contribution.getSlot(), contribution.getSubcommitteeIndex());
    }
    // valid.
    if (!signatureVerifier.verify(aggregatorPublicKey.get(), syncCommitteeUtil.getContributionAndProofSigningRoot(state, contributionAndProof), proof.getSignature())) {
        return futureFailureResult("Rejecting proof %s because aggregator signature is invalid", proof.getSignature());
    }
    final SpecConfigAltair config = SpecConfigAltair.required(spec.getSpecConfig(contributionEpoch));
    final SyncCommittee syncCommittee = syncCommitteeUtil.getSyncCommittee(state, contributionEpoch);
    final int subcommitteeSize = config.getSyncCommitteeSize() / SYNC_COMMITTEE_SUBNET_COUNT;
    // [REJECT] The aggregate signature is valid for the message beacon_block_root and
    // aggregate pubkey derived from the participation info in aggregation_bits for the
    // subcommittee specified by the subcommittee_index.
    final List<BLSPublicKey> contributorPublicKeys = contribution.getAggregationBits().streamAllSetBits().mapToObj(participantIndex -> getParticipantPublicKey(state, syncCommittee, contribution, subcommitteeSize, participantIndex)).collect(Collectors.toList());
    if (!signatureVerifier.verify(contributorPublicKeys, syncCommitteeUtil.getSyncCommitteeMessageSigningRoot(contribution.getBeaconBlockRoot(), contributionEpoch, state.getForkInfo()), contribution.getSignature())) {
        return futureFailureResult("Rejecting proof because aggregate signature %s is invalid", contribution.getSignature());
    }
    return signatureVerifier.batchVerify().thenApply(signatureValid -> {
        if (!signatureValid) {
            return failureResult("Rejecting proof with signature %s because batch signature check failed", contribution.getSignature());
        }
        if (!seenIndices.add(uniquenessKey)) {
            // Got added by another thread while we were validating it
            return IGNORE;
        }
        return ACCEPT;
    });
}
Also used : AsyncBLSSignatureVerifier(tech.pegasys.teku.spec.logic.common.util.AsyncBLSSignatureVerifier) TimeProvider(tech.pegasys.teku.infrastructure.time.TimeProvider) SafeFuture(tech.pegasys.teku.infrastructure.async.SafeFuture) BeaconStateAccessors(tech.pegasys.teku.spec.logic.common.helpers.BeaconStateAccessors) IGNORE(tech.pegasys.teku.statetransition.validation.InternalValidationResult.IGNORE) Bytes(org.apache.tuweni.bytes.Bytes) ContributionAndProof(tech.pegasys.teku.spec.datastructures.operations.versions.altair.ContributionAndProof) SYNC_COMMITTEE_SUBNET_COUNT(tech.pegasys.teku.spec.constants.NetworkConstants.SYNC_COMMITTEE_SUBNET_COUNT) LimitedSet(tech.pegasys.teku.infrastructure.collections.LimitedSet) FormatMethod(com.google.errorprone.annotations.FormatMethod) SyncCommitteeUtil(tech.pegasys.teku.spec.logic.common.util.SyncCommitteeUtil) UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) Spec(tech.pegasys.teku.spec.Spec) ACCEPT(tech.pegasys.teku.statetransition.validation.InternalValidationResult.ACCEPT) SyncCommitteeContribution(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SyncCommitteeContribution) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) Set(java.util.Set) ValidationResultCode(tech.pegasys.teku.statetransition.validation.ValidationResultCode) Collectors(java.util.stream.Collectors) SignedContributionAndProof(tech.pegasys.teku.spec.datastructures.operations.versions.altair.SignedContributionAndProof) Objects(java.util.Objects) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) List(java.util.List) VALID_CONTRIBUTION_AND_PROOF_SET_SIZE(tech.pegasys.teku.spec.config.Constants.VALID_CONTRIBUTION_AND_PROOF_SET_SIZE) Logger(org.apache.logging.log4j.Logger) RecentChainData(tech.pegasys.teku.storage.client.RecentChainData) Optional(java.util.Optional) AsyncBatchBLSSignatureVerifier(tech.pegasys.teku.spec.logic.common.util.AsyncBatchBLSSignatureVerifier) BeaconStateAltair(tech.pegasys.teku.spec.datastructures.state.beaconstate.versions.altair.BeaconStateAltair) LogManager(org.apache.logging.log4j.LogManager) InternalValidationResult(tech.pegasys.teku.statetransition.validation.InternalValidationResult) SpecConfigAltair(tech.pegasys.teku.spec.config.SpecConfigAltair) BeaconState(tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState) Bytes(org.apache.tuweni.bytes.Bytes) AsyncBatchBLSSignatureVerifier(tech.pegasys.teku.spec.logic.common.util.AsyncBatchBLSSignatureVerifier) BeaconStateAccessors(tech.pegasys.teku.spec.logic.common.helpers.BeaconStateAccessors) BLSPublicKey(tech.pegasys.teku.bls.BLSPublicKey) UInt64(tech.pegasys.teku.infrastructure.unsigned.UInt64) SyncCommittee(tech.pegasys.teku.spec.datastructures.state.SyncCommittee) SpecConfigAltair(tech.pegasys.teku.spec.config.SpecConfigAltair)

Aggregations

SyncCommittee (tech.pegasys.teku.spec.datastructures.state.SyncCommittee)7 UInt64 (tech.pegasys.teku.infrastructure.unsigned.UInt64)5 List (java.util.List)3 BLSPublicKey (tech.pegasys.teku.bls.BLSPublicKey)3 SpecConfigAltair (tech.pegasys.teku.spec.config.SpecConfigAltair)3 BeaconState (tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconState)3 IntArrayList (it.unimi.dsi.fastutil.ints.IntArrayList)2 IntList (it.unimi.dsi.fastutil.ints.IntList)2 ArrayList (java.util.ArrayList)2 Bytes (org.apache.tuweni.bytes.Bytes)2 Bytes32 (org.apache.tuweni.bytes.Bytes32)2 Hash (tech.pegasys.teku.infrastructure.crypto.Hash)2 Spec (tech.pegasys.teku.spec.Spec)2 Domain (tech.pegasys.teku.spec.constants.Domain)2 SYNC_COMMITTEE_SUBNET_COUNT (tech.pegasys.teku.spec.constants.NetworkConstants.SYNC_COMMITTEE_SUBNET_COUNT)2 ContributionAndProof (tech.pegasys.teku.spec.datastructures.operations.versions.altair.ContributionAndProof)2 SignedContributionAndProof (tech.pegasys.teku.spec.datastructures.operations.versions.altair.SignedContributionAndProof)2 BeaconStateCache (tech.pegasys.teku.spec.datastructures.state.beaconstate.BeaconStateCache)2 MutableBeaconState (tech.pegasys.teku.spec.datastructures.state.beaconstate.MutableBeaconState)2 SszPublicKey (tech.pegasys.teku.spec.datastructures.type.SszPublicKey)2