@@ -2,7 +2,7 @@ pub mod metadata_service;
22mod metrics;
33
44use std:: {
5- collections:: HashMap ,
5+ collections:: { HashMap , HashSet } ,
66 fmt:: Debug ,
77 future:: Future ,
88 num:: NonZeroUsize ,
@@ -31,11 +31,11 @@ use signature_collector::{
3131use slashing_protection:: { NotSafe , Safe , SlashingDatabase } ;
3232use slot_clock:: SlotClock ;
3333use ssv_types:: {
34- Cluster , ClusterId , ENCRYPTED_KEY_LENGTH , ValidatorIndex , ValidatorMetadata ,
34+ Cluster , ClusterId , CommitteeId , ENCRYPTED_KEY_LENGTH , ValidatorIndex , ValidatorMetadata ,
3535 consensus:: {
3636 BEACON_ROLE_AGGREGATOR , BEACON_ROLE_PROPOSER , BEACON_ROLE_SYNC_COMMITTEE_CONTRIBUTION ,
37- BeaconVote , Contribution , ContributionWrapper , Contributions , NoDataValidation , QbftData ,
38- ValidatorConsensusData , ValidatorDuty ,
37+ BeaconVote , BeaconVoteValidator , Contribution , ContributionWrapper , Contributions ,
38+ NoDataValidation , QbftData , ValidatorConsensusData , ValidatorDuty ,
3939 } ,
4040 msgid:: Role ,
4141 partial_sig:: PartialSignatureKind ,
@@ -228,7 +228,7 @@ impl<T: SlotClock, E: EthSpec> AnchorValidatorStore<T, E> {
228228 . map ( |validator| {
229229 let mut duties = 0 ;
230230 if let Some ( idx) = & validator. index {
231- if slot_metadata. attesting_validators . contains ( idx) {
231+ if slot_metadata. attesting_validator_indices . contains ( idx) {
232232 duties += 1 ;
233233 }
234234 if slot_metadata. sync_validators . contains ( idx) {
@@ -525,6 +525,45 @@ impl<T: SlotClock, E: EthSpec> AnchorValidatorStore<T, E> {
525525
526526 Ok ( signed_exit)
527527 }
528+
529+ fn create_beacon_vote_validator (
530+ & self ,
531+ slot : Slot ,
532+ validator_attestation_committees : HashMap < PublicKeyBytes , u64 > ,
533+ ) -> Box < BeaconVoteValidator < E > > {
534+ Box :: new ( BeaconVoteValidator :: new (
535+ slot,
536+ Arc :: clone ( & self . slashing_protection ) ,
537+ self . disable_slashing_protection ,
538+ self . spec . clone ( ) ,
539+ validator_attestation_committees,
540+ self . genesis_validators_root ,
541+ ) )
542+ }
543+
544+ fn get_attesting_validators_in_committee (
545+ & self ,
546+ metadata : & SlotMetadata < E > ,
547+ committee_id : CommitteeId ,
548+ ) -> HashMap < PublicKeyBytes , u64 > {
549+ let committee_validators = self
550+ . database
551+ . state ( )
552+ . metadata ( )
553+ . get_all_by ( & committee_id)
554+ . map ( |v| v. public_key )
555+ . collect :: < HashSet < _ > > ( ) ;
556+
557+ metadata
558+ . attesting_validator_committees
559+ . iter ( )
560+ . filter_map ( |( & pubkey, & index) | {
561+ committee_validators
562+ . contains ( & pubkey)
563+ . then_some ( ( pubkey, index) )
564+ } )
565+ . collect :: < HashMap < _ , _ > > ( )
566+ }
528567}
529568
530569/// # Arguments
@@ -609,8 +648,11 @@ struct SlotMetadata<E: EthSpec> {
609648 slot : Slot ,
610649 /// The BeaconVote we will use as initial QBFT data.
611650 beacon_vote : BeaconVote ,
612- /// All our validators that are attesting in this slot.
613- attesting_validators : Vec < ValidatorIndex > ,
651+ /// The indices of all our validators that are attesting in this slot.
652+ attesting_validator_indices : Vec < ValidatorIndex > ,
653+ /// The pubkeys of all our validators that are attesting in this slot, mapped to their
654+ /// attestation committee index.
655+ attesting_validator_committees : HashMap < PublicKeyBytes , u64 > ,
614656 /// All our validators that are in the sync committee for this slot.
615657 sync_validators : Vec < ValidatorIndex > ,
616658 /// All validators that are aggregator for this slot multiple times, and thus require special
@@ -909,6 +951,10 @@ impl<T: SlotClock, E: EthSpec> ValidatorStore for AnchorValidatorStore<T, E> {
909951 }
910952
911953 let ( validator, cluster) = self . get_validator_and_cluster ( validator_pubkey) ?;
954+ let slot_metadata = self . get_slot_metadata ( attestation. data ( ) . slot ) . await ?;
955+
956+ let validator_attestation_committees =
957+ self . get_attesting_validators_in_committee ( & slot_metadata, cluster. committee_id ( ) ) ;
912958
913959 let timer =
914960 metrics:: start_timer_vec ( & metrics:: CONSENSUS_TIMES , & [ metrics:: BEACON_VOTE ] ) ;
@@ -928,7 +974,10 @@ impl<T: SlotClock, E: EthSpec> ValidatorStore for AnchorValidatorStore<T, E> {
928974 source : attestation. data ( ) . source ,
929975 target : attestation. data ( ) . target ,
930976 } ,
931- Box :: new ( NoDataValidation ) ,
977+ self . create_beacon_vote_validator (
978+ attestation. data ( ) . slot ,
979+ validator_attestation_committees,
980+ ) ,
932981 start_time,
933982 & cluster,
934983 )
@@ -1246,6 +1295,9 @@ impl<T: SlotClock, E: EthSpec> ValidatorStore for AnchorValidatorStore<T, E> {
12461295 let ( validator, cluster) = self . get_validator_and_cluster ( * validator_pubkey) ?;
12471296 let metadata = self . get_slot_metadata ( slot) . await ?;
12481297
1298+ let validator_attestation_committees =
1299+ self . get_attesting_validators_in_committee ( & metadata, cluster. committee_id ( ) ) ;
1300+
12491301 let timer =
12501302 metrics:: start_timer_vec ( & metrics:: CONSENSUS_TIMES , & [ metrics:: BEACON_VOTE ] ) ;
12511303 let start_time = self
@@ -1258,7 +1310,7 @@ impl<T: SlotClock, E: EthSpec> ValidatorStore for AnchorValidatorStore<T, E> {
12581310 instance_height : slot. as_usize ( ) . into ( ) ,
12591311 } ,
12601312 metadata. beacon_vote . clone ( ) ,
1261- Box :: new ( NoDataValidation ) ,
1313+ self . create_beacon_vote_validator ( slot , validator_attestation_committees ) ,
12621314 start_time,
12631315 & cluster,
12641316 )
0 commit comments