Electra attestation interfaces (#13937)

* config values

* block protos

* get_committee_indices

* proto and ssz

* attestation interface

* Revert "Auxiliary commit to revert individual files from deadb2183723511721b3288c7168808a4fa97c64"

This reverts commit 32ad5009537bc5ec0e6caf9f52143d380d00be85.

* todos

* get_attesting_indices

* Revert "Auxiliary commit to revert individual files from dd2789723f90b15eb1f874b561d88d11dcc9c0bf"

This reverts commit f39644ed3cb6f3964fc6c86fdf4bd5de2a9668c8.

* beacon spec changes

* Fix pending attestation. Build ok

* Electra: add electra version

* Electra: consensus types

* gocognit exclusion

* @potuz's suggestion

* build fix

* interfaces for indexed att and slashing

* indexed att usage

* BuildSignedBeaconBlockFromExecutionPayload

* slashing usage

* grpc stubs

* remove unused methods

* Electra attestation interfaces

* cleanup

* tests

* make linter happy

* simple casting

* test fixes

* Fix spectest failures

* Regen pb and ssz files

* Handle "not ok" type assertion cases

* Setters that check version should always return an error. SetAttesterSlashings and SetAttestations

* gofmt

* Fix TestMinSpanChunksSlice_CheckSlashable

---------

Co-authored-by: terence tsao <terence@prysmaticlabs.com>
Co-authored-by: Preston Van Loon <preston@pvl.dev>
This commit is contained in:
Radosław Kapka
2024-05-01 06:29:38 +09:00
committed by GitHub
parent ae16d5f52c
commit 2c5a2e8ec7
174 changed files with 3463 additions and 1792 deletions

View File

@@ -401,7 +401,7 @@ func (s *Service) saveOrphanedOperations(ctx context.Context, orphanedRoot [32]b
}
for _, a := range orphanedBlk.Block().Body().Attestations() {
// if the attestation is one epoch older, it wouldn't been useful to save it.
if a.Data.Slot+params.BeaconConfig().SlotsPerEpoch < s.CurrentSlot() {
if a.GetData().Slot+params.BeaconConfig().SlotsPerEpoch < s.CurrentSlot() {
continue
}
if helpers.IsAggregated(a) {

View File

@@ -13,6 +13,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/operations/blstoexec"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/blocks"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpbv1 "github.com/prysmaticlabs/prysm/v5/proto/eth/v1"
@@ -312,14 +313,14 @@ func TestSaveOrphanedAtts(t *testing.T) {
require.NoError(t, service.saveOrphanedOperations(ctx, r3, r4))
require.Equal(t, 3, service.cfg.AttPool.AggregatedAttestationCount())
wantAtts := []*ethpb.Attestation{
wantAtts := []interfaces.Attestation{
blk3.Block.Body.Attestations[0],
blk2.Block.Body.Attestations[0],
blk1.Block.Body.Attestations[0],
}
atts := service.cfg.AttPool.AggregatedAttestations()
sort.Slice(atts, func(i, j int) bool {
return atts[i].Data.Slot > atts[j].Data.Slot
return atts[i].GetData().Slot > atts[j].GetData().Slot
})
require.DeepEqual(t, wantAtts, atts)
}
@@ -389,14 +390,14 @@ func TestSaveOrphanedOps(t *testing.T) {
require.NoError(t, service.saveOrphanedOperations(ctx, r3, r4))
require.Equal(t, 3, service.cfg.AttPool.AggregatedAttestationCount())
wantAtts := []*ethpb.Attestation{
wantAtts := []interfaces.Attestation{
blk3.Block.Body.Attestations[0],
blk2.Block.Body.Attestations[0],
blk1.Block.Body.Attestations[0],
}
atts := service.cfg.AttPool.AggregatedAttestations()
sort.Slice(atts, func(i, j int) bool {
return atts[i].Data.Slot > atts[j].Data.Slot
return atts[i].GetData().Slot > atts[j].GetData().Slot
})
require.DeepEqual(t, wantAtts, atts)
require.Equal(t, 1, len(service.cfg.SlashingPool.PendingProposerSlashings(ctx, st, false)))
@@ -517,14 +518,14 @@ func TestSaveOrphanedAtts_DoublyLinkedTrie(t *testing.T) {
require.NoError(t, service.saveOrphanedOperations(ctx, r3, r4))
require.Equal(t, 3, service.cfg.AttPool.AggregatedAttestationCount())
wantAtts := []*ethpb.Attestation{
wantAtts := []interfaces.Attestation{
blk3.Block.Body.Attestations[0],
blk2.Block.Body.Attestations[0],
blk1.Block.Body.Attestations[0],
}
atts := service.cfg.AttPool.AggregatedAttestations()
sort.Slice(atts, func(i, j int) bool {
return atts[i].Data.Slot > atts[j].Data.Slot
return atts[i].GetData().Slot > atts[j].GetData().Slot
})
require.DeepEqual(t, wantAtts, atts)
}

View File

@@ -369,6 +369,6 @@ func reportEpochMetrics(ctx context.Context, postState, headState state.BeaconSt
func reportAttestationInclusion(blk interfaces.ReadOnlyBeaconBlock) {
for _, att := range blk.Body().Attestations() {
attestationInclusionDelay.Observe(float64(blk.Slot() - att.Data.Slot))
attestationInclusionDelay.Observe(float64(blk.Slot() - att.GetData().Slot))
}
}

View File

@@ -6,6 +6,7 @@ import (
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation"
@@ -36,17 +37,17 @@ import (
//
// # Update latest messages for attesting indices
// update_latest_messages(store, indexed_attestation.attesting_indices, attestation)
func (s *Service) OnAttestation(ctx context.Context, a *ethpb.Attestation, disparity time.Duration) error {
func (s *Service) OnAttestation(ctx context.Context, a interfaces.Attestation, disparity time.Duration) error {
ctx, span := trace.StartSpan(ctx, "blockChain.onAttestation")
defer span.End()
if err := helpers.ValidateNilAttestation(a); err != nil {
return err
}
if err := helpers.ValidateSlotTargetEpoch(a.Data); err != nil {
if err := helpers.ValidateSlotTargetEpoch(a.GetData()); err != nil {
return err
}
tgt := ethpb.CopyCheckpoint(a.Data.Target)
tgt := ethpb.CopyCheckpoint(a.GetData().Target)
// Note that target root check is ignored here because it was performed in sync's validation pipeline:
// validate_aggregate_proof.go and validate_beacon_attestation.go
@@ -67,7 +68,7 @@ func (s *Service) OnAttestation(ctx context.Context, a *ethpb.Attestation, dispa
}
// Verify attestation beacon block is known and not from the future.
if err := s.verifyBeaconBlock(ctx, a.Data); err != nil {
if err := s.verifyBeaconBlock(ctx, a.GetData()); err != nil {
return errors.Wrap(err, "could not verify attestation beacon block")
}
@@ -75,12 +76,12 @@ func (s *Service) OnAttestation(ctx context.Context, a *ethpb.Attestation, dispa
// validate_aggregate_proof.go and validate_beacon_attestation.go
// Verify attestations can only affect the fork choice of subsequent slots.
if err := slots.VerifyTime(genesisTime, a.Data.Slot+1, disparity); err != nil {
if err := slots.VerifyTime(genesisTime, a.GetData().Slot+1, disparity); err != nil {
return err
}
// Use the target state to verify attesting indices are valid.
committee, err := helpers.BeaconCommitteeFromState(ctx, baseState, a.Data.Slot, a.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, baseState, a.GetData().Slot, a.GetData().CommitteeIndex)
if err != nil {
return err
}
@@ -97,7 +98,7 @@ func (s *Service) OnAttestation(ctx context.Context, a *ethpb.Attestation, dispa
// We assume trusted attestation in this function has verified signature.
// Update forkchoice store with the new attestation for updating weight.
s.cfg.ForkChoiceStore.ProcessAttestation(ctx, indexedAtt.AttestingIndices, bytesutil.ToBytes32(a.Data.BeaconBlockRoot), a.Data.Target.Epoch)
s.cfg.ForkChoiceStore.ProcessAttestation(ctx, indexedAtt.GetAttestingIndices(), bytesutil.ToBytes32(a.GetData().BeaconBlockRoot), a.GetData().Target.Epoch)
return nil
}

View File

@@ -9,6 +9,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/transition"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -73,7 +74,7 @@ func TestStore_OnAttestation_ErrorConditions(t *testing.T) {
tests := []struct {
name string
a *ethpb.Attestation
a interfaces.Attestation
wantedErr string
}{
{

View File

@@ -366,17 +366,17 @@ func (s *Service) handleEpochBoundary(ctx context.Context, slot primitives.Slot,
func (s *Service) handleBlockAttestations(ctx context.Context, blk interfaces.ReadOnlyBeaconBlock, st state.BeaconState) error {
// Feed in block's attestations to fork choice store.
for _, a := range blk.Body().Attestations() {
committee, err := helpers.BeaconCommitteeFromState(ctx, st, a.Data.Slot, a.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, st, a.GetData().Slot, a.GetData().CommitteeIndex)
if err != nil {
return err
}
indices, err := attestation.AttestingIndices(a.AggregationBits, committee)
indices, err := attestation.AttestingIndices(a.GetAggregationBits(), committee)
if err != nil {
return err
}
r := bytesutil.ToBytes32(a.Data.BeaconBlockRoot)
r := bytesutil.ToBytes32(a.GetData().BeaconBlockRoot)
if s.cfg.ForkChoiceStore.HasNode(r) {
s.cfg.ForkChoiceStore.ProcessAttestation(ctx, indices, r, a.Data.Target.Epoch)
s.cfg.ForkChoiceStore.ProcessAttestation(ctx, indices, r, a.GetData().Target.Epoch)
} else if err := s.cfg.AttPool.SaveBlockAttestation(a); err != nil {
return err
}
@@ -387,7 +387,7 @@ func (s *Service) handleBlockAttestations(ctx context.Context, blk interfaces.Re
// InsertSlashingsToForkChoiceStore inserts attester slashing indices to fork choice store.
// To call this function, it's caller's responsibility to ensure the slashing object is valid.
// This function requires a write lock on forkchoice.
func (s *Service) InsertSlashingsToForkChoiceStore(ctx context.Context, slashings []*ethpb.AttesterSlashing) {
func (s *Service) InsertSlashingsToForkChoiceStore(ctx context.Context, slashings []interfaces.AttesterSlashing) {
for _, slashing := range slashings {
indices := blocks.SlashableAttesterIndices(slashing)
for _, index := range indices {

View File

@@ -824,7 +824,10 @@ func TestRemoveBlockAttestationsInPool(t *testing.T) {
require.NoError(t, service.cfg.BeaconDB.SaveStateSummary(ctx, &ethpb.StateSummary{Root: r[:]}))
require.NoError(t, service.cfg.BeaconDB.SaveGenesisBlockRoot(ctx, r))
atts := b.Block.Body.Attestations
atts := make([]interfaces.Attestation, len(b.Block.Body.Attestations))
for i, a := range b.Block.Body.Attestations {
atts[i] = a
}
require.NoError(t, service.cfg.AttPool.SaveAggregatedAttestations(atts))
wsb, err := consensusblocks.NewSignedBeaconBlock(b)
require.NoError(t, err)
@@ -2010,12 +2013,12 @@ func TestOnBlock_HandleBlockAttestations(t *testing.T) {
require.Equal(t, 1, len(wsb.Block().Body().Attestations()))
a := wsb.Block().Body().Attestations()[0]
r := bytesutil.ToBytes32(a.Data.BeaconBlockRoot)
r := bytesutil.ToBytes32(a.GetData().BeaconBlockRoot)
require.Equal(t, true, service.cfg.ForkChoiceStore.HasNode(r))
require.Equal(t, 1, len(wsb.Block().Body().Attestations()))
a3 := wsb3.Block().Body().Attestations()[0]
r3 := bytesutil.ToBytes32(a3.Data.BeaconBlockRoot)
r3 := bytesutil.ToBytes32(a3.GetData().BeaconBlockRoot)
require.Equal(t, false, service.cfg.ForkChoiceStore.HasNode(r3))
require.NoError(t, service.handleBlockAttestations(ctx, wsb.Block(), st)) // fine to use the same committee as st

View File

@@ -10,6 +10,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -31,7 +32,7 @@ type AttestationStateFetcher interface {
// AttestationReceiver interface defines the methods of chain service receive and processing new attestations.
type AttestationReceiver interface {
AttestationStateFetcher
VerifyLmdFfgConsistency(ctx context.Context, att *ethpb.Attestation) error
VerifyLmdFfgConsistency(ctx context.Context, att interfaces.Attestation) error
InForkchoice([32]byte) bool
}
@@ -51,13 +52,13 @@ func (s *Service) AttestationTargetState(ctx context.Context, target *ethpb.Chec
}
// VerifyLmdFfgConsistency verifies that attestation's LMD and FFG votes are consistency to each other.
func (s *Service) VerifyLmdFfgConsistency(ctx context.Context, a *ethpb.Attestation) error {
r, err := s.TargetRootForEpoch([32]byte(a.Data.BeaconBlockRoot), a.Data.Target.Epoch)
func (s *Service) VerifyLmdFfgConsistency(ctx context.Context, a interfaces.Attestation) error {
r, err := s.TargetRootForEpoch([32]byte(a.GetData().BeaconBlockRoot), a.GetData().Target.Epoch)
if err != nil {
return err
}
if !bytes.Equal(a.Data.Target.Root, r[:]) {
return fmt.Errorf("FFG and LMD votes are not consistent, block root: %#x, target root: %#x, canonical target root: %#x", a.Data.BeaconBlockRoot, a.Data.Target.Root, r)
if !bytes.Equal(a.GetData().Target.Root, r[:]) {
return fmt.Errorf("FFG and LMD votes are not consistent, block root: %#x, target root: %#x, canonical target root: %#x", a.GetData().BeaconBlockRoot, a.GetData().Target.Root, r)
}
return nil
}
@@ -170,13 +171,13 @@ func (s *Service) processAttestations(ctx context.Context, disparity time.Durati
// Based on the spec, don't process the attestation until the subsequent slot.
// This delays consideration in the fork choice until their slot is in the past.
// https://github.com/ethereum/consensus-specs/blob/dev/specs/phase0/fork-choice.md#validate_on_attestation
nextSlot := a.Data.Slot + 1
nextSlot := a.GetData().Slot + 1
if err := slots.VerifyTime(uint64(s.genesisTime.Unix()), nextSlot, disparity); err != nil {
continue
}
hasState := s.cfg.BeaconDB.HasStateSummary(ctx, bytesutil.ToBytes32(a.Data.BeaconBlockRoot))
hasBlock := s.hasBlock(ctx, bytesutil.ToBytes32(a.Data.BeaconBlockRoot))
hasState := s.cfg.BeaconDB.HasStateSummary(ctx, bytesutil.ToBytes32(a.GetData().BeaconBlockRoot))
hasBlock := s.hasBlock(ctx, bytesutil.ToBytes32(a.GetData().BeaconBlockRoot))
if !(hasState && hasBlock) {
continue
}
@@ -185,17 +186,17 @@ func (s *Service) processAttestations(ctx context.Context, disparity time.Durati
log.WithError(err).Error("Could not delete fork choice attestation in pool")
}
if !helpers.VerifyCheckpointEpoch(a.Data.Target, s.genesisTime) {
if !helpers.VerifyCheckpointEpoch(a.GetData().Target, s.genesisTime) {
continue
}
if err := s.receiveAttestationNoPubsub(ctx, a, disparity); err != nil {
log.WithFields(logrus.Fields{
"slot": a.Data.Slot,
"committeeIndex": a.Data.CommitteeIndex,
"beaconBlockRoot": fmt.Sprintf("%#x", bytesutil.Trunc(a.Data.BeaconBlockRoot)),
"targetRoot": fmt.Sprintf("%#x", bytesutil.Trunc(a.Data.Target.Root)),
"aggregationCount": a.AggregationBits.Count(),
"slot": a.GetData().Slot,
"committeeIndex": a.GetData().CommitteeIndex,
"beaconBlockRoot": fmt.Sprintf("%#x", bytesutil.Trunc(a.GetData().BeaconBlockRoot)),
"targetRoot": fmt.Sprintf("%#x", bytesutil.Trunc(a.GetData().Target.Root)),
"aggregationCount": a.GetAggregationBits().Count(),
}).WithError(err).Warn("Could not process attestation for fork choice")
}
}
@@ -206,7 +207,7 @@ func (s *Service) processAttestations(ctx context.Context, disparity time.Durati
// 1. Validate attestation, update validator's latest vote
// 2. Apply fork choice to the processed attestation
// 3. Save latest head info
func (s *Service) receiveAttestationNoPubsub(ctx context.Context, att *ethpb.Attestation, disparity time.Duration) error {
func (s *Service) receiveAttestationNoPubsub(ctx context.Context, att interfaces.Attestation, disparity time.Duration) error {
ctx, span := trace.StartSpan(ctx, "beacon-chain.blockchain.receiveAttestationNoPubsub")
defer span.End()

View File

@@ -10,6 +10,7 @@ import (
forkchoicetypes "github.com/prysmaticlabs/prysm/v5/beacon-chain/forkchoice/types"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/blocks"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -83,7 +84,11 @@ func TestProcessAttestations_Ok(t *testing.T) {
state, blkRoot, err := prepareForkchoiceState(ctx, 0, tRoot, tRoot, params.BeaconConfig().ZeroHash, ojc, ofc)
require.NoError(t, err)
require.NoError(t, service.cfg.ForkChoiceStore.InsertNode(ctx, state, blkRoot))
require.NoError(t, service.cfg.AttPool.SaveForkchoiceAttestations(atts))
attsToSave := make([]interfaces.Attestation, len(atts))
for i, a := range atts {
attsToSave[i] = a
}
require.NoError(t, service.cfg.AttPool.SaveForkchoiceAttestations(attsToSave))
service.processAttestations(ctx, 0)
require.Equal(t, 0, len(service.cfg.AttPool.ForkchoiceAttestations()))
require.LogsDoNotContain(t, hook, "Could not process attestation for fork choice")
@@ -121,7 +126,11 @@ func TestService_ProcessAttestationsAndUpdateHead(t *testing.T) {
// Generate attestations for this block in Slot 1
atts, err := util.GenerateAttestations(copied, pks, 1, 1, false)
require.NoError(t, err)
require.NoError(t, service.cfg.AttPool.SaveForkchoiceAttestations(atts))
attsToSave := make([]interfaces.Attestation, len(atts))
for i, a := range atts {
attsToSave[i] = a
}
require.NoError(t, service.cfg.AttPool.SaveForkchoiceAttestations(attsToSave))
// Verify the target is in forkchoice
require.Equal(t, true, fcs.HasNode(bytesutil.ToBytes32(atts[0].Data.BeaconBlockRoot)))
require.Equal(t, tRoot, bytesutil.ToBytes32(atts[0].Data.BeaconBlockRoot))

View File

@@ -52,7 +52,7 @@ type BlobReceiver interface {
// SlashingReceiver interface defines the methods of chain service for receiving validated slashing over the wire.
type SlashingReceiver interface {
ReceiveAttesterSlashing(ctx context.Context, slashings *ethpb.AttesterSlashing)
ReceiveAttesterSlashing(ctx context.Context, slashing interfaces.AttesterSlashing)
}
// ReceiveBlock is a function that defines the operations (minus pubsub)
@@ -295,10 +295,10 @@ func (s *Service) HasBlock(ctx context.Context, root [32]byte) bool {
}
// ReceiveAttesterSlashing receives an attester slashing and inserts it to forkchoice
func (s *Service) ReceiveAttesterSlashing(ctx context.Context, slashing *ethpb.AttesterSlashing) {
func (s *Service) ReceiveAttesterSlashing(ctx context.Context, slashing interfaces.AttesterSlashing) {
s.cfg.ForkChoiceStore.Lock()
defer s.cfg.ForkChoiceStore.Unlock()
s.InsertSlashingsToForkChoiceStore(ctx, []*ethpb.AttesterSlashing{slashing})
s.InsertSlashingsToForkChoiceStore(ctx, []interfaces.AttesterSlashing{slashing})
}
// prunePostBlockOperationPools only runs on new head otherwise should return a nil.
@@ -479,7 +479,7 @@ func (s *Service) sendBlockAttestationsToSlasher(signed interfaces.ReadOnlySigne
// is done in the background to avoid adding more load to this critical code path.
ctx := context.TODO()
for _, att := range signed.Block().Body().Attestations() {
committee, err := helpers.BeaconCommitteeFromState(ctx, preState, att.Data.Slot, att.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, preState, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
log.WithError(err).Error("Could not get attestation committee")
return

View File

@@ -20,6 +20,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/startup"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state/stategen"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/require"
"google.golang.org/protobuf/proto"
@@ -49,7 +50,7 @@ func (mb *mockBroadcaster) Broadcast(_ context.Context, _ proto.Message) error {
return nil
}
func (mb *mockBroadcaster) BroadcastAttestation(_ context.Context, _ uint64, _ *ethpb.Attestation) error {
func (mb *mockBroadcaster) BroadcastAttestation(_ context.Context, _ uint64, _ interfaces.Attestation) error {
mb.broadcastCalled = true
return nil
}

View File

@@ -414,8 +414,8 @@ func (*ChainService) HeadGenesisValidatorsRoot() [32]byte {
}
// VerifyLmdFfgConsistency mocks VerifyLmdFfgConsistency and always returns nil.
func (*ChainService) VerifyLmdFfgConsistency(_ context.Context, a *ethpb.Attestation) error {
if !bytes.Equal(a.Data.BeaconBlockRoot, a.Data.Target.Root) {
func (*ChainService) VerifyLmdFfgConsistency(_ context.Context, a interfaces.Attestation) error {
if !bytes.Equal(a.GetData().BeaconBlockRoot, a.GetData().Target.Root) {
return errors.New("LMD and FFG miss matched")
}
return nil
@@ -495,7 +495,7 @@ func (s *ChainService) UpdateHead(ctx context.Context, slot primitives.Slot) {
}
// ReceiveAttesterSlashing mocks the same method in the chain service.
func (*ChainService) ReceiveAttesterSlashing(context.Context, *ethpb.AttesterSlashing) {}
func (*ChainService) ReceiveAttesterSlashing(context.Context, interfaces.AttesterSlashing) {}
// IsFinalized mocks the same method in the chain service.
func (s *ChainService) IsFinalized(_ context.Context, blockRoot [32]byte) bool {

View File

@@ -48,7 +48,7 @@ func ProcessAttestationsNoVerifySignature(
func ProcessAttestationNoVerifySignature(
ctx context.Context,
beaconState state.BeaconState,
att *ethpb.Attestation,
att interfaces.Attestation,
totalBalance uint64,
) (state.BeaconState, error) {
ctx, span := trace.StartSpan(ctx, "altair.ProcessAttestationNoVerifySignature")
@@ -58,24 +58,24 @@ func ProcessAttestationNoVerifySignature(
return nil, err
}
delay, err := beaconState.Slot().SafeSubSlot(att.Data.Slot)
delay, err := beaconState.Slot().SafeSubSlot(att.GetData().Slot)
if err != nil {
return nil, fmt.Errorf("att slot %d can't be greater than state slot %d", att.Data.Slot, beaconState.Slot())
return nil, fmt.Errorf("att slot %d can't be greater than state slot %d", att.GetData().Slot, beaconState.Slot())
}
participatedFlags, err := AttestationParticipationFlagIndices(beaconState, att.Data, delay)
participatedFlags, err := AttestationParticipationFlagIndices(beaconState, att.GetData(), delay)
if err != nil {
return nil, err
}
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.Data.Slot, att.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return nil, err
}
indices, err := attestation.AttestingIndices(att.AggregationBits, committee)
indices, err := attestation.AttestingIndices(att.GetAggregationBits(), committee)
if err != nil {
return nil, err
}
return SetParticipationAndRewardProposer(ctx, beaconState, att.Data.Target.Epoch, indices, participatedFlags, totalBalance)
return SetParticipationAndRewardProposer(ctx, beaconState, att.GetData().Target.Epoch, indices, participatedFlags, totalBalance)
}
// SetParticipationAndRewardProposer retrieves and sets the epoch participation bits in state. Based on the epoch participation, it rewards

View File

@@ -46,7 +46,7 @@ func ProcessAttestationsNoVerifySignature(
func VerifyAttestationNoVerifySignature(
ctx context.Context,
beaconState state.ReadOnlyBeaconState,
att *ethpb.Attestation,
att interfaces.Attestation,
) error {
ctx, span := trace.StartSpan(ctx, "core.VerifyAttestationNoVerifySignature")
defer span.End()
@@ -56,7 +56,7 @@ func VerifyAttestationNoVerifySignature(
}
currEpoch := time.CurrentEpoch(beaconState)
prevEpoch := time.PrevEpoch(beaconState)
data := att.Data
data := att.GetData()
if data.Target.Epoch != prevEpoch && data.Target.Epoch != currEpoch {
return fmt.Errorf(
"expected target epoch (%d) to be the previous epoch (%d) or the current epoch (%d)",
@@ -76,11 +76,11 @@ func VerifyAttestationNoVerifySignature(
}
}
if err := helpers.ValidateSlotTargetEpoch(att.Data); err != nil {
if err := helpers.ValidateSlotTargetEpoch(att.GetData()); err != nil {
return err
}
s := att.Data.Slot
s := att.GetData().Slot
minInclusionCheck := s+params.BeaconConfig().MinAttestationInclusionDelay <= beaconState.Slot()
if !minInclusionCheck {
return fmt.Errorf(
@@ -102,13 +102,13 @@ func VerifyAttestationNoVerifySignature(
)
}
}
activeValidatorCount, err := helpers.ActiveValidatorCount(ctx, beaconState, att.Data.Target.Epoch)
activeValidatorCount, err := helpers.ActiveValidatorCount(ctx, beaconState, att.GetData().Target.Epoch)
if err != nil {
return err
}
c := helpers.SlotCommitteeCount(activeValidatorCount)
if uint64(att.Data.CommitteeIndex) >= c {
return fmt.Errorf("committee index %d >= committee count %d", att.Data.CommitteeIndex, c)
if uint64(att.GetData().CommitteeIndex) >= c {
return fmt.Errorf("committee index %d >= committee count %d", att.GetData().CommitteeIndex, c)
}
if err := helpers.VerifyAttestationBitfieldLengths(ctx, beaconState, att); err != nil {
@@ -116,7 +116,7 @@ func VerifyAttestationNoVerifySignature(
}
// Verify attesting indices are correct.
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.Data.Slot, att.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return err
}
@@ -133,7 +133,7 @@ func VerifyAttestationNoVerifySignature(
func ProcessAttestationNoVerifySignature(
ctx context.Context,
beaconState state.BeaconState,
att *ethpb.Attestation,
att interfaces.Attestation,
) (state.BeaconState, error) {
ctx, span := trace.StartSpan(ctx, "core.ProcessAttestationNoVerifySignature")
defer span.End()
@@ -143,15 +143,15 @@ func ProcessAttestationNoVerifySignature(
}
currEpoch := time.CurrentEpoch(beaconState)
data := att.Data
s := att.Data.Slot
data := att.GetData()
s := att.GetData().Slot
proposerIndex, err := helpers.BeaconProposerIndex(ctx, beaconState)
if err != nil {
return nil, err
}
pendingAtt := &ethpb.PendingAttestation{
Data: data,
AggregationBits: att.AggregationBits,
AggregationBits: att.GetAggregationBits(),
InclusionDelay: beaconState.Slot() - s,
ProposerIndex: proposerIndex,
}
@@ -171,11 +171,11 @@ func ProcessAttestationNoVerifySignature(
// VerifyAttestationSignature converts and attestation into an indexed attestation and verifies
// the signature in that attestation.
func VerifyAttestationSignature(ctx context.Context, beaconState state.ReadOnlyBeaconState, att *ethpb.Attestation) error {
func VerifyAttestationSignature(ctx context.Context, beaconState state.ReadOnlyBeaconState, att interfaces.Attestation) error {
if err := helpers.ValidateNilAttestation(att); err != nil {
return err
}
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.Data.Slot, att.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, beaconState, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return err
}
@@ -203,7 +203,7 @@ func VerifyAttestationSignature(ctx context.Context, beaconState state.ReadOnlyB
// domain = get_domain(state, DOMAIN_BEACON_ATTESTER, indexed_attestation.data.target.epoch)
// signing_root = compute_signing_root(indexed_attestation.data, domain)
// return bls.FastAggregateVerify(pubkeys, signing_root, indexed_attestation.signature)
func VerifyIndexedAttestation(ctx context.Context, beaconState state.ReadOnlyBeaconState, indexedAtt *ethpb.IndexedAttestation) error {
func VerifyIndexedAttestation(ctx context.Context, beaconState state.ReadOnlyBeaconState, indexedAtt ethpb.IndexedAtt) error {
ctx, span := trace.StartSpan(ctx, "core.VerifyIndexedAttestation")
defer span.End()
@@ -212,14 +212,14 @@ func VerifyIndexedAttestation(ctx context.Context, beaconState state.ReadOnlyBea
}
domain, err := signing.Domain(
beaconState.Fork(),
indexedAtt.Data.Target.Epoch,
indexedAtt.GetData().Target.Epoch,
params.BeaconConfig().DomainBeaconAttester,
beaconState.GenesisValidatorsRoot(),
)
if err != nil {
return err
}
indices := indexedAtt.AttestingIndices
indices := indexedAtt.GetAttestingIndices()
var pubkeys []bls.PublicKey
for i := 0; i < len(indices); i++ {
pubkeyAtIdx := beaconState.PubkeyAtIndex(primitives.ValidatorIndex(indices[i]))

View File

@@ -11,6 +11,7 @@ import (
state_native "github.com/prysmaticlabs/prysm/v5/beacon-chain/state/state-native"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
@@ -386,7 +387,7 @@ func TestValidateIndexedAttestation_BadAttestationsSignatureSet(t *testing.T) {
sig := keys[0].Sign([]byte{'t', 'e', 's', 't'})
list := bitfield.Bitlist{0b11111}
var atts []*ethpb.Attestation
var atts []interfaces.Attestation
for i := uint64(0); i < 1000; i++ {
atts = append(atts, &ethpb.Attestation{
Data: &ethpb.AttestationData{
@@ -402,7 +403,7 @@ func TestValidateIndexedAttestation_BadAttestationsSignatureSet(t *testing.T) {
_, err := blocks.AttestationSignatureBatch(context.Background(), beaconState, atts)
assert.ErrorContains(t, want, err)
atts = []*ethpb.Attestation{}
atts = []interfaces.Attestation{}
list = bitfield.Bitlist{0b10000}
for i := uint64(0); i < 1000; i++ {
atts = append(atts, &ethpb.Attestation{
@@ -543,7 +544,7 @@ func TestRetrieveAttestationSignatureSet_VerifiesMultipleAttestations(t *testing
}
att2.Signature = bls.AggregateSignatures(sigs).Marshal()
set, err := blocks.AttestationSignatureBatch(ctx, st, []*ethpb.Attestation{att1, att2})
set, err := blocks.AttestationSignatureBatch(ctx, st, []interfaces.Attestation{att1, att2})
require.NoError(t, err)
verified, err := set.Verify()
require.NoError(t, err)
@@ -607,6 +608,6 @@ func TestRetrieveAttestationSignatureSet_AcrossFork(t *testing.T) {
}
att2.Signature = bls.AggregateSignatures(sigs).Marshal()
_, err = blocks.AttestationSignatureBatch(ctx, st, []*ethpb.Attestation{att1, att2})
_, err = blocks.AttestationSignatureBatch(ctx, st, []interfaces.Attestation{att1, att2})
require.NoError(t, err)
}

View File

@@ -8,6 +8,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/container/slice"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -40,7 +41,7 @@ import (
func ProcessAttesterSlashings(
ctx context.Context,
beaconState state.BeaconState,
slashings []*ethpb.AttesterSlashing,
slashings []interfaces.AttesterSlashing,
slashFunc slashValidatorFunc,
) (state.BeaconState, error) {
var err error
@@ -57,7 +58,7 @@ func ProcessAttesterSlashings(
func ProcessAttesterSlashing(
ctx context.Context,
beaconState state.BeaconState,
slashing *ethpb.AttesterSlashing,
slashing interfaces.AttesterSlashing,
slashFunc slashValidatorFunc,
) (state.BeaconState, error) {
if err := VerifyAttesterSlashing(ctx, beaconState, slashing); err != nil {
@@ -104,20 +105,20 @@ func ProcessAttesterSlashing(
}
// VerifyAttesterSlashing validates the attestation data in both attestations in the slashing object.
func VerifyAttesterSlashing(ctx context.Context, beaconState state.ReadOnlyBeaconState, slashing *ethpb.AttesterSlashing) error {
func VerifyAttesterSlashing(ctx context.Context, beaconState state.ReadOnlyBeaconState, slashing interfaces.AttesterSlashing) error {
if slashing == nil {
return errors.New("nil slashing")
}
if slashing.Attestation_1 == nil || slashing.Attestation_2 == nil {
if slashing.GetFirstAttestation() == nil || slashing.GetSecondAttestation() == nil {
return errors.New("nil attestation")
}
if slashing.Attestation_1.Data == nil || slashing.Attestation_2.Data == nil {
if slashing.GetFirstAttestation().GetData() == nil || slashing.GetSecondAttestation().GetData() == nil {
return errors.New("nil attestation data")
}
att1 := slashing.Attestation_1
att2 := slashing.Attestation_2
data1 := att1.Data
data2 := att2.Data
att1 := slashing.GetFirstAttestation()
att2 := slashing.GetSecondAttestation()
data1 := att1.GetData()
data2 := att2.GetData()
if !IsSlashableAttestationData(data1, data2) {
return errors.New("attestations are not slashable")
}
@@ -157,11 +158,11 @@ func IsSlashableAttestationData(data1, data2 *ethpb.AttestationData) bool {
}
// SlashableAttesterIndices returns the intersection of attester indices from both attestations in this slashing.
func SlashableAttesterIndices(slashing *ethpb.AttesterSlashing) []uint64 {
if slashing == nil || slashing.Attestation_1 == nil || slashing.Attestation_2 == nil {
func SlashableAttesterIndices(slashing interfaces.AttesterSlashing) []uint64 {
if slashing == nil || slashing.GetFirstAttestation() == nil || slashing.GetSecondAttestation() == nil {
return nil
}
indices1 := slashing.Attestation_1.AttestingIndices
indices2 := slashing.Attestation_2.AttestingIndices
indices1 := slashing.GetFirstAttestation().GetAttestingIndices()
indices2 := slashing.GetSecondAttestation().GetAttestingIndices()
return slice.IntersectionUint64(indices1, indices2)
}

View File

@@ -9,6 +9,7 @@ import (
v "github.com/prysmaticlabs/prysm/v5/beacon-chain/core/validators"
state_native "github.com/prysmaticlabs/prysm/v5/beacon-chain/state/state-native"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
@@ -57,7 +58,11 @@ func TestProcessAttesterSlashings_DataNotSlashable(t *testing.T) {
AttesterSlashings: slashings,
},
}
_, err = blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
_, err = blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
assert.ErrorContains(t, "attestations are not slashable", err)
}
@@ -92,7 +97,11 @@ func TestProcessAttesterSlashings_IndexedAttestationFailedToVerify(t *testing.T)
},
}
_, err = blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
_, err = blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
assert.ErrorContains(t, "validator indices count exceeds MAX_VALIDATORS_PER_COMMITTEE", err)
}
@@ -144,7 +153,11 @@ func TestProcessAttesterSlashings_AppliesCorrectStatus(t *testing.T) {
},
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
require.NoError(t, err)
newRegistry := newState.Validators()
@@ -213,7 +226,11 @@ func TestProcessAttesterSlashings_AppliesCorrectStatusAltair(t *testing.T) {
},
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
require.NoError(t, err)
newRegistry := newState.Validators()
@@ -282,7 +299,11 @@ func TestProcessAttesterSlashings_AppliesCorrectStatusBellatrix(t *testing.T) {
},
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
require.NoError(t, err)
newRegistry := newState.Validators()
@@ -351,7 +372,11 @@ func TestProcessAttesterSlashings_AppliesCorrectStatusCapella(t *testing.T) {
},
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
require.NoError(t, err)
newRegistry := newState.Validators()

View File

@@ -10,6 +10,7 @@ import (
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/blocks"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -216,7 +217,7 @@ func TestFuzzProcessAttesterSlashings_10000(t *testing.T) {
fuzzer.Fuzz(a)
s, err := state_native.InitializeFromProtoUnsafePhase0(state)
require.NoError(t, err)
r, err := ProcessAttesterSlashings(ctx, s, []*ethpb.AttesterSlashing{a}, v.SlashValidator)
r, err := ProcessAttesterSlashings(ctx, s, []interfaces.AttesterSlashing{a}, v.SlashValidator)
if err != nil && r != nil {
t.Fatalf("return value should be nil on err. found: %v on error: %v for state: %v and slashing: %v", r, err, state, a)
}

View File

@@ -8,6 +8,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/signing"
v "github.com/prysmaticlabs/prysm/v5/beacon-chain/core/validators"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -91,7 +92,11 @@ func TestProcessAttesterSlashings_RegressionSlashableIndices(t *testing.T) {
},
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, b.Block.Body.AttesterSlashings, v.SlashValidator)
ss := make([]interfaces.AttesterSlashing, len(b.Block.Body.AttesterSlashings))
for i, s := range b.Block.Body.AttesterSlashings {
ss[i] = s
}
newState, err := blocks.ProcessAttesterSlashings(context.Background(), beaconState, ss, v.SlashValidator)
require.NoError(t, err)
newRegistry := newState.Validators()
if !newRegistry[expectedSlashedVal].Slashed {

View File

@@ -179,7 +179,7 @@ func randaoSigningData(ctx context.Context, beaconState state.ReadOnlyBeaconStat
func createAttestationSignatureBatch(
ctx context.Context,
beaconState state.ReadOnlyBeaconState,
atts []*ethpb.Attestation,
atts []interfaces.Attestation,
domain []byte,
) (*bls.SignatureBatch, error) {
if len(atts) == 0 {
@@ -191,8 +191,8 @@ func createAttestationSignatureBatch(
msgs := make([][32]byte, len(atts))
descs := make([]string, len(atts))
for i, a := range atts {
sigs[i] = a.Signature
c, err := helpers.BeaconCommitteeFromState(ctx, beaconState, a.Data.Slot, a.Data.CommitteeIndex)
sigs[i] = a.GetSignature()
c, err := helpers.BeaconCommitteeFromState(ctx, beaconState, a.GetData().Slot, a.GetData().CommitteeIndex)
if err != nil {
return nil, err
}
@@ -203,7 +203,7 @@ func createAttestationSignatureBatch(
if err := attestation.IsValidAttestationIndices(ctx, ia); err != nil {
return nil, err
}
indices := ia.AttestingIndices
indices := ia.GetAttestingIndices()
pubkeys := make([][]byte, len(indices))
for i := 0; i < len(indices); i++ {
pubkeyAtIdx := beaconState.PubkeyAtIndex(primitives.ValidatorIndex(indices[i]))
@@ -215,7 +215,7 @@ func createAttestationSignatureBatch(
}
pks[i] = aggP
root, err := signing.ComputeSigningRoot(ia.Data, domain)
root, err := signing.ComputeSigningRoot(ia.GetData(), domain)
if err != nil {
return nil, errors.Wrap(err, "could not get signing root of object")
}
@@ -233,7 +233,7 @@ func createAttestationSignatureBatch(
// AttestationSignatureBatch retrieves all the related attestation signature data such as the relevant public keys,
// signatures and attestation signing data and collate it into a signature batch object.
func AttestationSignatureBatch(ctx context.Context, beaconState state.ReadOnlyBeaconState, atts []*ethpb.Attestation) (*bls.SignatureBatch, error) {
func AttestationSignatureBatch(ctx context.Context, beaconState state.ReadOnlyBeaconState, atts []interfaces.Attestation) (*bls.SignatureBatch, error) {
if len(atts) == 0 {
return bls.NewSet(), nil
}
@@ -243,10 +243,10 @@ func AttestationSignatureBatch(ctx context.Context, beaconState state.ReadOnlyBe
dt := params.BeaconConfig().DomainBeaconAttester
// Split attestations by fork. Note: the signature domain will differ based on the fork.
var preForkAtts []*ethpb.Attestation
var postForkAtts []*ethpb.Attestation
var preForkAtts []interfaces.Attestation
var postForkAtts []interfaces.Attestation
for _, a := range atts {
if slots.ToEpoch(a.Data.Slot) < fork.Epoch {
if slots.ToEpoch(a.GetData().Slot) < fork.Epoch {
preForkAtts = append(preForkAtts, a)
} else {
postForkAtts = append(postForkAtts, a)

View File

@@ -54,7 +54,7 @@ func ProcessAttestations(
return nil, nil, errors.Wrap(err, "could not check validator attested previous epoch")
}
committee, err := helpers.BeaconCommitteeFromState(ctx, state, a.Data.Slot, a.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, state, a.GetData().Slot, a.GetData().CommitteeIndex)
if err != nil {
return nil, nil, err
}

View File

@@ -11,6 +11,7 @@ go_library(
deps = [
"//async/event:go_default_library",
"//consensus-types/blocks:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
],
)

View File

@@ -3,6 +3,7 @@ package operation
import (
"github.com/prysmaticlabs/prysm/v5/consensus-types/blocks"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
@@ -37,7 +38,7 @@ const (
// UnAggregatedAttReceivedData is the data sent with UnaggregatedAttReceived events.
type UnAggregatedAttReceivedData struct {
// Attestation is the unaggregated attestation object.
Attestation *ethpb.Attestation
Attestation interfaces.Attestation
}
// AggregatedAttReceivedData is the data sent with AggregatedAttReceived events.
@@ -75,5 +76,5 @@ type ProposerSlashingReceivedData struct {
// AttesterSlashingReceivedData is the data sent with AttesterSlashingReceived events.
type AttesterSlashingReceivedData struct {
AttesterSlashing *ethpb.AttesterSlashing
AttesterSlashing interfaces.AttesterSlashing
}

View File

@@ -25,6 +25,7 @@ go_library(
"//beacon-chain/state:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//container/slice:go_default_library",
"//container/trie:go_default_library",
@@ -72,6 +73,7 @@ go_test(
"//beacon-chain/state/state-native:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//container/slice:go_default_library",
"//crypto/hash:go_default_library",

View File

@@ -7,6 +7,7 @@ import (
"time"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -21,20 +22,20 @@ var (
// ValidateNilAttestation checks if any composite field of input attestation is nil.
// Access to these nil fields will result in run time panic,
// it is recommended to run these checks as first line of defense.
func ValidateNilAttestation(attestation *ethpb.Attestation) error {
func ValidateNilAttestation(attestation interfaces.Attestation) error {
if attestation == nil {
return errors.New("attestation can't be nil")
}
if attestation.Data == nil {
if attestation.GetData() == nil {
return errors.New("attestation's data can't be nil")
}
if attestation.Data.Source == nil {
if attestation.GetData().Source == nil {
return errors.New("attestation's source can't be nil")
}
if attestation.Data.Target == nil {
if attestation.GetData().Target == nil {
return errors.New("attestation's target can't be nil")
}
if attestation.AggregationBits == nil {
if attestation.GetAggregationBits() == nil {
return errors.New("attestation's bitfield can't be nil")
}
return nil
@@ -71,8 +72,8 @@ func IsAggregator(committeeCount uint64, slotSig []byte) (bool, error) {
// IsAggregated returns true if the attestation is an aggregated attestation,
// false otherwise.
func IsAggregated(attestation *ethpb.Attestation) bool {
return attestation.AggregationBits.Count() > 1
func IsAggregated(attestation interfaces.Attestation) bool {
return attestation.GetAggregationBits().Count() > 1
}
// ComputeSubnetForAttestation returns the subnet for which the provided attestation will be broadcasted to.
@@ -90,8 +91,8 @@ func IsAggregated(attestation *ethpb.Attestation) bool {
// committees_since_epoch_start = committees_per_slot * slots_since_epoch_start
//
// return uint64((committees_since_epoch_start + committee_index) % ATTESTATION_SUBNET_COUNT)
func ComputeSubnetForAttestation(activeValCount uint64, att *ethpb.Attestation) uint64 {
return ComputeSubnetFromCommitteeAndSlot(activeValCount, att.Data.CommitteeIndex, att.Data.Slot)
func ComputeSubnetForAttestation(activeValCount uint64, att interfaces.Attestation) uint64 {
return ComputeSubnetFromCommitteeAndSlot(activeValCount, att.GetData().CommitteeIndex, att.GetData().Slot)
}
// ComputeSubnetFromCommitteeAndSlot is a flattened version of ComputeSubnetForAttestation where we only pass in

View File

@@ -9,6 +9,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
state_native "github.com/prysmaticlabs/prysm/v5/beacon-chain/state/state-native"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
@@ -238,7 +239,7 @@ func TestVerifyCheckpointEpoch_Ok(t *testing.T) {
func TestValidateNilAttestation(t *testing.T) {
tests := []struct {
name string
attestation *ethpb.Attestation
attestation interfaces.Attestation
errString string
}{
{

View File

@@ -15,12 +15,12 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/container/slice"
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
"github.com/prysmaticlabs/prysm/v5/math"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/time/slots"
)
@@ -257,8 +257,8 @@ func VerifyBitfieldLength(bf bitfield.Bitfield, committeeSize uint64) error {
// VerifyAttestationBitfieldLengths verifies that an attestations aggregation bitfields is
// a valid length matching the size of the committee.
func VerifyAttestationBitfieldLengths(ctx context.Context, state state.ReadOnlyBeaconState, att *ethpb.Attestation) error {
committee, err := BeaconCommitteeFromState(ctx, state, att.Data.Slot, att.Data.CommitteeIndex)
func VerifyAttestationBitfieldLengths(ctx context.Context, state state.ReadOnlyBeaconState, att interfaces.Attestation) error {
committee, err := BeaconCommitteeFromState(ctx, state, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return errors.Wrap(err, "could not retrieve beacon committees")
}
@@ -267,7 +267,7 @@ func VerifyAttestationBitfieldLengths(ctx context.Context, state state.ReadOnlyB
return errors.New("no committee exist for this attestation")
}
if err := VerifyBitfieldLength(att.AggregationBits, uint64(len(committee))); err != nil {
if err := VerifyBitfieldLength(att.GetAggregationBits(), uint64(len(committee))); err != nil {
return errors.Wrap(err, "failed to verify aggregation bitfield")
}
return nil

View File

@@ -671,5 +671,5 @@ func ValidatorMaxEffectiveBalance(val *ethpb.Validator) uint64 {
if HasCompoundingWithdrawalCredential(val) {
return params.BeaconConfig().MaxEffectiveBalanceElectra
}
return params.BeaconConfig().MinActivationBalance // TODO: Add test that MinActivationBalance == (old) MaxEffectiveBalance
return params.BeaconConfig().MinActivationBalance
}

View File

@@ -156,10 +156,10 @@ func (s *Store) CheckAttesterDoubleVotes(
signingRootsBkt := tx.Bucket(attestationDataRootsBucket)
attRecordsBkt := tx.Bucket(attestationRecordsBucket)
encEpoch := encodeTargetEpoch(attToProcess.IndexedAttestation.Data.Target.Epoch)
encEpoch := encodeTargetEpoch(attToProcess.IndexedAttestation.GetData().Target.Epoch)
localDoubleVotes := make([]*slashertypes.AttesterDoubleVote, 0)
for _, valIdx := range attToProcess.IndexedAttestation.AttestingIndices {
for _, valIdx := range attToProcess.IndexedAttestation.GetAttestingIndices() {
// Check if there is signing root in the database for this combination
// of validator index and target epoch.
encIdx := encodeValidatorIndex(primitives.ValidatorIndex(valIdx))
@@ -194,7 +194,7 @@ func (s *Store) CheckAttesterDoubleVotes(
// Build the proof of double vote.
slashAtt := &slashertypes.AttesterDoubleVote{
ValidatorIndex: primitives.ValidatorIndex(valIdx),
Target: attToProcess.IndexedAttestation.Data.Target.Epoch,
Target: attToProcess.IndexedAttestation.GetData().Target.Epoch,
Wrapper_1: existingAttRecord,
Wrapper_2: attToProcess,
}
@@ -280,7 +280,7 @@ func (s *Store) SaveAttestationRecordsForValidators(
encodedRecords := make([][]byte, attWrappersCount)
for i, attestation := range attWrappers {
encEpoch := encodeTargetEpoch(attestation.IndexedAttestation.Data.Target.Epoch)
encEpoch := encodeTargetEpoch(attestation.IndexedAttestation.GetData().Target.Epoch)
value, err := encodeAttestationRecord(attestation)
if err != nil {
@@ -325,7 +325,7 @@ func (s *Store) SaveAttestationRecordsForValidators(
return err
}
for _, validatorIndex := range attWrapper.IndexedAttestation.AttestingIndices {
for _, validatorIndex := range attWrapper.IndexedAttestation.GetAttestingIndices() {
encodedIndex := encodeValidatorIndex(primitives.ValidatorIndex(validatorIndex))
key := append(encodedTargetEpoch, encodedIndex...)
@@ -638,8 +638,8 @@ func (s *Store) HighestAttestations(
}
highestAtt := &ethpb.HighestAttestation{
ValidatorIndex: uint64(indices[i]),
HighestSourceEpoch: attWrapper.IndexedAttestation.Data.Source.Epoch,
HighestTargetEpoch: attWrapper.IndexedAttestation.Data.Target.Epoch,
HighestSourceEpoch: attWrapper.IndexedAttestation.GetData().Source.Epoch,
HighestTargetEpoch: attWrapper.IndexedAttestation.GetData().Target.Epoch,
}
history = append(history, highestAtt)
break

View File

@@ -62,7 +62,7 @@ func TestStore_AttestationRecordForValidator_SaveRetrieve(t *testing.T) {
actual, err := beaconDB.AttestationRecordForValidator(ctx, validatorIndex, primitives.Epoch(i+1))
require.NoError(t, err)
require.DeepEqual(t, expected.IndexedAttestation.Data.Source.Epoch, actual.IndexedAttestation.Data.Source.Epoch)
require.DeepEqual(t, expected.IndexedAttestation.GetData().Source.Epoch, actual.IndexedAttestation.GetData().Source.Epoch)
}
}
@@ -544,7 +544,7 @@ func BenchmarkHighestAttestations(b *testing.B) {
for i := 0; i < count; i++ {
indicesForAtt := make([]primitives.ValidatorIndex, valsPerAtt)
for r := 0; r < valsPerAtt; r++ {
indicesForAtt[r] = primitives.ValidatorIndex(atts[i].IndexedAttestation.AttestingIndices[r])
indicesForAtt[r] = primitives.ValidatorIndex(atts[i].IndexedAttestation.GetAttestingIndices()[r])
}
allIndices = append(allIndices, indicesForAtt...)
}

View File

@@ -33,12 +33,12 @@ func (s *Service) canUpdateAttestedValidator(idx primitives.ValidatorIndex, slot
}
// attestingIndices returns the indices of validators that participated in the given aggregated attestation.
func attestingIndices(ctx context.Context, state state.BeaconState, att *ethpb.Attestation) ([]uint64, error) {
committee, err := helpers.BeaconCommitteeFromState(ctx, state, att.Data.Slot, att.Data.CommitteeIndex)
func attestingIndices(ctx context.Context, state state.BeaconState, att interfaces.Attestation) ([]uint64, error) {
committee, err := helpers.BeaconCommitteeFromState(ctx, state, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return nil, err
}
return attestation.AttestingIndices(att.AggregationBits, committee)
return attestation.AttestingIndices(att.GetAggregationBits(), committee)
}
// logMessageTimelyFlagsForIndex returns the log message with performance info for the attestation (head, source, target)
@@ -63,7 +63,7 @@ func (s *Service) processAttestations(ctx context.Context, state state.BeaconSta
}
// processIncludedAttestation logs in the event for the tracked validators' and their latest attestation gets processed.
func (s *Service) processIncludedAttestation(ctx context.Context, state state.BeaconState, att *ethpb.Attestation) {
func (s *Service) processIncludedAttestation(ctx context.Context, state state.BeaconState, att interfaces.Attestation) {
attestingIndices, err := attestingIndices(ctx, state, att)
if err != nil {
log.WithError(err).Error("Could not get attesting indices")
@@ -72,8 +72,8 @@ func (s *Service) processIncludedAttestation(ctx context.Context, state state.Be
s.Lock()
defer s.Unlock()
for _, idx := range attestingIndices {
if s.canUpdateAttestedValidator(primitives.ValidatorIndex(idx), att.Data.Slot) {
logFields := logMessageTimelyFlagsForIndex(primitives.ValidatorIndex(idx), att.Data)
if s.canUpdateAttestedValidator(primitives.ValidatorIndex(idx), att.GetData().Slot) {
logFields := logMessageTimelyFlagsForIndex(primitives.ValidatorIndex(idx), att.GetData())
balance, err := state.BalanceAtIndex(primitives.ValidatorIndex(idx))
if err != nil {
log.WithError(err).Error("Could not get balance")
@@ -88,7 +88,7 @@ func (s *Service) processIncludedAttestation(ctx context.Context, state state.Be
balanceChg := int64(balance - latestPerf.balance)
latestPerf.balanceChange = balanceChg
latestPerf.balance = balance
latestPerf.attestedSlot = att.Data.Slot
latestPerf.attestedSlot = att.GetData().Slot
latestPerf.inclusionSlot = state.Slot()
inclusionSlotGauge.WithLabelValues(fmt.Sprintf("%d", idx)).Set(float64(latestPerf.inclusionSlot))
aggregatedPerf.totalDistance += uint64(latestPerf.inclusionSlot - latestPerf.attestedSlot)
@@ -161,10 +161,10 @@ func (s *Service) processIncludedAttestation(ctx context.Context, state state.Be
}
// processUnaggregatedAttestation logs when the beacon node observes an unaggregated attestation from tracked validator.
func (s *Service) processUnaggregatedAttestation(ctx context.Context, att *ethpb.Attestation) {
func (s *Service) processUnaggregatedAttestation(ctx context.Context, att interfaces.Attestation) {
s.RLock()
defer s.RUnlock()
root := bytesutil.ToBytes32(att.Data.BeaconBlockRoot)
root := bytesutil.ToBytes32(att.GetData().BeaconBlockRoot)
st := s.config.StateGen.StateByRootIfCachedNoCopy(root)
if st == nil {
log.WithField("beaconBlockRoot", fmt.Sprintf("%#x", bytesutil.Trunc(root[:]))).Debug(
@@ -177,8 +177,8 @@ func (s *Service) processUnaggregatedAttestation(ctx context.Context, att *ethpb
return
}
for _, idx := range attestingIndices {
if s.canUpdateAttestedValidator(primitives.ValidatorIndex(idx), att.Data.Slot) {
logFields := logMessageTimelyFlagsForIndex(primitives.ValidatorIndex(idx), att.Data)
if s.canUpdateAttestedValidator(primitives.ValidatorIndex(idx), att.GetData().Slot) {
logFields := logMessageTimelyFlagsForIndex(primitives.ValidatorIndex(idx), att.GetData())
log.WithFields(logFields).Info("Processed unaggregated attestation")
}
}

View File

@@ -124,14 +124,14 @@ func (s *Service) processSlashings(blk interfaces.ReadOnlyBeaconBlock) {
log.WithFields(logrus.Fields{
"attesterIndex": idx,
"blockInclusionSlot": blk.Slot(),
"attestationSlot1": slashing.Attestation_1.Data.Slot,
"beaconBlockRoot1": fmt.Sprintf("%#x", bytesutil.Trunc(slashing.Attestation_1.Data.BeaconBlockRoot)),
"sourceEpoch1": slashing.Attestation_1.Data.Source.Epoch,
"targetEpoch1": slashing.Attestation_1.Data.Target.Epoch,
"attestationSlot2": slashing.Attestation_2.Data.Slot,
"beaconBlockRoot2": fmt.Sprintf("%#x", bytesutil.Trunc(slashing.Attestation_2.Data.BeaconBlockRoot)),
"sourceEpoch2": slashing.Attestation_2.Data.Source.Epoch,
"targetEpoch2": slashing.Attestation_2.Data.Target.Epoch,
"attestationSlot1": slashing.GetFirstAttestation().GetData().Slot,
"beaconBlockRoot1": fmt.Sprintf("%#x", bytesutil.Trunc(slashing.GetFirstAttestation().GetData().BeaconBlockRoot)),
"sourceEpoch1": slashing.GetFirstAttestation().GetData().Source.Epoch,
"targetEpoch1": slashing.GetFirstAttestation().GetData().Target.Epoch,
"attestationSlot2": slashing.GetSecondAttestation().GetData().Slot,
"beaconBlockRoot2": fmt.Sprintf("%#x", bytesutil.Trunc(slashing.GetSecondAttestation().GetData().BeaconBlockRoot)),
"sourceEpoch2": slashing.GetSecondAttestation().GetData().Source.Epoch,
"targetEpoch2": slashing.GetSecondAttestation().GetData().Target.Epoch,
}).Info("Attester slashing was included")
}
}

View File

@@ -20,9 +20,9 @@ go_library(
"//cache/lru:go_default_library",
"//config/features:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/hash:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
"//proto/prysm/v1alpha1/attestation/aggregation/attestations:go_default_library",
"//time:go_default_library",
"//time/slots:go_default_library",
@@ -49,6 +49,7 @@ go_test(
"//beacon-chain/operations/attestations/kv:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/bls:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",

View File

@@ -15,9 +15,9 @@ go_library(
deps = [
"//beacon-chain/core/helpers:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/hash:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
"//proto/prysm/v1alpha1/attestation/aggregation/attestations:go_default_library",
"@com_github_patrickmn_go_cache//:go_default_library",
"@com_github_pkg_errors//:go_default_library",
@@ -39,6 +39,7 @@ go_test(
embed = [":go_default_library"],
deps = [
"//config/fieldparams:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//crypto/bls:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
"//testing/assert:go_default_library",

View File

@@ -7,8 +7,8 @@ import (
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
attaggregation "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation/attestations"
log "github.com/sirupsen/logrus"
"go.opencensus.io/trace"
@@ -28,13 +28,13 @@ func (c *AttCaches) AggregateUnaggregatedAttestations(ctx context.Context) error
return c.aggregateUnaggregatedAtts(ctx, unaggregatedAtts)
}
func (c *AttCaches) aggregateUnaggregatedAtts(ctx context.Context, unaggregatedAtts []*ethpb.Attestation) error {
func (c *AttCaches) aggregateUnaggregatedAtts(ctx context.Context, unaggregatedAtts []interfaces.Attestation) error {
_, span := trace.StartSpan(ctx, "operations.attestations.kv.aggregateUnaggregatedAtts")
defer span.End()
attsByDataRoot := make(map[[32]byte][]*ethpb.Attestation, len(unaggregatedAtts))
attsByDataRoot := make(map[[32]byte][]interfaces.Attestation, len(unaggregatedAtts))
for _, att := range unaggregatedAtts {
attDataRoot, err := att.Data.HashTreeRoot()
attDataRoot, err := att.GetData().HashTreeRoot()
if err != nil {
return err
}
@@ -66,12 +66,12 @@ func (c *AttCaches) aggregateUnaggregatedAtts(ctx context.Context, unaggregatedA
// aggregateParallel aggregates attestations in parallel for `atts` and saves them in the pool,
// returns the unaggregated attestations that weren't able to aggregate.
// Given `n` CPU cores, it creates a channel of size `n` and spawns `n` goroutines to aggregate attestations
func (c *AttCaches) aggregateParallel(atts map[[32]byte][]*ethpb.Attestation, leftOver map[[32]byte]bool) map[[32]byte]bool {
func (c *AttCaches) aggregateParallel(atts map[[32]byte][]interfaces.Attestation, leftOver map[[32]byte]bool) map[[32]byte]bool {
var leftoverLock sync.Mutex
wg := sync.WaitGroup{}
n := runtime.GOMAXPROCS(0) // defaults to the value of runtime.NumCPU
ch := make(chan []*ethpb.Attestation, n)
ch := make(chan []interfaces.Attestation, n)
wg.Add(n)
for i := 0; i < n; i++ {
go func() {
@@ -87,7 +87,7 @@ func (c *AttCaches) aggregateParallel(atts map[[32]byte][]*ethpb.Attestation, le
continue
}
if helpers.IsAggregated(aggregated) {
if err := c.SaveAggregatedAttestations([]*ethpb.Attestation{aggregated}); err != nil {
if err := c.SaveAggregatedAttestations([]interfaces.Attestation{aggregated}); err != nil {
log.WithError(err).Error("could not save aggregated attestation")
continue
}
@@ -116,7 +116,7 @@ func (c *AttCaches) aggregateParallel(atts map[[32]byte][]*ethpb.Attestation, le
}
// SaveAggregatedAttestation saves an aggregated attestation in cache.
func (c *AttCaches) SaveAggregatedAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) SaveAggregatedAttestation(att interfaces.Attestation) error {
if err := helpers.ValidateNilAttestation(att); err != nil {
return err
}
@@ -139,16 +139,16 @@ func (c *AttCaches) SaveAggregatedAttestation(att *ethpb.Attestation) error {
return nil
}
r, err := hashFn(att.Data)
r, err := hashFn(att.GetData())
if err != nil {
return errors.Wrap(err, "could not tree hash attestation")
}
copiedAtt := ethpb.CopyAttestation(att)
copiedAtt := interfaces.CopyAttestation(att)
c.aggregatedAttLock.Lock()
defer c.aggregatedAttLock.Unlock()
atts, ok := c.aggregatedAtt[r]
if !ok {
atts := []*ethpb.Attestation{copiedAtt}
atts := []interfaces.Attestation{copiedAtt}
c.aggregatedAtt[r] = atts
return nil
}
@@ -163,7 +163,7 @@ func (c *AttCaches) SaveAggregatedAttestation(att *ethpb.Attestation) error {
}
// SaveAggregatedAttestations saves a list of aggregated attestations in cache.
func (c *AttCaches) SaveAggregatedAttestations(atts []*ethpb.Attestation) error {
func (c *AttCaches) SaveAggregatedAttestations(atts []interfaces.Attestation) error {
for _, att := range atts {
if err := c.SaveAggregatedAttestation(att); err != nil {
log.WithError(err).Debug("Could not save aggregated attestation")
@@ -176,11 +176,11 @@ func (c *AttCaches) SaveAggregatedAttestations(atts []*ethpb.Attestation) error
}
// AggregatedAttestations returns the aggregated attestations in cache.
func (c *AttCaches) AggregatedAttestations() []*ethpb.Attestation {
func (c *AttCaches) AggregatedAttestations() []interfaces.Attestation {
c.aggregatedAttLock.RLock()
defer c.aggregatedAttLock.RUnlock()
atts := make([]*ethpb.Attestation, 0)
atts := make([]interfaces.Attestation, 0)
for _, a := range c.aggregatedAtt {
atts = append(atts, a...)
@@ -191,16 +191,16 @@ func (c *AttCaches) AggregatedAttestations() []*ethpb.Attestation {
// AggregatedAttestationsBySlotIndex returns the aggregated attestations in cache,
// filtered by committee index and slot.
func (c *AttCaches) AggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []*ethpb.Attestation {
func (c *AttCaches) AggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []interfaces.Attestation {
_, span := trace.StartSpan(ctx, "operations.attestations.kv.AggregatedAttestationsBySlotIndex")
defer span.End()
atts := make([]*ethpb.Attestation, 0)
atts := make([]interfaces.Attestation, 0)
c.aggregatedAttLock.RLock()
defer c.aggregatedAttLock.RUnlock()
for _, a := range c.aggregatedAtt {
if slot == a[0].Data.Slot && committeeIndex == a[0].Data.CommitteeIndex {
if slot == a[0].GetData().Slot && committeeIndex == a[0].GetData().CommitteeIndex {
atts = append(atts, a...)
}
}
@@ -209,14 +209,14 @@ func (c *AttCaches) AggregatedAttestationsBySlotIndex(ctx context.Context, slot
}
// DeleteAggregatedAttestation deletes the aggregated attestations in cache.
func (c *AttCaches) DeleteAggregatedAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) DeleteAggregatedAttestation(att interfaces.Attestation) error {
if err := helpers.ValidateNilAttestation(att); err != nil {
return err
}
if !helpers.IsAggregated(att) {
return errors.New("attestation is not aggregated")
}
r, err := hashFn(att.Data)
r, err := hashFn(att.GetData())
if err != nil {
return errors.Wrap(err, "could not tree hash attestation data")
}
@@ -232,9 +232,9 @@ func (c *AttCaches) DeleteAggregatedAttestation(att *ethpb.Attestation) error {
return nil
}
filtered := make([]*ethpb.Attestation, 0)
filtered := make([]interfaces.Attestation, 0)
for _, a := range attList {
if c, err := att.AggregationBits.Contains(a.AggregationBits); err != nil {
if c, err := att.GetAggregationBits().Contains(a.GetAggregationBits()); err != nil {
return err
} else if !c {
filtered = append(filtered, a)
@@ -250,11 +250,11 @@ func (c *AttCaches) DeleteAggregatedAttestation(att *ethpb.Attestation) error {
}
// HasAggregatedAttestation checks if the input attestations has already existed in cache.
func (c *AttCaches) HasAggregatedAttestation(att *ethpb.Attestation) (bool, error) {
func (c *AttCaches) HasAggregatedAttestation(att interfaces.Attestation) (bool, error) {
if err := helpers.ValidateNilAttestation(att); err != nil {
return false, err
}
r, err := hashFn(att.Data)
r, err := hashFn(att.GetData())
if err != nil {
return false, errors.Wrap(err, "could not tree hash attestation")
}
@@ -263,7 +263,7 @@ func (c *AttCaches) HasAggregatedAttestation(att *ethpb.Attestation) (bool, erro
defer c.aggregatedAttLock.RUnlock()
if atts, ok := c.aggregatedAtt[r]; ok {
for _, a := range atts {
if c, err := a.AggregationBits.Contains(att.AggregationBits); err != nil {
if c, err := a.GetAggregationBits().Contains(att.GetAggregationBits()); err != nil {
return false, err
} else if c {
return true, nil
@@ -275,7 +275,7 @@ func (c *AttCaches) HasAggregatedAttestation(att *ethpb.Attestation) (bool, erro
defer c.blockAttLock.RUnlock()
if atts, ok := c.blockAtt[r]; ok {
for _, a := range atts {
if c, err := a.AggregationBits.Contains(att.AggregationBits); err != nil {
if c, err := a.GetAggregationBits().Contains(att.GetAggregationBits()); err != nil {
return false, err
} else if c {
return true, nil

View File

@@ -9,6 +9,7 @@ import (
"github.com/pkg/errors"
fssz "github.com/prysmaticlabs/fastssz"
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
@@ -30,7 +31,7 @@ func TestKV_Aggregated_AggregateUnaggregatedAttestations(t *testing.T) {
att6 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1010}, Signature: sig1.Marshal()})
att7 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1100}, Signature: sig1.Marshal()})
att8 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1001}, Signature: sig2.Marshal()})
atts := []*ethpb.Attestation{att1, att2, att3, att4, att5, att6, att7, att8}
atts := []interfaces.Attestation{att1, att2, att3, att4, att5, att6, att7, att8}
require.NoError(t, cache.SaveUnaggregatedAttestations(atts))
require.NoError(t, cache.AggregateUnaggregatedAttestations(context.Background()))
@@ -41,7 +42,7 @@ func TestKV_Aggregated_AggregateUnaggregatedAttestations(t *testing.T) {
func TestKV_Aggregated_SaveAggregatedAttestation(t *testing.T) {
tests := []struct {
name string
att *ethpb.Attestation
att interfaces.Attestation
count int
wantErrString string
}{
@@ -118,13 +119,13 @@ func TestKV_Aggregated_SaveAggregatedAttestation(t *testing.T) {
func TestKV_Aggregated_SaveAggregatedAttestations(t *testing.T) {
tests := []struct {
name string
atts []*ethpb.Attestation
atts []interfaces.Attestation
count int
wantErrString string
}{
{
name: "no duplicates",
atts: []*ethpb.Attestation{
atts: []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1},
AggregationBits: bitfield.Bitlist{0b1101}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1},
@@ -153,13 +154,13 @@ func TestKV_Aggregated_SaveAggregatedAttestations(t *testing.T) {
func TestKV_Aggregated_SaveAggregatedAttestations_SomeGoodSomeBad(t *testing.T) {
tests := []struct {
name string
atts []*ethpb.Attestation
atts []interfaces.Attestation
count int
wantErrString string
}{
{
name: "the first attestation is bad",
atts: []*ethpb.Attestation{
atts: []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1},
AggregationBits: bitfield.Bitlist{0b1100}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1},
@@ -191,7 +192,7 @@ func TestKV_Aggregated_AggregatedAttestations(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b1101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1101}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b1101}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
for _, att := range atts {
require.NoError(t, cache.SaveAggregatedAttestation(att))
@@ -199,7 +200,7 @@ func TestKV_Aggregated_AggregatedAttestations(t *testing.T) {
returned := cache.AggregatedAttestations()
sort.Slice(returned, func(i, j int) bool {
return returned[i].Data.Slot < returned[j].Data.Slot
return returned[i].GetData().Slot < returned[j].GetData().Slot
})
assert.DeepSSZEqual(t, atts, returned)
}
@@ -246,13 +247,13 @@ func TestKV_Aggregated_DeleteAggregatedAttestation(t *testing.T) {
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b11010}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b11010}})
att4 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b10101}})
atts := []*ethpb.Attestation{att1, att2, att3, att4}
atts := []interfaces.Attestation{att1, att2, att3, att4}
require.NoError(t, cache.SaveAggregatedAttestations(atts))
require.NoError(t, cache.DeleteAggregatedAttestation(att1))
require.NoError(t, cache.DeleteAggregatedAttestation(att3))
returned := cache.AggregatedAttestations()
wanted := []*ethpb.Attestation{att2}
wanted := []interfaces.Attestation{att2}
assert.DeepEqual(t, wanted, returned)
})
@@ -262,16 +263,16 @@ func TestKV_Aggregated_DeleteAggregatedAttestation(t *testing.T) {
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b110111}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b110100}})
att4 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b110101}})
atts := []*ethpb.Attestation{att1, att2, att3, att4}
atts := []interfaces.Attestation{att1, att2, att3, att4}
require.NoError(t, cache.SaveAggregatedAttestations(atts))
assert.Equal(t, 2, cache.AggregatedAttestationCount(), "Unexpected number of atts")
require.NoError(t, cache.DeleteAggregatedAttestation(att4))
returned := cache.AggregatedAttestations()
wanted := []*ethpb.Attestation{att1, att2}
wanted := []interfaces.Attestation{att1, att2}
sort.Slice(returned, func(i, j int) bool {
return string(returned[i].AggregationBits) < string(returned[j].AggregationBits)
return string(returned[i].GetAggregationBits()) < string(returned[j].GetAggregationBits())
})
assert.DeepEqual(t, wanted, returned)
})
@@ -280,7 +281,7 @@ func TestKV_Aggregated_DeleteAggregatedAttestation(t *testing.T) {
func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
tests := []struct {
name string
existing []*ethpb.Attestation
existing []interfaces.Attestation
input *ethpb.Attestation
want bool
err error
@@ -319,7 +320,7 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "single attestation in cache with exact match",
existing: []*ethpb.Attestation{{
existing: []interfaces.Attestation{&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
@@ -334,7 +335,7 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "single attestation in cache with subset aggregation",
existing: []*ethpb.Attestation{{
existing: []interfaces.Attestation{&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
@@ -349,7 +350,7 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "single attestation in cache with superset aggregation",
existing: []*ethpb.Attestation{{
existing: []interfaces.Attestation{&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
@@ -364,14 +365,14 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "multiple attestations with same data in cache with overlapping aggregation, input is subset",
existing: []*ethpb.Attestation{
{
existing: []interfaces.Attestation{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
AggregationBits: bitfield.Bitlist{0b1111000},
},
{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
@@ -387,14 +388,14 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "multiple attestations with same data in cache with overlapping aggregation and input is superset",
existing: []*ethpb.Attestation{
{
existing: []interfaces.Attestation{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
AggregationBits: bitfield.Bitlist{0b1111000},
},
{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 1,
}),
@@ -410,14 +411,14 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "multiple attestations with different data in cache",
existing: []*ethpb.Attestation{
{
existing: []interfaces.Attestation{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 2,
}),
AggregationBits: bitfield.Bitlist{0b1111000},
},
{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 3,
}),
@@ -433,8 +434,8 @@ func TestKV_Aggregated_HasAggregatedAttestation(t *testing.T) {
},
{
name: "attestations with different bitlist lengths",
existing: []*ethpb.Attestation{
{
existing: []interfaces.Attestation{
&ethpb.Attestation{
Data: util.HydrateAttestationData(&ethpb.AttestationData{
Slot: 2,
}),

View File

@@ -2,15 +2,15 @@ package kv
import (
"github.com/pkg/errors"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
)
// SaveBlockAttestation saves an block attestation in cache.
func (c *AttCaches) SaveBlockAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) SaveBlockAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}
r, err := hashFn(att.Data)
r, err := hashFn(att.GetData())
if err != nil {
return errors.Wrap(err, "could not tree hash attestation")
}
@@ -19,26 +19,26 @@ func (c *AttCaches) SaveBlockAttestation(att *ethpb.Attestation) error {
defer c.blockAttLock.Unlock()
atts, ok := c.blockAtt[r]
if !ok {
atts = make([]*ethpb.Attestation, 0, 1)
atts = make([]interfaces.Attestation, 0, 1)
}
// Ensure that this attestation is not already fully contained in an existing attestation.
for _, a := range atts {
if c, err := a.AggregationBits.Contains(att.AggregationBits); err != nil {
if c, err := a.GetAggregationBits().Contains(att.GetAggregationBits()); err != nil {
return err
} else if c {
return nil
}
}
c.blockAtt[r] = append(atts, ethpb.CopyAttestation(att))
c.blockAtt[r] = append(atts, interfaces.CopyAttestation(att))
return nil
}
// BlockAttestations returns the block attestations in cache.
func (c *AttCaches) BlockAttestations() []*ethpb.Attestation {
atts := make([]*ethpb.Attestation, 0)
func (c *AttCaches) BlockAttestations() []interfaces.Attestation {
atts := make([]interfaces.Attestation, 0)
c.blockAttLock.RLock()
defer c.blockAttLock.RUnlock()
@@ -50,11 +50,11 @@ func (c *AttCaches) BlockAttestations() []*ethpb.Attestation {
}
// DeleteBlockAttestation deletes a block attestation in cache.
func (c *AttCaches) DeleteBlockAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) DeleteBlockAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}
r, err := hashFn(att.Data)
r, err := hashFn(att.GetData())
if err != nil {
return errors.Wrap(err, "could not tree hash attestation")
}

View File

@@ -5,6 +5,7 @@ import (
"testing"
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -17,7 +18,7 @@ func TestKV_BlockAttestation_CanSaveRetrieve(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b1101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1101}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b1101}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
for _, att := range atts {
require.NoError(t, cache.SaveBlockAttestation(att))
@@ -31,7 +32,7 @@ func TestKV_BlockAttestation_CanSaveRetrieve(t *testing.T) {
returned := cache.BlockAttestations()
sort.Slice(returned, func(i, j int) bool {
return returned[i].Data.Slot < returned[j].Data.Slot
return returned[i].GetData().Slot < returned[j].GetData().Slot
})
assert.DeepEqual(t, atts, returned)
@@ -43,7 +44,7 @@ func TestKV_BlockAttestation_CanDelete(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b1101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1101}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b1101}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
for _, att := range atts {
require.NoError(t, cache.SaveBlockAttestation(att))
@@ -53,6 +54,6 @@ func TestKV_BlockAttestation_CanDelete(t *testing.T) {
require.NoError(t, cache.DeleteBlockAttestation(att3))
returned := cache.BlockAttestations()
wanted := []*ethpb.Attestation{att2}
wanted := []interfaces.Attestation{att2}
assert.DeepEqual(t, wanted, returned)
}

View File

@@ -2,11 +2,11 @@ package kv
import (
"github.com/pkg/errors"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
)
// SaveForkchoiceAttestation saves an forkchoice attestation in cache.
func (c *AttCaches) SaveForkchoiceAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) SaveForkchoiceAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}
@@ -15,7 +15,7 @@ func (c *AttCaches) SaveForkchoiceAttestation(att *ethpb.Attestation) error {
return errors.Wrap(err, "could not tree hash attestation")
}
att = ethpb.CopyAttestation(att)
att = interfaces.CopyAttestation(att)
c.forkchoiceAttLock.Lock()
defer c.forkchoiceAttLock.Unlock()
c.forkchoiceAtt[r] = att
@@ -24,7 +24,7 @@ func (c *AttCaches) SaveForkchoiceAttestation(att *ethpb.Attestation) error {
}
// SaveForkchoiceAttestations saves a list of forkchoice attestations in cache.
func (c *AttCaches) SaveForkchoiceAttestations(atts []*ethpb.Attestation) error {
func (c *AttCaches) SaveForkchoiceAttestations(atts []interfaces.Attestation) error {
for _, att := range atts {
if err := c.SaveForkchoiceAttestation(att); err != nil {
return err
@@ -35,20 +35,20 @@ func (c *AttCaches) SaveForkchoiceAttestations(atts []*ethpb.Attestation) error
}
// ForkchoiceAttestations returns the forkchoice attestations in cache.
func (c *AttCaches) ForkchoiceAttestations() []*ethpb.Attestation {
func (c *AttCaches) ForkchoiceAttestations() []interfaces.Attestation {
c.forkchoiceAttLock.RLock()
defer c.forkchoiceAttLock.RUnlock()
atts := make([]*ethpb.Attestation, 0, len(c.forkchoiceAtt))
atts := make([]interfaces.Attestation, 0, len(c.forkchoiceAtt))
for _, att := range c.forkchoiceAtt {
atts = append(atts, ethpb.CopyAttestation(att) /* Copied */)
atts = append(atts, interfaces.CopyAttestation(att) /* Copied */)
}
return atts
}
// DeleteForkchoiceAttestation deletes a forkchoice attestation in cache.
func (c *AttCaches) DeleteForkchoiceAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) DeleteForkchoiceAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}

View File

@@ -5,6 +5,7 @@ import (
"testing"
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -17,7 +18,7 @@ func TestKV_Forkchoice_CanSaveRetrieve(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b1101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1101}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b1101}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
for _, att := range atts {
require.NoError(t, cache.SaveForkchoiceAttestation(att))
@@ -26,7 +27,7 @@ func TestKV_Forkchoice_CanSaveRetrieve(t *testing.T) {
returned := cache.ForkchoiceAttestations()
sort.Slice(returned, func(i, j int) bool {
return returned[i].Data.Slot < returned[j].Data.Slot
return returned[i].GetData().Slot < returned[j].GetData().Slot
})
assert.DeepEqual(t, atts, returned)
@@ -38,7 +39,7 @@ func TestKV_Forkchoice_CanDelete(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b1101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b1101}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b1101}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
for _, att := range atts {
require.NoError(t, cache.SaveForkchoiceAttestation(att))
@@ -48,7 +49,7 @@ func TestKV_Forkchoice_CanDelete(t *testing.T) {
require.NoError(t, cache.DeleteForkchoiceAttestation(att3))
returned := cache.ForkchoiceAttestations()
wanted := []*ethpb.Attestation{att2}
wanted := []interfaces.Attestation{att2}
assert.DeepEqual(t, wanted, returned)
}

View File

@@ -9,8 +9,8 @@ import (
"github.com/patrickmn/go-cache"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
var hashFn = hash.Proto
@@ -20,13 +20,13 @@ var hashFn = hash.Proto
// such are unaggregated, aggregated or attestations within a block.
type AttCaches struct {
aggregatedAttLock sync.RWMutex
aggregatedAtt map[[32]byte][]*ethpb.Attestation
aggregatedAtt map[[32]byte][]interfaces.Attestation
unAggregateAttLock sync.RWMutex
unAggregatedAtt map[[32]byte]*ethpb.Attestation
unAggregatedAtt map[[32]byte]interfaces.Attestation
forkchoiceAttLock sync.RWMutex
forkchoiceAtt map[[32]byte]*ethpb.Attestation
forkchoiceAtt map[[32]byte]interfaces.Attestation
blockAttLock sync.RWMutex
blockAtt map[[32]byte][]*ethpb.Attestation
blockAtt map[[32]byte][]interfaces.Attestation
seenAtt *cache.Cache
}
@@ -36,10 +36,10 @@ func NewAttCaches() *AttCaches {
secsInEpoch := time.Duration(params.BeaconConfig().SlotsPerEpoch.Mul(params.BeaconConfig().SecondsPerSlot))
c := cache.New(secsInEpoch*time.Second, 2*secsInEpoch*time.Second)
pool := &AttCaches{
unAggregatedAtt: make(map[[32]byte]*ethpb.Attestation),
aggregatedAtt: make(map[[32]byte][]*ethpb.Attestation),
forkchoiceAtt: make(map[[32]byte]*ethpb.Attestation),
blockAtt: make(map[[32]byte][]*ethpb.Attestation),
unAggregatedAtt: make(map[[32]byte]interfaces.Attestation),
aggregatedAtt: make(map[[32]byte][]interfaces.Attestation),
forkchoiceAtt: make(map[[32]byte]interfaces.Attestation),
blockAtt: make(map[[32]byte][]interfaces.Attestation),
seenAtt: c,
}

View File

@@ -4,11 +4,11 @@ import (
"github.com/patrickmn/go-cache"
"github.com/pkg/errors"
"github.com/prysmaticlabs/go-bitfield"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
)
func (c *AttCaches) insertSeenBit(att *ethpb.Attestation) error {
r, err := hashFn(att.Data)
func (c *AttCaches) insertSeenBit(att interfaces.Attestation) error {
r, err := hashFn(att.GetData())
if err != nil {
return err
}
@@ -21,7 +21,7 @@ func (c *AttCaches) insertSeenBit(att *ethpb.Attestation) error {
}
alreadyExists := false
for _, bit := range seenBits {
if c, err := bit.Contains(att.AggregationBits); err != nil {
if c, err := bit.Contains(att.GetAggregationBits()); err != nil {
return err
} else if c {
alreadyExists = true
@@ -29,18 +29,18 @@ func (c *AttCaches) insertSeenBit(att *ethpb.Attestation) error {
}
}
if !alreadyExists {
seenBits = append(seenBits, att.AggregationBits)
seenBits = append(seenBits, att.GetAggregationBits())
}
c.seenAtt.Set(string(r[:]), seenBits, cache.DefaultExpiration /* one epoch */)
return nil
}
c.seenAtt.Set(string(r[:]), []bitfield.Bitlist{att.AggregationBits}, cache.DefaultExpiration /* one epoch */)
c.seenAtt.Set(string(r[:]), []bitfield.Bitlist{att.GetAggregationBits()}, cache.DefaultExpiration /* one epoch */)
return nil
}
func (c *AttCaches) hasSeenBit(att *ethpb.Attestation) (bool, error) {
r, err := hashFn(att.Data)
func (c *AttCaches) hasSeenBit(att interfaces.Attestation) (bool, error) {
r, err := hashFn(att.GetData())
if err != nil {
return false, err
}
@@ -52,7 +52,7 @@ func (c *AttCaches) hasSeenBit(att *ethpb.Attestation) (bool, error) {
return false, errors.New("could not convert to bitlist type")
}
for _, bit := range seenBits {
if c, err := bit.Contains(att.AggregationBits); err != nil {
if c, err := bit.Contains(att.GetAggregationBits()); err != nil {
return false, err
} else if c {
return true, nil

View File

@@ -5,13 +5,13 @@ import (
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"go.opencensus.io/trace"
)
// SaveUnaggregatedAttestation saves an unaggregated attestation in cache.
func (c *AttCaches) SaveUnaggregatedAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) SaveUnaggregatedAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}
@@ -31,7 +31,7 @@ func (c *AttCaches) SaveUnaggregatedAttestation(att *ethpb.Attestation) error {
if err != nil {
return errors.Wrap(err, "could not tree hash attestation")
}
att = ethpb.CopyAttestation(att) // Copied.
att = interfaces.CopyAttestation(att) // Copied.
c.unAggregateAttLock.Lock()
defer c.unAggregateAttLock.Unlock()
c.unAggregatedAtt[r] = att
@@ -40,7 +40,7 @@ func (c *AttCaches) SaveUnaggregatedAttestation(att *ethpb.Attestation) error {
}
// SaveUnaggregatedAttestations saves a list of unaggregated attestations in cache.
func (c *AttCaches) SaveUnaggregatedAttestations(atts []*ethpb.Attestation) error {
func (c *AttCaches) SaveUnaggregatedAttestations(atts []interfaces.Attestation) error {
for _, att := range atts {
if err := c.SaveUnaggregatedAttestation(att); err != nil {
return err
@@ -51,18 +51,18 @@ func (c *AttCaches) SaveUnaggregatedAttestations(atts []*ethpb.Attestation) erro
}
// UnaggregatedAttestations returns all the unaggregated attestations in cache.
func (c *AttCaches) UnaggregatedAttestations() ([]*ethpb.Attestation, error) {
func (c *AttCaches) UnaggregatedAttestations() ([]interfaces.Attestation, error) {
c.unAggregateAttLock.RLock()
defer c.unAggregateAttLock.RUnlock()
unAggregatedAtts := c.unAggregatedAtt
atts := make([]*ethpb.Attestation, 0, len(unAggregatedAtts))
atts := make([]interfaces.Attestation, 0, len(unAggregatedAtts))
for _, att := range unAggregatedAtts {
seen, err := c.hasSeenBit(att)
if err != nil {
return nil, err
}
if !seen {
atts = append(atts, ethpb.CopyAttestation(att) /* Copied */)
atts = append(atts, interfaces.CopyAttestation(att) /* Copied */)
}
}
return atts, nil
@@ -70,18 +70,18 @@ func (c *AttCaches) UnaggregatedAttestations() ([]*ethpb.Attestation, error) {
// UnaggregatedAttestationsBySlotIndex returns the unaggregated attestations in cache,
// filtered by committee index and slot.
func (c *AttCaches) UnaggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []*ethpb.Attestation {
func (c *AttCaches) UnaggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []interfaces.Attestation {
_, span := trace.StartSpan(ctx, "operations.attestations.kv.UnaggregatedAttestationsBySlotIndex")
defer span.End()
atts := make([]*ethpb.Attestation, 0)
atts := make([]interfaces.Attestation, 0)
c.unAggregateAttLock.RLock()
defer c.unAggregateAttLock.RUnlock()
unAggregatedAtts := c.unAggregatedAtt
for _, a := range unAggregatedAtts {
if slot == a.Data.Slot && committeeIndex == a.Data.CommitteeIndex {
if slot == a.GetData().Slot && committeeIndex == a.GetData().CommitteeIndex {
atts = append(atts, a)
}
}
@@ -90,7 +90,7 @@ func (c *AttCaches) UnaggregatedAttestationsBySlotIndex(ctx context.Context, slo
}
// DeleteUnaggregatedAttestation deletes the unaggregated attestations in cache.
func (c *AttCaches) DeleteUnaggregatedAttestation(att *ethpb.Attestation) error {
func (c *AttCaches) DeleteUnaggregatedAttestation(att interfaces.Attestation) error {
if att == nil {
return nil
}

View File

@@ -10,6 +10,7 @@ import (
fssz "github.com/prysmaticlabs/fastssz"
"github.com/prysmaticlabs/go-bitfield"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -19,7 +20,7 @@ import (
func TestKV_Unaggregated_SaveUnaggregatedAttestation(t *testing.T) {
tests := []struct {
name string
att *ethpb.Attestation
att interfaces.Attestation
count int
wantErrString string
}{
@@ -66,8 +67,8 @@ func TestKV_Unaggregated_SaveUnaggregatedAttestation(t *testing.T) {
cache.seenAtt.Set(string(r[:]), []bitfield.Bitlist{{0xff}}, c.DefaultExpiration)
assert.Equal(t, 0, len(cache.unAggregatedAtt), "Invalid start pool, atts: %d", len(cache.unAggregatedAtt))
if tt.att != nil && tt.att.Signature == nil {
tt.att.Signature = make([]byte, fieldparams.BLSSignatureLength)
if tt.att != nil && tt.att.GetSignature() == nil {
tt.att.(*ethpb.Attestation).Signature = make([]byte, fieldparams.BLSSignatureLength)
}
err := cache.SaveUnaggregatedAttestation(tt.att)
@@ -85,13 +86,13 @@ func TestKV_Unaggregated_SaveUnaggregatedAttestation(t *testing.T) {
func TestKV_Unaggregated_SaveUnaggregatedAttestations(t *testing.T) {
tests := []struct {
name string
atts []*ethpb.Attestation
atts []interfaces.Attestation
count int
wantErrString string
}{
{
name: "unaggregated only",
atts: []*ethpb.Attestation{
atts: []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}}),
@@ -100,9 +101,9 @@ func TestKV_Unaggregated_SaveUnaggregatedAttestations(t *testing.T) {
},
{
name: "has aggregated",
atts: []*ethpb.Attestation{
atts: []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}}),
{AggregationBits: bitfield.Bitlist{0b1111}, Data: &ethpb.AttestationData{Slot: 2}},
&ethpb.Attestation{AggregationBits: bitfield.Bitlist{0b1111}, Data: &ethpb.AttestationData{Slot: 2}},
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}}),
},
wantErrString: "attestation is aggregated",
@@ -145,14 +146,14 @@ func TestKV_Unaggregated_DeleteUnaggregatedAttestation(t *testing.T) {
att1 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b101}})
att2 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b110}})
att3 := util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b110}})
atts := []*ethpb.Attestation{att1, att2, att3}
atts := []interfaces.Attestation{att1, att2, att3}
require.NoError(t, cache.SaveUnaggregatedAttestations(atts))
for _, att := range atts {
assert.NoError(t, cache.DeleteUnaggregatedAttestation(att))
}
returned, err := cache.UnaggregatedAttestations()
require.NoError(t, err)
assert.DeepEqual(t, []*ethpb.Attestation{}, returned)
assert.DeepEqual(t, []interfaces.Attestation{}, returned)
})
}
@@ -168,7 +169,7 @@ func TestKV_Unaggregated_DeleteSeenUnaggregatedAttestations(t *testing.T) {
t.Run("none seen", func(t *testing.T) {
cache := NewAttCaches()
atts := []*ethpb.Attestation{
atts := []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1001}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1010}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1100}}),
@@ -185,7 +186,7 @@ func TestKV_Unaggregated_DeleteSeenUnaggregatedAttestations(t *testing.T) {
t.Run("some seen", func(t *testing.T) {
cache := NewAttCaches()
atts := []*ethpb.Attestation{
atts := []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1001}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1010}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1100}}),
@@ -202,15 +203,15 @@ func TestKV_Unaggregated_DeleteSeenUnaggregatedAttestations(t *testing.T) {
assert.Equal(t, 2, cache.UnaggregatedAttestationCount())
returned, err := cache.UnaggregatedAttestations()
sort.Slice(returned, func(i, j int) bool {
return bytes.Compare(returned[i].AggregationBits, returned[j].AggregationBits) < 0
return bytes.Compare(returned[i].GetAggregationBits(), returned[j].GetAggregationBits()) < 0
})
require.NoError(t, err)
assert.DeepEqual(t, []*ethpb.Attestation{atts[0], atts[2]}, returned)
assert.DeepEqual(t, []interfaces.Attestation{atts[0], atts[2]}, returned)
})
t.Run("all seen", func(t *testing.T) {
cache := NewAttCaches()
atts := []*ethpb.Attestation{
atts := []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1001}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1010}}),
util.HydrateAttestation(&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b1100}}),
@@ -229,7 +230,7 @@ func TestKV_Unaggregated_DeleteSeenUnaggregatedAttestations(t *testing.T) {
assert.Equal(t, 0, cache.UnaggregatedAttestationCount())
returned, err := cache.UnaggregatedAttestations()
require.NoError(t, err)
assert.DeepEqual(t, []*ethpb.Attestation{}, returned)
assert.DeepEqual(t, []interfaces.Attestation{}, returned)
})
}
@@ -246,9 +247,9 @@ func TestKV_Unaggregated_UnaggregatedAttestationsBySlotIndex(t *testing.T) {
}
ctx := context.Background()
returned := cache.UnaggregatedAttestationsBySlotIndex(ctx, 1, 1)
assert.DeepEqual(t, []*ethpb.Attestation{att1}, returned)
assert.DeepEqual(t, []interfaces.Attestation{att1}, returned)
returned = cache.UnaggregatedAttestationsBySlotIndex(ctx, 1, 2)
assert.DeepEqual(t, []*ethpb.Attestation{att2}, returned)
assert.DeepEqual(t, []interfaces.Attestation{att2}, returned)
returned = cache.UnaggregatedAttestationsBySlotIndex(ctx, 2, 1)
assert.DeepEqual(t, []*ethpb.Attestation{att3}, returned)
assert.DeepEqual(t, []interfaces.Attestation{att3}, returned)
}

View File

@@ -4,8 +4,8 @@ import (
"context"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/operations/attestations/kv"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
// Pool defines the necessary methods for Prysm attestations pool to serve
@@ -15,30 +15,30 @@ import (
type Pool interface {
// For Aggregated attestations
AggregateUnaggregatedAttestations(ctx context.Context) error
SaveAggregatedAttestation(att *ethpb.Attestation) error
SaveAggregatedAttestations(atts []*ethpb.Attestation) error
AggregatedAttestations() []*ethpb.Attestation
AggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []*ethpb.Attestation
DeleteAggregatedAttestation(att *ethpb.Attestation) error
HasAggregatedAttestation(att *ethpb.Attestation) (bool, error)
SaveAggregatedAttestation(att interfaces.Attestation) error
SaveAggregatedAttestations(atts []interfaces.Attestation) error
AggregatedAttestations() []interfaces.Attestation
AggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []interfaces.Attestation
DeleteAggregatedAttestation(att interfaces.Attestation) error
HasAggregatedAttestation(att interfaces.Attestation) (bool, error)
AggregatedAttestationCount() int
// For unaggregated attestations.
SaveUnaggregatedAttestation(att *ethpb.Attestation) error
SaveUnaggregatedAttestations(atts []*ethpb.Attestation) error
UnaggregatedAttestations() ([]*ethpb.Attestation, error)
UnaggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []*ethpb.Attestation
DeleteUnaggregatedAttestation(att *ethpb.Attestation) error
SaveUnaggregatedAttestation(att interfaces.Attestation) error
SaveUnaggregatedAttestations(atts []interfaces.Attestation) error
UnaggregatedAttestations() ([]interfaces.Attestation, error)
UnaggregatedAttestationsBySlotIndex(ctx context.Context, slot primitives.Slot, committeeIndex primitives.CommitteeIndex) []interfaces.Attestation
DeleteUnaggregatedAttestation(att interfaces.Attestation) error
DeleteSeenUnaggregatedAttestations() (int, error)
UnaggregatedAttestationCount() int
// For attestations that were included in the block.
SaveBlockAttestation(att *ethpb.Attestation) error
BlockAttestations() []*ethpb.Attestation
DeleteBlockAttestation(att *ethpb.Attestation) error
SaveBlockAttestation(att interfaces.Attestation) error
BlockAttestations() []interfaces.Attestation
DeleteBlockAttestation(att interfaces.Attestation) error
// For attestations to be passed to fork choice.
SaveForkchoiceAttestation(att *ethpb.Attestation) error
SaveForkchoiceAttestations(atts []*ethpb.Attestation) error
ForkchoiceAttestations() []*ethpb.Attestation
DeleteForkchoiceAttestation(att *ethpb.Attestation) error
SaveForkchoiceAttestation(att interfaces.Attestation) error
SaveForkchoiceAttestations(atts []interfaces.Attestation) error
ForkchoiceAttestations() []interfaces.Attestation
DeleteForkchoiceAttestation(att interfaces.Attestation) error
ForkchoiceAttestationCount() int
}

View File

@@ -9,8 +9,8 @@ import (
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/config/features"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
attaggregation "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation/attestations"
"github.com/prysmaticlabs/prysm/v5/time/slots"
"go.opencensus.io/trace"
@@ -67,7 +67,7 @@ func (s *Service) batchForkChoiceAtts(ctx context.Context) error {
atts := append(s.cfg.Pool.AggregatedAttestations(), s.cfg.Pool.BlockAttestations()...)
atts = append(atts, s.cfg.Pool.ForkchoiceAttestations()...)
attsByDataRoot := make(map[[32]byte][]*ethpb.Attestation, len(atts))
attsByDataRoot := make(map[[32]byte][]interfaces.Attestation, len(atts))
// Consolidate attestations by aggregating them by similar data root.
for _, att := range atts {
@@ -79,7 +79,7 @@ func (s *Service) batchForkChoiceAtts(ctx context.Context) error {
continue
}
attDataRoot, err := att.Data.HashTreeRoot()
attDataRoot, err := att.GetData().HashTreeRoot()
if err != nil {
return err
}
@@ -103,10 +103,10 @@ func (s *Service) batchForkChoiceAtts(ctx context.Context) error {
// This aggregates a list of attestations using the aggregation algorithm defined in AggregateAttestations
// and saves the attestations for fork choice.
func (s *Service) aggregateAndSaveForkChoiceAtts(atts []*ethpb.Attestation) error {
clonedAtts := make([]*ethpb.Attestation, len(atts))
func (s *Service) aggregateAndSaveForkChoiceAtts(atts []interfaces.Attestation) error {
clonedAtts := make([]interfaces.Attestation, len(atts))
for i, a := range atts {
clonedAtts[i] = ethpb.CopyAttestation(a)
clonedAtts[i] = interfaces.CopyAttestation(a)
}
aggregatedAtts, err := attaggregation.Aggregate(clonedAtts)
if err != nil {
@@ -118,12 +118,12 @@ func (s *Service) aggregateAndSaveForkChoiceAtts(atts []*ethpb.Attestation) erro
// This checks if the attestation has previously been aggregated for fork choice
// return true if yes, false if no.
func (s *Service) seen(att *ethpb.Attestation) (bool, error) {
attRoot, err := hash.Proto(att.Data)
func (s *Service) seen(att interfaces.Attestation) (bool, error) {
attRoot, err := hash.Proto(att.GetData())
if err != nil {
return false, err
}
incomingBits := att.AggregationBits
incomingBits := att.GetAggregationBits()
savedBits, ok := s.forkChoiceProcessedRoots.Get(attRoot)
if ok {
savedBitlist, ok := savedBits.(bitfield.Bitlist)

View File

@@ -7,6 +7,7 @@ import (
"testing"
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
attaggregation "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation/attestations"
@@ -25,35 +26,35 @@ func TestBatchAttestations_Multiple(t *testing.T) {
sig := priv.Sign([]byte("dummy_test_data"))
var mockRoot [32]byte
unaggregatedAtts := []*ethpb.Attestation{
{Data: &ethpb.AttestationData{
unaggregatedAtts := []interfaces.Attestation{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 2,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
Target: &ethpb.Checkpoint{Root: mockRoot[:]}}, AggregationBits: bitfield.Bitlist{0b100100}, Signature: sig.Marshal()},
{Data: &ethpb.AttestationData{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 1,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
Target: &ethpb.Checkpoint{Root: mockRoot[:]}}, AggregationBits: bitfield.Bitlist{0b101000}, Signature: sig.Marshal()},
{Data: &ethpb.AttestationData{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 0,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
Target: &ethpb.Checkpoint{Root: mockRoot[:]}}, AggregationBits: bitfield.Bitlist{0b100010}, Signature: sig.Marshal()},
}
aggregatedAtts := []*ethpb.Attestation{
{Data: &ethpb.AttestationData{
aggregatedAtts := []interfaces.Attestation{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 2,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
Target: &ethpb.Checkpoint{Root: mockRoot[:]}}, AggregationBits: bitfield.Bitlist{0b111000}, Signature: sig.Marshal()},
{Data: &ethpb.AttestationData{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 1,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
Target: &ethpb.Checkpoint{Root: mockRoot[:]}}, AggregationBits: bitfield.Bitlist{0b100011}, Signature: sig.Marshal()},
{Data: &ethpb.AttestationData{
&ethpb.Attestation{Data: &ethpb.AttestationData{
Slot: 0,
BeaconBlockRoot: mockRoot[:],
Source: &ethpb.Checkpoint{Root: mockRoot[:]},
@@ -93,12 +94,12 @@ func TestBatchAttestations_Multiple(t *testing.T) {
}
require.NoError(t, s.batchForkChoiceAtts(context.Background()))
wanted, err := attaggregation.Aggregate([]*ethpb.Attestation{aggregatedAtts[0], blockAtts[0]})
wanted, err := attaggregation.Aggregate([]interfaces.Attestation{aggregatedAtts[0], blockAtts[0]})
require.NoError(t, err)
aggregated, err := attaggregation.Aggregate([]*ethpb.Attestation{aggregatedAtts[1], blockAtts[1]})
aggregated, err := attaggregation.Aggregate([]interfaces.Attestation{aggregatedAtts[1], blockAtts[1]})
require.NoError(t, err)
wanted = append(wanted, aggregated...)
aggregated, err = attaggregation.Aggregate([]*ethpb.Attestation{aggregatedAtts[2], blockAtts[2]})
aggregated, err = attaggregation.Aggregate([]interfaces.Attestation{aggregatedAtts[2], blockAtts[2]})
require.NoError(t, err)
wanted = append(wanted, aggregated...)
@@ -106,10 +107,10 @@ func TestBatchAttestations_Multiple(t *testing.T) {
received := s.cfg.Pool.ForkchoiceAttestations()
sort.Slice(received, func(i, j int) bool {
return received[i].Data.Slot < received[j].Data.Slot
return received[i].GetData().Slot < received[j].GetData().Slot
})
sort.Slice(wanted, func(i, j int) bool {
return wanted[i].Data.Slot < wanted[j].Data.Slot
return wanted[i].GetData().Slot < wanted[j].GetData().Slot
})
assert.DeepSSZEqual(t, wanted, received)
@@ -129,18 +130,18 @@ func TestBatchAttestations_Single(t *testing.T) {
Target: &ethpb.Checkpoint{Root: mockRoot[:]},
}
unaggregatedAtts := []*ethpb.Attestation{
{Data: d, AggregationBits: bitfield.Bitlist{0b101000}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b100100}, Signature: sig.Marshal()},
unaggregatedAtts := []interfaces.Attestation{
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b101000}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b100100}, Signature: sig.Marshal()},
}
aggregatedAtts := []*ethpb.Attestation{
{Data: d, AggregationBits: bitfield.Bitlist{0b101100}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()},
aggregatedAtts := []interfaces.Attestation{
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b101100}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()},
}
blockAtts := []*ethpb.Attestation{
{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b100010}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()}, // Duplicated
blockAtts := []interfaces.Attestation{
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b100010}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b110010}, Signature: sig.Marshal()}, // Duplicated
}
require.NoError(t, s.cfg.Pool.SaveUnaggregatedAttestations(unaggregatedAtts))
require.NoError(t, s.cfg.Pool.SaveAggregatedAttestations(aggregatedAtts))
@@ -174,9 +175,9 @@ func TestAggregateAndSaveForkChoiceAtts_Single(t *testing.T) {
Target: &ethpb.Checkpoint{Root: mockRoot[:]},
}
atts := []*ethpb.Attestation{
{Data: d, AggregationBits: bitfield.Bitlist{0b101}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b110}, Signature: sig.Marshal()}}
atts := []interfaces.Attestation{
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b101}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b110}, Signature: sig.Marshal()}}
require.NoError(t, s.aggregateAndSaveForkChoiceAtts(atts))
wanted, err := attaggregation.Aggregate(atts)
@@ -204,19 +205,19 @@ func TestAggregateAndSaveForkChoiceAtts_Multiple(t *testing.T) {
require.Equal(t, true, ok, "Entity is not of type *ethpb.AttestationData")
d2.Slot = 2
atts1 := []*ethpb.Attestation{
{Data: d, AggregationBits: bitfield.Bitlist{0b101}, Signature: sig.Marshal()},
{Data: d, AggregationBits: bitfield.Bitlist{0b110}, Signature: sig.Marshal()},
atts1 := []interfaces.Attestation{
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b101}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d, AggregationBits: bitfield.Bitlist{0b110}, Signature: sig.Marshal()},
}
require.NoError(t, s.aggregateAndSaveForkChoiceAtts(atts1))
atts2 := []*ethpb.Attestation{
{Data: d1, AggregationBits: bitfield.Bitlist{0b10110}, Signature: sig.Marshal()},
{Data: d1, AggregationBits: bitfield.Bitlist{0b11100}, Signature: sig.Marshal()},
{Data: d1, AggregationBits: bitfield.Bitlist{0b11000}, Signature: sig.Marshal()},
atts2 := []interfaces.Attestation{
&ethpb.Attestation{Data: d1, AggregationBits: bitfield.Bitlist{0b10110}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d1, AggregationBits: bitfield.Bitlist{0b11100}, Signature: sig.Marshal()},
&ethpb.Attestation{Data: d1, AggregationBits: bitfield.Bitlist{0b11000}, Signature: sig.Marshal()},
}
require.NoError(t, s.aggregateAndSaveForkChoiceAtts(atts2))
att3 := []*ethpb.Attestation{
{Data: d2, AggregationBits: bitfield.Bitlist{0b1100}, Signature: sig.Marshal()},
att3 := []interfaces.Attestation{
&ethpb.Attestation{Data: d2, AggregationBits: bitfield.Bitlist{0b1100}, Signature: sig.Marshal()},
}
require.NoError(t, s.aggregateAndSaveForkChoiceAtts(att3))
@@ -230,7 +231,7 @@ func TestAggregateAndSaveForkChoiceAtts_Multiple(t *testing.T) {
received := s.cfg.Pool.ForkchoiceAttestations()
sort.Slice(received, func(i, j int) bool {
return received[i].Data.Slot < received[j].Data.Slot
return received[i].GetData().Slot < received[j].GetData().Slot
})
for i, a := range wanted {
assert.Equal(t, true, proto.Equal(a, received[i]))

View File

@@ -29,7 +29,7 @@ func (s *Service) pruneAttsPool() {
func (s *Service) pruneExpiredAtts() {
aggregatedAtts := s.cfg.Pool.AggregatedAttestations()
for _, att := range aggregatedAtts {
if s.expired(att.Data.Slot) {
if s.expired(att.GetData().Slot) {
if err := s.cfg.Pool.DeleteAggregatedAttestation(att); err != nil {
log.WithError(err).Error("Could not delete expired aggregated attestation")
}
@@ -46,7 +46,7 @@ func (s *Service) pruneExpiredAtts() {
return
}
for _, att := range unAggregatedAtts {
if s.expired(att.Data.Slot) {
if s.expired(att.GetData().Slot) {
if err := s.cfg.Pool.DeleteUnaggregatedAttestation(att); err != nil {
log.WithError(err).Error("Could not delete expired unaggregated attestation")
}
@@ -56,7 +56,7 @@ func (s *Service) pruneExpiredAtts() {
blockAtts := s.cfg.Pool.BlockAttestations()
for _, att := range blockAtts {
if s.expired(att.Data.Slot) {
if s.expired(att.GetData().Slot) {
if err := s.cfg.Pool.DeleteBlockAttestation(att); err != nil {
log.WithError(err).Error("Could not delete expired block attestation")
}

View File

@@ -9,6 +9,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/async"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
@@ -31,15 +32,15 @@ func TestPruneExpired_Ticker(t *testing.T) {
ad2 := util.HydrateAttestationData(&ethpb.AttestationData{Slot: 1})
atts := []*ethpb.Attestation{
{Data: ad1, AggregationBits: bitfield.Bitlist{0b1000, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
{Data: ad2, AggregationBits: bitfield.Bitlist{0b1000, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
atts := []interfaces.Attestation{
&ethpb.Attestation{Data: ad1, AggregationBits: bitfield.Bitlist{0b1000, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
&ethpb.Attestation{Data: ad2, AggregationBits: bitfield.Bitlist{0b1000, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
}
require.NoError(t, s.cfg.Pool.SaveUnaggregatedAttestations(atts))
require.Equal(t, 2, s.cfg.Pool.UnaggregatedAttestationCount(), "Unexpected number of attestations")
atts = []*ethpb.Attestation{
{Data: ad1, AggregationBits: bitfield.Bitlist{0b1101, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
{Data: ad2, AggregationBits: bitfield.Bitlist{0b1101, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
atts = []interfaces.Attestation{
&ethpb.Attestation{Data: ad1, AggregationBits: bitfield.Bitlist{0b1101, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
&ethpb.Attestation{Data: ad2, AggregationBits: bitfield.Bitlist{0b1101, 0b1}, Signature: make([]byte, fieldparams.BLSSignatureLength)},
}
require.NoError(t, s.cfg.Pool.SaveAggregatedAttestations(atts))
assert.Equal(t, 2, s.cfg.Pool.AggregatedAttestationCount())
@@ -57,17 +58,17 @@ func TestPruneExpired_Ticker(t *testing.T) {
atts, err := s.cfg.Pool.UnaggregatedAttestations()
require.NoError(t, err)
for _, attestation := range atts {
if attestation.Data.Slot == 0 {
if attestation.GetData().Slot == 0 {
return
}
}
for _, attestation := range s.cfg.Pool.AggregatedAttestations() {
if attestation.Data.Slot == 0 {
if attestation.GetData().Slot == 0 {
return
}
}
for _, attestation := range s.cfg.Pool.BlockAttestations() {
if attestation.Data.Slot == 0 {
if attestation.GetData().Slot == 0 {
return
}
}
@@ -96,7 +97,7 @@ func TestPruneExpired_PruneExpiredAtts(t *testing.T) {
att2 := &ethpb.Attestation{Data: ad1, AggregationBits: bitfield.Bitlist{0b1111}}
att3 := &ethpb.Attestation{Data: ad2, AggregationBits: bitfield.Bitlist{0b1101}}
att4 := &ethpb.Attestation{Data: ad2, AggregationBits: bitfield.Bitlist{0b1110}}
atts := []*ethpb.Attestation{att1, att2, att3, att4}
atts := []interfaces.Attestation{att1, att2, att3, att4}
require.NoError(t, s.cfg.Pool.SaveAggregatedAttestations(atts))
for _, att := range atts {
require.NoError(t, s.cfg.Pool.SaveBlockAttestation(att))
@@ -108,12 +109,12 @@ func TestPruneExpired_PruneExpiredAtts(t *testing.T) {
s.pruneExpiredAtts()
// All the attestations on slot 0 should be pruned.
for _, attestation := range s.cfg.Pool.AggregatedAttestations() {
if attestation.Data.Slot == 0 {
if attestation.GetData().Slot == 0 {
t.Error("Should be pruned")
}
}
for _, attestation := range s.cfg.Pool.BlockAttestations() {
if attestation.Data.Slot == 0 {
if attestation.GetData().Slot == 0 {
t.Error("Should be pruned")
}
}

View File

@@ -21,6 +21,7 @@ go_library(
"//beacon-chain/core/time:go_default_library",
"//beacon-chain/state:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//container/slice:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
@@ -47,6 +48,7 @@ go_test(
"//beacon-chain/state:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/bls:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",

View File

@@ -8,6 +8,7 @@ go_library(
visibility = ["//visibility:public"],
deps = [
"//beacon-chain/state:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
],
)

View File

@@ -4,17 +4,18 @@ import (
"context"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
// PoolMock is a fake implementation of PoolManager.
type PoolMock struct {
PendingAttSlashings []*ethpb.AttesterSlashing
PendingAttSlashings []interfaces.AttesterSlashing
PendingPropSlashings []*ethpb.ProposerSlashing
}
// PendingAttesterSlashings --
func (m *PoolMock) PendingAttesterSlashings(_ context.Context, _ state.ReadOnlyBeaconState, _ bool) []*ethpb.AttesterSlashing {
func (m *PoolMock) PendingAttesterSlashings(_ context.Context, _ state.ReadOnlyBeaconState, _ bool) []interfaces.AttesterSlashing {
return m.PendingAttSlashings
}
@@ -24,7 +25,7 @@ func (m *PoolMock) PendingProposerSlashings(_ context.Context, _ state.ReadOnlyB
}
// InsertAttesterSlashing --
func (m *PoolMock) InsertAttesterSlashing(_ context.Context, _ state.ReadOnlyBeaconState, slashing *ethpb.AttesterSlashing) error {
func (m *PoolMock) InsertAttesterSlashing(_ context.Context, _ state.ReadOnlyBeaconState, slashing interfaces.AttesterSlashing) error {
m.PendingAttSlashings = append(m.PendingAttSlashings, slashing)
return nil
}
@@ -36,7 +37,7 @@ func (m *PoolMock) InsertProposerSlashing(_ context.Context, _ state.ReadOnlyBea
}
// MarkIncludedAttesterSlashing --
func (*PoolMock) MarkIncludedAttesterSlashing(_ *ethpb.AttesterSlashing) {
func (*PoolMock) MarkIncludedAttesterSlashing(_ interfaces.AttesterSlashing) {
panic("implement me")
}

View File

@@ -11,6 +11,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/time"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/container/slice"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -30,7 +31,7 @@ func NewPool() *Pool {
// PendingAttesterSlashings returns attester slashings that are able to be included into a block.
// This method will return the amount of pending attester slashings for a block transition unless parameter `noLimit` is true
// to indicate the request is for noLimit pending items.
func (p *Pool) PendingAttesterSlashings(ctx context.Context, state state.ReadOnlyBeaconState, noLimit bool) []*ethpb.AttesterSlashing {
func (p *Pool) PendingAttesterSlashings(ctx context.Context, state state.ReadOnlyBeaconState, noLimit bool) []interfaces.AttesterSlashing {
p.lock.Lock()
defer p.lock.Unlock()
_, span := trace.StartSpan(ctx, "operations.PendingAttesterSlashing")
@@ -46,7 +47,7 @@ func (p *Pool) PendingAttesterSlashings(ctx context.Context, state state.ReadOnl
if noLimit {
maxSlashings = uint64(len(p.pendingAttesterSlashing))
}
pending := make([]*ethpb.AttesterSlashing, 0, maxSlashings)
pending := make([]interfaces.AttesterSlashing, 0, maxSlashings)
for i := 0; i < len(p.pendingAttesterSlashing); i++ {
if uint64(len(pending)) >= maxSlashings {
break
@@ -63,7 +64,10 @@ func (p *Pool) PendingAttesterSlashings(ctx context.Context, state state.ReadOnl
continue
}
attSlashing := slashing.attesterSlashing
slashedVal := slice.IntersectionUint64(attSlashing.Attestation_1.AttestingIndices, attSlashing.Attestation_2.AttestingIndices)
slashedVal := slice.IntersectionUint64(
attSlashing.GetFirstAttestation().GetAttestingIndices(),
attSlashing.GetSecondAttestation().GetAttestingIndices(),
)
for _, idx := range slashedVal {
included[primitives.ValidatorIndex(idx)] = true
}
@@ -118,7 +122,7 @@ func (p *Pool) PendingProposerSlashings(ctx context.Context, state state.ReadOnl
func (p *Pool) InsertAttesterSlashing(
ctx context.Context,
state state.ReadOnlyBeaconState,
slashing *ethpb.AttesterSlashing,
slashing interfaces.AttesterSlashing,
) error {
p.lock.Lock()
defer p.lock.Unlock()
@@ -129,7 +133,7 @@ func (p *Pool) InsertAttesterSlashing(
return errors.Wrap(err, "could not verify attester slashing")
}
slashedVal := slice.IntersectionUint64(slashing.Attestation_1.AttestingIndices, slashing.Attestation_2.AttestingIndices)
slashedVal := slice.IntersectionUint64(slashing.GetFirstAttestation().GetAttestingIndices(), slashing.GetSecondAttestation().GetAttestingIndices())
cantSlash := make([]uint64, 0, len(slashedVal))
slashingReason := ""
for _, val := range slashedVal {
@@ -229,10 +233,10 @@ func (p *Pool) InsertProposerSlashing(
// MarkIncludedAttesterSlashing is used when an attester slashing has been included in a beacon block.
// Every block seen by this node that contains proposer slashings should call this method to include
// the proposer slashings.
func (p *Pool) MarkIncludedAttesterSlashing(as *ethpb.AttesterSlashing) {
func (p *Pool) MarkIncludedAttesterSlashing(as interfaces.AttesterSlashing) {
p.lock.Lock()
defer p.lock.Unlock()
slashedVal := slice.IntersectionUint64(as.Attestation_1.AttestingIndices, as.Attestation_2.AttestingIndices)
slashedVal := slice.IntersectionUint64(as.GetFirstAttestation().GetAttestingIndices(), as.GetSecondAttestation().GetAttestingIndices())
for _, val := range slashedVal {
i := sort.Search(len(p.pendingAttesterSlashing), func(i int) bool {
return uint64(p.pendingAttesterSlashing[i].validatorToSlash) >= val

View File

@@ -6,6 +6,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -314,7 +315,7 @@ func TestPool_InsertAttesterSlashing_SigFailsVerify_ClearPool(t *testing.T) {
// We mess up the signature of the second slashing.
badSig := make([]byte, 96)
copy(badSig, "muahaha")
pendingSlashings[1].attesterSlashing.Attestation_1.Signature = badSig
pendingSlashings[1].attesterSlashing.(*ethpb.AttesterSlashing).Attestation_1.Signature = badSig
slashings[1].Attestation_1.Signature = badSig
p := &Pool{
pendingAttesterSlashing: make([]*PendingAttesterSlashing, 0),
@@ -455,7 +456,7 @@ func TestPool_PendingAttesterSlashings(t *testing.T) {
params.SetupTestConfigCleanup(t)
beaconState, privKeys := util.DeterministicGenesisState(t, 64)
pendingSlashings := make([]*PendingAttesterSlashing, 20)
slashings := make([]*ethpb.AttesterSlashing, 20)
slashings := make([]interfaces.AttesterSlashing, 20)
for i := 0; i < len(pendingSlashings); i++ {
sl, err := util.GenerateAttesterSlashingForValidator(beaconState, privKeys[i], primitives.ValidatorIndex(i))
require.NoError(t, err)
@@ -468,14 +469,14 @@ func TestPool_PendingAttesterSlashings(t *testing.T) {
tests := []struct {
name string
fields fields
want []*ethpb.AttesterSlashing
want []interfaces.AttesterSlashing
}{
{
name: "Empty list",
fields: fields{
pending: []*PendingAttesterSlashing{},
},
want: []*ethpb.AttesterSlashing{},
want: []interfaces.AttesterSlashing{},
},
{
name: "All pending",
@@ -530,7 +531,7 @@ func TestPool_PendingAttesterSlashings_Slashed(t *testing.T) {
require.NoError(t, beaconState.UpdateValidatorAtIndex(5, val))
pendingSlashings := make([]*PendingAttesterSlashing, 20)
pendingSlashings2 := make([]*PendingAttesterSlashing, 20)
slashings := make([]*ethpb.AttesterSlashing, 20)
slashings := make([]interfaces.AttesterSlashing, 20)
for i := 0; i < len(pendingSlashings); i++ {
sl, err := util.GenerateAttesterSlashingForValidator(beaconState, privKeys[i], primitives.ValidatorIndex(i))
require.NoError(t, err)
@@ -548,7 +549,7 @@ func TestPool_PendingAttesterSlashings_Slashed(t *testing.T) {
tests := []struct {
name string
fields fields
want []*ethpb.AttesterSlashing
want []interfaces.AttesterSlashing
}{
{
name: "One item",
@@ -588,7 +589,7 @@ func TestPool_PendingAttesterSlashings_NoDuplicates(t *testing.T) {
params.OverrideBeaconConfig(conf)
beaconState, privKeys := util.DeterministicGenesisState(t, 64)
pendingSlashings := make([]*PendingAttesterSlashing, 3)
slashings := make([]*ethpb.AttesterSlashing, 3)
slashings := make([]interfaces.AttesterSlashing, 3)
for i := 0; i < 2; i++ {
sl, err := util.GenerateAttesterSlashingForValidator(beaconState, privKeys[i], primitives.ValidatorIndex(i))
require.NoError(t, err)

View File

@@ -5,6 +5,7 @@ import (
"sync"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
@@ -14,7 +15,7 @@ type PoolInserter interface {
InsertAttesterSlashing(
ctx context.Context,
state state.ReadOnlyBeaconState,
slashing *ethpb.AttesterSlashing,
slashing interfaces.AttesterSlashing,
) error
InsertProposerSlashing(
ctx context.Context,
@@ -27,9 +28,9 @@ type PoolInserter interface {
// This pool is used by proposers to insert data into new blocks.
type PoolManager interface {
PoolInserter
PendingAttesterSlashings(ctx context.Context, state state.ReadOnlyBeaconState, noLimit bool) []*ethpb.AttesterSlashing
PendingAttesterSlashings(ctx context.Context, state state.ReadOnlyBeaconState, noLimit bool) []interfaces.AttesterSlashing
PendingProposerSlashings(ctx context.Context, state state.ReadOnlyBeaconState, noLimit bool) []*ethpb.ProposerSlashing
MarkIncludedAttesterSlashing(as *ethpb.AttesterSlashing)
MarkIncludedAttesterSlashing(as interfaces.AttesterSlashing)
MarkIncludedProposerSlashing(ps *ethpb.ProposerSlashing)
}
@@ -44,6 +45,6 @@ type Pool struct {
// PendingAttesterSlashing represents an attester slashing in the operation pool.
// Allows for easy binary searching of included validator indexes.
type PendingAttesterSlashing struct {
attesterSlashing *ethpb.AttesterSlashing
attesterSlashing interfaces.AttesterSlashing
validatorToSlash primitives.ValidatorIndex
}

View File

@@ -57,6 +57,7 @@ go_library(
"//cmd/beacon-chain/flags:go_default_library",
"//config/features:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//consensus-types/wrapper:go_default_library",
"//container/leaky-bucket:go_default_library",

View File

@@ -12,6 +12,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/altair"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
"github.com/prysmaticlabs/prysm/v5/monitoring/tracing"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -56,7 +57,7 @@ func (s *Service) Broadcast(ctx context.Context, msg proto.Message) error {
// BroadcastAttestation broadcasts an attestation to the p2p network, the message is assumed to be
// broadcasted to the current fork.
func (s *Service) BroadcastAttestation(ctx context.Context, subnet uint64, att *ethpb.Attestation) error {
func (s *Service) BroadcastAttestation(ctx context.Context, subnet uint64, att interfaces.Attestation) error {
if att == nil {
return errors.New("attempted to broadcast nil attestation")
}
@@ -96,7 +97,7 @@ func (s *Service) BroadcastSyncCommitteeMessage(ctx context.Context, subnet uint
return nil
}
func (s *Service) internalBroadcastAttestation(ctx context.Context, subnet uint64, att *ethpb.Attestation, forkDigest [4]byte) {
func (s *Service) internalBroadcastAttestation(ctx context.Context, subnet uint64, att interfaces.Attestation, forkDigest [4]byte) {
_, span := trace.StartSpan(ctx, "p2p.internalBroadcastAttestation")
defer span.End()
ctx = trace.NewContext(context.Background(), span) // clear parent context / deadline.
@@ -112,7 +113,7 @@ func (s *Service) internalBroadcastAttestation(ctx context.Context, subnet uint6
span.AddAttributes(
trace.BoolAttribute("hasPeer", hasPeer),
trace.Int64Attribute("slot", int64(att.Data.Slot)), // lint:ignore uintcast -- It's safe to do this for tracing.
trace.Int64Attribute("slot", int64(att.GetData().Slot)), // lint:ignore uintcast -- It's safe to do this for tracing.
trace.Int64Attribute("subnet", int64(subnet)), // lint:ignore uintcast -- It's safe to do this for tracing.
)
@@ -138,9 +139,9 @@ func (s *Service) internalBroadcastAttestation(ctx context.Context, subnet uint6
// In the event our attestation is outdated and beyond the
// acceptable threshold, we exit early and do not broadcast it.
currSlot := slots.CurrentSlot(uint64(s.genesisTime.Unix()))
if err := helpers.ValidateAttestationTime(att.Data.Slot, s.genesisTime, params.BeaconConfig().MaximumGossipClockDisparityDuration()); err != nil {
if err := helpers.ValidateAttestationTime(att.GetData().Slot, s.genesisTime, params.BeaconConfig().MaximumGossipClockDisparityDuration()); err != nil {
log.WithFields(logrus.Fields{
"attestationSlot": att.Data.Slot,
"attestationSlot": att.GetData().Slot,
"currentSlot": currSlot,
}).WithError(err).Warning("Attestation is too old to broadcast, discarding it")
return

View File

@@ -12,6 +12,7 @@ import (
"github.com/multiformats/go-multiaddr"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/encoder"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/peers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/metadata"
"google.golang.org/protobuf/proto"
@@ -33,7 +34,7 @@ type P2P interface {
// Broadcaster broadcasts messages to peers over the p2p pubsub protocol.
type Broadcaster interface {
Broadcast(context.Context, proto.Message) error
BroadcastAttestation(ctx context.Context, subnet uint64, att *ethpb.Attestation) error
BroadcastAttestation(ctx context.Context, subnet uint64, att interfaces.Attestation) error
BroadcastSyncCommitteeMessage(ctx context.Context, subnet uint64, sMsg *ethpb.SyncCommitteeMessage) error
BroadcastBlob(ctx context.Context, subnet uint64, blob *ethpb.BlobSidecar) error
}

View File

@@ -20,6 +20,7 @@ go_library(
"//beacon-chain/p2p/encoder:go_default_library",
"//beacon-chain/p2p/peers:go_default_library",
"//beacon-chain/p2p/peers/scorers:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
"//proto/prysm/v1alpha1/metadata:go_default_library",
"@com_github_ethereum_go_ethereum//crypto:go_default_library",

View File

@@ -12,6 +12,7 @@ import (
"github.com/multiformats/go-multiaddr"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/encoder"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/peers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/metadata"
"google.golang.org/protobuf/proto"
@@ -134,7 +135,7 @@ func (_ *FakeP2P) Broadcast(_ context.Context, _ proto.Message) error {
}
// BroadcastAttestation -- fake.
func (_ *FakeP2P) BroadcastAttestation(_ context.Context, _ uint64, _ *ethpb.Attestation) error {
func (_ *FakeP2P) BroadcastAttestation(_ context.Context, _ uint64, _ interfaces.Attestation) error {
return nil
}

View File

@@ -5,6 +5,7 @@ import (
"sync"
"sync/atomic"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"google.golang.org/protobuf/proto"
)
@@ -13,7 +14,7 @@ import (
type MockBroadcaster struct {
BroadcastCalled atomic.Bool
BroadcastMessages []proto.Message
BroadcastAttestations []*ethpb.Attestation
BroadcastAttestations []interfaces.Attestation
msgLock sync.Mutex
attLock sync.Mutex
}
@@ -28,7 +29,7 @@ func (m *MockBroadcaster) Broadcast(_ context.Context, msg proto.Message) error
}
// BroadcastAttestation records a broadcast occurred.
func (m *MockBroadcaster) BroadcastAttestation(_ context.Context, _ uint64, a *ethpb.Attestation) error {
func (m *MockBroadcaster) BroadcastAttestation(_ context.Context, _ uint64, a interfaces.Attestation) error {
m.BroadcastCalled.Store(true)
m.attLock.Lock()
defer m.attLock.Unlock()

View File

@@ -25,6 +25,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/encoder"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/peers"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/p2p/peers/scorers"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/metadata"
"github.com/sirupsen/logrus"
@@ -166,7 +167,7 @@ func (p *TestP2P) Broadcast(_ context.Context, _ proto.Message) error {
}
// BroadcastAttestation broadcasts an attestation.
func (p *TestP2P) BroadcastAttestation(_ context.Context, _ uint64, _ *ethpb.Attestation) error {
func (p *TestP2P) BroadcastAttestation(_ context.Context, _ uint64, _ interfaces.Attestation) error {
p.BroadcastCalled.Store(true)
return nil
}

View File

@@ -878,7 +878,13 @@ func (s *Server) GetBlockAttestations(w http.ResponseWriter, r *http.Request) {
consensusAtts := blk.Block().Body().Attestations()
atts := make([]*structs.Attestation, len(consensusAtts))
for i, att := range consensusAtts {
atts[i] = structs.AttFromConsensus(att)
a, ok := att.(*eth.Attestation)
if ok {
atts[i] = structs.AttFromConsensus(a)
} else {
httputil.HandleError(w, fmt.Sprintf("unable to convert consensus attestations of type %T", att), http.StatusInternalServerError)
return
}
}
root, err := blk.Block().HashTreeRoot()
if err != nil {

View File

@@ -58,7 +58,13 @@ func (s *Server) ListAttestations(w http.ResponseWriter, r *http.Request) {
if isEmptyReq {
allAtts := make([]*structs.Attestation, len(attestations))
for i, att := range attestations {
allAtts[i] = structs.AttFromConsensus(att)
a, ok := att.(*eth.Attestation)
if ok {
allAtts[i] = structs.AttFromConsensus(a)
} else {
httputil.HandleError(w, fmt.Sprintf("unable to convert attestations of type %T", att), http.StatusInternalServerError)
return
}
}
httputil.WriteJson(w, &structs.ListAttestationsResponse{Data: allAtts})
return
@@ -67,11 +73,17 @@ func (s *Server) ListAttestations(w http.ResponseWriter, r *http.Request) {
bothDefined := rawSlot != "" && rawCommitteeIndex != ""
filteredAtts := make([]*structs.Attestation, 0, len(attestations))
for _, att := range attestations {
committeeIndexMatch := rawCommitteeIndex != "" && att.Data.CommitteeIndex == primitives.CommitteeIndex(committeeIndex)
slotMatch := rawSlot != "" && att.Data.Slot == primitives.Slot(slot)
committeeIndexMatch := rawCommitteeIndex != "" && att.GetData().CommitteeIndex == primitives.CommitteeIndex(committeeIndex)
slotMatch := rawSlot != "" && att.GetData().Slot == primitives.Slot(slot)
shouldAppend := (bothDefined && committeeIndexMatch && slotMatch) || (!bothDefined && (committeeIndexMatch || slotMatch))
if shouldAppend {
filteredAtts = append(filteredAtts, structs.AttFromConsensus(att))
a, ok := att.(*eth.Attestation)
if ok {
filteredAtts = append(filteredAtts, structs.AttFromConsensus(a))
} else {
httputil.HandleError(w, fmt.Sprintf("unable to convert attestations of type %T", att), http.StatusInternalServerError)
return
}
}
}
httputil.WriteJson(w, &structs.ListAttestationsResponse{Data: filteredAtts})
@@ -455,7 +467,17 @@ func (s *Server) GetAttesterSlashings(w http.ResponseWriter, r *http.Request) {
return
}
sourceSlashings := s.SlashingsPool.PendingAttesterSlashings(ctx, headState, true /* return unlimited slashings */)
slashings := structs.AttesterSlashingsFromConsensus(sourceSlashings)
ss := make([]*eth.AttesterSlashing, 0, len(sourceSlashings))
for _, slashing := range sourceSlashings {
s, ok := slashing.(*eth.AttesterSlashing)
if ok {
ss = append(ss, s)
} else {
httputil.HandleError(w, fmt.Sprintf("unable to convert slashing of type %T", slashing), http.StatusInternalServerError)
return
}
}
slashings := structs.AttesterSlashingsFromConsensus(ss)
httputil.WriteJson(w, &structs.GetAttesterSlashingsResponse{Data: slashings})
}

View File

@@ -29,6 +29,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/rpc/core"
state_native "github.com/prysmaticlabs/prysm/v5/beacon-chain/state/state-native"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/crypto/bls/common"
@@ -115,8 +116,8 @@ func TestListAttestations(t *testing.T) {
s := &Server{
AttestationsPool: attestations.NewPool(),
}
require.NoError(t, s.AttestationsPool.SaveAggregatedAttestations([]*ethpbv1alpha1.Attestation{att1, att2}))
require.NoError(t, s.AttestationsPool.SaveUnaggregatedAttestations([]*ethpbv1alpha1.Attestation{att3, att4}))
require.NoError(t, s.AttestationsPool.SaveAggregatedAttestations([]interfaces.Attestation{att1, att2}))
require.NoError(t, s.AttestationsPool.SaveUnaggregatedAttestations([]interfaces.Attestation{att3, att4}))
t.Run("empty request", func(t *testing.T) {
url := "http://example.com"
@@ -240,15 +241,15 @@ func TestSubmitAttestations(t *testing.T) {
assert.Equal(t, http.StatusOK, writer.Code)
assert.Equal(t, true, broadcaster.BroadcastCalled.Load())
assert.Equal(t, 1, broadcaster.NumAttestations())
assert.Equal(t, "0x03", hexutil.Encode(broadcaster.BroadcastAttestations[0].AggregationBits))
assert.Equal(t, "0x8146f4397bfd8fd057ebbcd6a67327bdc7ed5fb650533edcb6377b650dea0b6da64c14ecd60846d5c0a0cd43893d6972092500f82c9d8a955e2b58c5ed3cbe885d84008ace6bd86ba9e23652f58e2ec207cec494c916063257abf285b9b15b15", hexutil.Encode(broadcaster.BroadcastAttestations[0].Signature))
assert.Equal(t, primitives.Slot(0), broadcaster.BroadcastAttestations[0].Data.Slot)
assert.Equal(t, primitives.CommitteeIndex(0), broadcaster.BroadcastAttestations[0].Data.CommitteeIndex)
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].Data.BeaconBlockRoot))
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].Data.Source.Root))
assert.Equal(t, primitives.Epoch(0), broadcaster.BroadcastAttestations[0].Data.Source.Epoch)
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].Data.Target.Root))
assert.Equal(t, primitives.Epoch(0), broadcaster.BroadcastAttestations[0].Data.Target.Epoch)
assert.Equal(t, "0x03", hexutil.Encode(broadcaster.BroadcastAttestations[0].GetAggregationBits()))
assert.Equal(t, "0x8146f4397bfd8fd057ebbcd6a67327bdc7ed5fb650533edcb6377b650dea0b6da64c14ecd60846d5c0a0cd43893d6972092500f82c9d8a955e2b58c5ed3cbe885d84008ace6bd86ba9e23652f58e2ec207cec494c916063257abf285b9b15b15", hexutil.Encode(broadcaster.BroadcastAttestations[0].GetSignature()))
assert.Equal(t, primitives.Slot(0), broadcaster.BroadcastAttestations[0].GetData().Slot)
assert.Equal(t, primitives.CommitteeIndex(0), broadcaster.BroadcastAttestations[0].GetData().CommitteeIndex)
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].GetData().BeaconBlockRoot))
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].GetData().Source.Root))
assert.Equal(t, primitives.Epoch(0), broadcaster.BroadcastAttestations[0].GetData().Source.Epoch)
assert.Equal(t, "0xcf8e0d4e9587369b2301d0790347320302cc0943d5a1884560367e8208d920f2", hexutil.Encode(broadcaster.BroadcastAttestations[0].GetData().Target.Root))
assert.Equal(t, primitives.Epoch(0), broadcaster.BroadcastAttestations[0].GetData().Target.Epoch)
assert.Equal(t, 1, s.AttestationsPool.UnaggregatedAttestationCount())
})
t.Run("multiple", func(t *testing.T) {
@@ -1060,7 +1061,7 @@ func TestGetAttesterSlashings(t *testing.T) {
s := &Server{
ChainInfoFetcher: &blockchainmock.ChainService{State: bs},
SlashingsPool: &slashingsmock.PoolMock{PendingAttSlashings: []*ethpbv1alpha1.AttesterSlashing{slashing1, slashing2}},
SlashingsPool: &slashingsmock.PoolMock{PendingAttSlashings: []interfaces.AttesterSlashing{slashing1, slashing2}},
}
request := httptest.NewRequest(http.MethodGet, "http://example.com/beacon/pool/attester_slashings", nil)

View File

@@ -22,6 +22,7 @@ go_library(
"//network/httputil:go_default_library",
"//proto/eth/v1:go_default_library",
"//proto/eth/v2:go_default_library",
"//proto/prysm/v1alpha1:go_default_library",
"//runtime/version:go_default_library",
"//time/slots:go_default_library",
"@com_github_ethereum_go_ethereum//common/hexutil:go_default_library",

View File

@@ -22,6 +22,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/network/httputil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/eth/v1"
ethpbv2 "github.com/prysmaticlabs/prysm/v5/proto/eth/v2"
eth "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/runtime/version"
"github.com/prysmaticlabs/prysm/v5/time/slots"
"go.opencensus.io/trace"
@@ -173,7 +174,11 @@ func handleBlockOperationEvents(w http.ResponseWriter, flusher http.Flusher, req
if !ok {
return write(w, flusher, topicDataMismatch, event.Data, AttestationTopic)
}
att := structs.AttFromConsensus(attData.Attestation)
a, ok := attData.Attestation.(*eth.Attestation)
if !ok {
return write(w, flusher, topicDataMismatch, event.Data, AttestationTopic)
}
att := structs.AttFromConsensus(a)
return send(w, flusher, AttestationTopic, att)
case operation.ExitReceived:
if _, ok := requestedTopics[VoluntaryExitTopic]; !ok {
@@ -229,7 +234,11 @@ func handleBlockOperationEvents(w http.ResponseWriter, flusher http.Flusher, req
if !ok {
return write(w, flusher, topicDataMismatch, event.Data, AttesterSlashingTopic)
}
return send(w, flusher, AttesterSlashingTopic, structs.AttesterSlashingFromConsensus(attesterSlashingData.AttesterSlashing))
slashing, ok := attesterSlashingData.AttesterSlashing.(*eth.AttesterSlashing)
if ok {
return send(w, flusher, AttesterSlashingTopic, structs.AttesterSlashingFromConsensus(slashing))
}
// TODO: extend to Electra
case operation.ProposerSlashingReceived:
if _, ok := requestedTopics[ProposerSlashingTopic]; !ok {
return nil

View File

@@ -104,18 +104,18 @@ func BlockRewardTestSetup(t *testing.T, forkName string) (state.BeaconState, int
sbb.SetSlot(2)
// we have to set the proposer index to the value that will be randomly chosen (fortunately it's deterministic)
sbb.SetProposerIndex(12)
sbb.SetAttestations([]*eth.Attestation{
{
require.NoError(t, sbb.SetAttestations([]interfaces.Attestation{
&eth.Attestation{
AggregationBits: bitfield.Bitlist{0b00000111},
Data: util.HydrateAttestationData(&eth.AttestationData{}),
Signature: make([]byte, fieldparams.BLSSignatureLength),
},
{
&eth.Attestation{
AggregationBits: bitfield.Bitlist{0b00000111},
Data: util.HydrateAttestationData(&eth.AttestationData{}),
Signature: make([]byte, fieldparams.BLSSignatureLength),
},
})
}))
attData1 := util.HydrateAttestationData(&eth.AttestationData{BeaconBlockRoot: bytesutil.PadTo([]byte("root1"), 32)})
attData2 := util.HydrateAttestationData(&eth.AttestationData{BeaconBlockRoot: bytesutil.PadTo([]byte("root2"), 32)})
@@ -125,8 +125,8 @@ func BlockRewardTestSetup(t *testing.T, forkName string) (state.BeaconState, int
require.NoError(t, err)
sigRoot2, err := signing.ComputeSigningRoot(attData2, domain)
require.NoError(t, err)
sbb.SetAttesterSlashings([]*eth.AttesterSlashing{
{
require.NoError(t, sbb.SetAttesterSlashings([]interfaces.AttesterSlashing{
&eth.AttesterSlashing{
Attestation_1: &eth.IndexedAttestation{
AttestingIndices: []uint64{0},
Data: attData1,
@@ -138,7 +138,7 @@ func BlockRewardTestSetup(t *testing.T, forkName string) (state.BeaconState, int
Signature: secretKeys[0].Sign(sigRoot2[:]).Marshal(),
},
},
})
}))
header1 := &eth.BeaconBlockHeader{
Slot: 0,
ProposerIndex: 1,

View File

@@ -33,6 +33,7 @@ go_library(
"//config/params:go_default_library",
"//consensus-types:go_default_library",
"//consensus-types/blocks:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//consensus-types/validator:go_default_library",
"//encoding/bytesutil:go_default_library",
@@ -79,6 +80,7 @@ go_test(
"//beacon-chain/sync/initial-sync/testing:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/bls:go_default_library",
"//encoding/bytesutil:go_default_library",

View File

@@ -25,6 +25,7 @@ import (
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
consensus_types "github.com/prysmaticlabs/prysm/v5/consensus-types"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
validator2 "github.com/prysmaticlabs/prysm/v5/consensus-types/validator"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
@@ -52,7 +53,7 @@ func (s *Server) GetAggregateAttestation(w http.ResponseWriter, r *http.Request)
return
}
var match *ethpbalpha.Attestation
var match interfaces.Attestation
var err error
match, err = matchingAtt(s.AttestationsPool.AggregatedAttestations(), primitives.Slot(slot), attDataRoot)
@@ -79,29 +80,29 @@ func (s *Server) GetAggregateAttestation(w http.ResponseWriter, r *http.Request)
response := &structs.AggregateAttestationResponse{
Data: &structs.Attestation{
AggregationBits: hexutil.Encode(match.AggregationBits),
AggregationBits: hexutil.Encode(match.GetAggregationBits()),
Data: &structs.AttestationData{
Slot: strconv.FormatUint(uint64(match.Data.Slot), 10),
CommitteeIndex: strconv.FormatUint(uint64(match.Data.CommitteeIndex), 10),
BeaconBlockRoot: hexutil.Encode(match.Data.BeaconBlockRoot),
Slot: strconv.FormatUint(uint64(match.GetData().Slot), 10),
CommitteeIndex: strconv.FormatUint(uint64(match.GetData().CommitteeIndex), 10),
BeaconBlockRoot: hexutil.Encode(match.GetData().BeaconBlockRoot),
Source: &structs.Checkpoint{
Epoch: strconv.FormatUint(uint64(match.Data.Source.Epoch), 10),
Root: hexutil.Encode(match.Data.Source.Root),
Epoch: strconv.FormatUint(uint64(match.GetData().Source.Epoch), 10),
Root: hexutil.Encode(match.GetData().Source.Root),
},
Target: &structs.Checkpoint{
Epoch: strconv.FormatUint(uint64(match.Data.Target.Epoch), 10),
Root: hexutil.Encode(match.Data.Target.Root),
Epoch: strconv.FormatUint(uint64(match.GetData().Target.Epoch), 10),
Root: hexutil.Encode(match.GetData().Target.Root),
},
},
Signature: hexutil.Encode(match.Signature),
Signature: hexutil.Encode(match.GetSignature()),
}}
httputil.WriteJson(w, response)
}
func matchingAtt(atts []*ethpbalpha.Attestation, slot primitives.Slot, attDataRoot []byte) (*ethpbalpha.Attestation, error) {
func matchingAtt(atts []interfaces.Attestation, slot primitives.Slot, attDataRoot []byte) (interfaces.Attestation, error) {
for _, att := range atts {
if att.Data.Slot == slot {
root, err := att.Data.HashTreeRoot()
if att.GetData().Slot == slot {
root, err := att.GetData().HashTreeRoot()
if err != nil {
return nil, errors.Wrap(err, "could not get attestation data root")
}

View File

@@ -33,6 +33,7 @@ import (
mockSync "github.com/prysmaticlabs/prysm/v5/beacon-chain/sync/initial-sync/testing"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
@@ -143,9 +144,9 @@ func TestGetAggregateAttestation(t *testing.T) {
}
pool := attestations.NewPool()
err := pool.SaveAggregatedAttestations([]*ethpbalpha.Attestation{attSlot1, attslot21, attslot22})
err := pool.SaveAggregatedAttestations([]interfaces.Attestation{attSlot1, attslot21, attslot22})
assert.NoError(t, err)
err = pool.SaveUnaggregatedAttestations([]*ethpbalpha.Attestation{attslot31, attslot32})
err = pool.SaveUnaggregatedAttestations([]interfaces.Attestation{attslot31, attslot32})
assert.NoError(t, err)
s := &Server{
@@ -314,7 +315,7 @@ func TestGetAggregateAttestation_SameSlotAndRoot_ReturnMostAggregationBits(t *te
Signature: sig,
}
pool := attestations.NewPool()
err := pool.SaveAggregatedAttestations([]*ethpbalpha.Attestation{att1, att2})
err := pool.SaveAggregatedAttestations([]interfaces.Attestation{att1, att2})
assert.NoError(t, err)
s := &Server{
AttestationsPool: pool,

View File

@@ -21,7 +21,7 @@ import (
// sortableAttestations implements the Sort interface to sort attestations
// by slot as the canonical sorting attribute.
type sortableAttestations []*ethpb.Attestation
type sortableAttestations []interfaces.Attestation
// Len is the number of elements in the collection.
func (s sortableAttestations) Len() int { return len(s) }
@@ -31,16 +31,16 @@ func (s sortableAttestations) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
// Less reports whether the element with index i must sort before the element with index j.
func (s sortableAttestations) Less(i, j int) bool {
return s[i].Data.Slot < s[j].Data.Slot
return s[i].GetData().Slot < s[j].GetData().Slot
}
func mapAttestationsByTargetRoot(atts []*ethpb.Attestation) map[[32]byte][]*ethpb.Attestation {
attsMap := make(map[[32]byte][]*ethpb.Attestation, len(atts))
func mapAttestationsByTargetRoot(atts []interfaces.Attestation) map[[32]byte][]interfaces.Attestation {
attsMap := make(map[[32]byte][]interfaces.Attestation, len(atts))
if len(atts) == 0 {
return attsMap
}
for _, att := range atts {
attsMap[bytesutil.ToBytes32(att.Data.Target.Root)] = append(attsMap[bytesutil.ToBytes32(att.Data.Target.Root)], att)
attsMap[bytesutil.ToBytes32(att.GetData().Target.Root)] = append(attsMap[bytesutil.ToBytes32(att.GetData().Target.Root)], att)
}
return attsMap
}
@@ -74,7 +74,7 @@ func (bs *Server) ListAttestations(
default:
return nil, status.Error(codes.InvalidArgument, "Must specify a filter criteria for fetching attestations")
}
atts := make([]*ethpb.Attestation, 0, params.BeaconConfig().MaxAttestations*uint64(len(blocks)))
atts := make([]interfaces.Attestation, 0, params.BeaconConfig().MaxAttestations*uint64(len(blocks)))
for _, blk := range blocks {
atts = append(atts, blk.Block().Body().Attestations()...)
}
@@ -96,8 +96,15 @@ func (bs *Server) ListAttestations(
if err != nil {
return nil, status.Errorf(codes.Internal, "Could not paginate attestations: %v", err)
}
attestations := make([]*ethpb.Attestation, 0, len(atts))
for _, att := range atts {
a, ok := att.(*ethpb.Attestation)
if ok {
attestations = append(attestations, a)
}
}
return &ethpb.ListAttestationsResponse{
Attestations: atts[start:end],
Attestations: attestations[start:end],
TotalSize: int32(numAttestations),
NextPageToken: nextPageToken,
}, nil
@@ -129,7 +136,7 @@ func (bs *Server) ListIndexedAttestations(
return nil, status.Error(codes.InvalidArgument, "Must specify a filter criteria for fetching attestations")
}
attsArray := make([]*ethpb.Attestation, 0, params.BeaconConfig().MaxAttestations*uint64(len(blocks)))
attsArray := make([]interfaces.Attestation, 0, params.BeaconConfig().MaxAttestations*uint64(len(blocks)))
for _, b := range blocks {
attsArray = append(attsArray, b.Block().Body().Attestations()...)
}
@@ -166,7 +173,7 @@ func (bs *Server) ListIndexedAttestations(
}
for i := 0; i < len(atts); i++ {
att := atts[i]
committee, err := helpers.BeaconCommitteeFromState(ctx, attState, att.Data.Slot, att.Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(ctx, attState, att.GetData().Slot, att.GetData().CommitteeIndex)
if err != nil {
return nil, status.Errorf(
codes.Internal,
@@ -178,7 +185,10 @@ func (bs *Server) ListIndexedAttestations(
if err != nil {
return nil, err
}
indexedAtts = append(indexedAtts, idxAtt)
a, ok := idxAtt.(*ethpb.IndexedAttestation)
if ok {
indexedAtts = append(indexedAtts, a)
}
}
}
@@ -226,8 +236,15 @@ func (bs *Server) AttestationPool(
if err != nil {
return nil, status.Errorf(codes.Internal, "Could not paginate attestations: %v", err)
}
attestations := make([]*ethpb.Attestation, 0, len(atts))
for _, att := range atts {
a, ok := att.(*ethpb.Attestation)
if ok {
attestations = append(attestations, a)
}
}
return &ethpb.AttestationPoolResponse{
Attestations: atts[start:end],
Attestations: attestations[start:end],
TotalSize: int32(numAtts),
NextPageToken: nextPageToken,
}, nil

View File

@@ -263,7 +263,7 @@ func TestServer_ListAttestations_Pagination_CustomPageParameters(t *testing.T) {
ctx := context.Background()
count := params.BeaconConfig().SlotsPerEpoch * 4
atts := make([]*ethpb.Attestation, 0, count)
atts := make([]interfaces.Attestation, 0, count)
for i := primitives.Slot(0); i < params.BeaconConfig().SlotsPerEpoch; i++ {
for s := primitives.CommitteeIndex(0); s < 4; s++ {
blockExample := util.NewBeaconBlock()
@@ -278,7 +278,11 @@ func TestServer_ListAttestations_Pagination_CustomPageParameters(t *testing.T) {
}),
}
util.SaveBlock(t, ctx, db, blockExample)
atts = append(atts, blockExample.Block.Body.Attestations...)
as := make([]interfaces.Attestation, len(blockExample.Block.Body.Attestations))
for i, a := range blockExample.Block.Body.Attestations {
as[i] = a
}
atts = append(atts, as...)
}
}
sort.Sort(sortableAttestations(atts))
@@ -303,9 +307,9 @@ func TestServer_ListAttestations_Pagination_CustomPageParameters(t *testing.T) {
},
res: &ethpb.ListAttestationsResponse{
Attestations: []*ethpb.Attestation{
atts[3],
atts[4],
atts[5],
atts[3].(*ethpb.Attestation),
atts[4].(*ethpb.Attestation),
atts[5].(*ethpb.Attestation),
},
NextPageToken: strconv.Itoa(2),
TotalSize: int32(count),
@@ -322,7 +326,7 @@ func TestServer_ListAttestations_Pagination_CustomPageParameters(t *testing.T) {
},
res: &ethpb.ListAttestationsResponse{
Attestations: []*ethpb.Attestation{
atts[10],
atts[10].(*ethpb.Attestation),
},
NextPageToken: strconv.Itoa(11),
TotalSize: int32(count),
@@ -339,14 +343,14 @@ func TestServer_ListAttestations_Pagination_CustomPageParameters(t *testing.T) {
},
res: &ethpb.ListAttestationsResponse{
Attestations: []*ethpb.Attestation{
atts[16],
atts[17],
atts[18],
atts[19],
atts[20],
atts[21],
atts[22],
atts[23],
atts[16].(*ethpb.Attestation),
atts[17].(*ethpb.Attestation),
atts[18].(*ethpb.Attestation),
atts[19].(*ethpb.Attestation),
atts[20].(*ethpb.Attestation),
atts[21].(*ethpb.Attestation),
atts[22].(*ethpb.Attestation),
atts[23].(*ethpb.Attestation),
},
NextPageToken: strconv.Itoa(3),
TotalSize: int32(count)},
@@ -460,7 +464,7 @@ func TestServer_ListAttestations_Pagination_DefaultPageSize(t *testing.T) {
func TestServer_mapAttestationToTargetRoot(t *testing.T) {
count := primitives.Slot(100)
atts := make([]*ethpb.Attestation, count)
atts := make([]interfaces.Attestation, count)
targetRoot1 := bytesutil.ToBytes32([]byte("root1"))
targetRoot2 := bytesutil.ToBytes32([]byte("root2"))
@@ -548,7 +552,9 @@ func TestServer_ListIndexedAttestations_GenesisEpoch(t *testing.T) {
require.NoError(t, err)
idxAtt, err := attestation.ConvertToIndexed(ctx, atts[i], committee)
require.NoError(t, err, "Could not convert attestation to indexed")
indexedAtts[i] = idxAtt
a, ok := idxAtt.(*ethpb.IndexedAttestation)
require.Equal(t, true, ok, "unexpected type of indexed attestation")
indexedAtts[i] = a
}
for i := 0; i < len(atts2); i++ {
att := atts2[i]
@@ -556,7 +562,9 @@ func TestServer_ListIndexedAttestations_GenesisEpoch(t *testing.T) {
require.NoError(t, err)
idxAtt, err := attestation.ConvertToIndexed(ctx, atts2[i], committee)
require.NoError(t, err, "Could not convert attestation to indexed")
indexedAtts[i+len(atts)] = idxAtt
a, ok := idxAtt.(*ethpb.IndexedAttestation)
require.Equal(t, true, ok, "unexpected type of indexed attestation")
indexedAtts[i+len(atts)] = a
}
bs := &Server{
@@ -588,7 +596,7 @@ func TestServer_ListIndexedAttestations_GenesisEpoch(t *testing.T) {
require.NoError(t, err)
assert.Equal(t, len(indexedAtts), len(res.IndexedAttestations), "Incorrect indexted attestations length")
sort.Slice(indexedAtts, func(i, j int) bool {
return indexedAtts[i].Data.Slot < indexedAtts[j].Data.Slot
return indexedAtts[i].GetData().Slot < indexedAtts[j].GetData().Slot
})
sort.Slice(res.IndexedAttestations, func(i, j int) bool {
return res.IndexedAttestations[i].Data.Slot < res.IndexedAttestations[j].Data.Slot
@@ -655,7 +663,9 @@ func TestServer_ListIndexedAttestations_OldEpoch(t *testing.T) {
require.NoError(t, err)
idxAtt, err := attestation.ConvertToIndexed(ctx, atts[i], committee)
require.NoError(t, err, "Could not convert attestation to indexed")
indexedAtts[i] = idxAtt
a, ok := idxAtt.(*ethpb.IndexedAttestation)
require.Equal(t, true, ok, "unexpected type of indexed attestation")
indexedAtts[i] = a
}
bs := &Server{
@@ -697,8 +707,8 @@ func TestServer_AttestationPool_Pagination_OutOfRange(t *testing.T) {
AttestationsPool: attestations.NewPool(),
}
atts := []*ethpb.Attestation{
{
atts := []interfaces.Attestation{
&ethpb.Attestation{
Data: &ethpb.AttestationData{
Slot: 1,
BeaconBlockRoot: bytesutil.PadTo([]byte{1}, 32),
@@ -708,7 +718,7 @@ func TestServer_AttestationPool_Pagination_OutOfRange(t *testing.T) {
AggregationBits: bitfield.Bitlist{0b1101},
Signature: bytesutil.PadTo([]byte{1}, fieldparams.BLSSignatureLength),
},
{
&ethpb.Attestation{
Data: &ethpb.AttestationData{
Slot: 2,
BeaconBlockRoot: bytesutil.PadTo([]byte{2}, 32),
@@ -718,7 +728,7 @@ func TestServer_AttestationPool_Pagination_OutOfRange(t *testing.T) {
AggregationBits: bitfield.Bitlist{0b1101},
Signature: bytesutil.PadTo([]byte{2}, fieldparams.BLSSignatureLength),
},
{
&ethpb.Attestation{
Data: &ethpb.AttestationData{
Slot: 3,
BeaconBlockRoot: bytesutil.PadTo([]byte{3}, 32),
@@ -746,7 +756,7 @@ func TestServer_AttestationPool_Pagination_DefaultPageSize(t *testing.T) {
AttestationsPool: attestations.NewPool(),
}
atts := make([]*ethpb.Attestation, params.BeaconConfig().DefaultPageSize+1)
atts := make([]interfaces.Attestation, params.BeaconConfig().DefaultPageSize+1)
for i := 0; i < len(atts); i++ {
att := util.NewAttestation()
att.Data.Slot = primitives.Slot(i)
@@ -768,7 +778,7 @@ func TestServer_AttestationPool_Pagination_CustomPageSize(t *testing.T) {
}
numAtts := 100
atts := make([]*ethpb.Attestation, numAtts)
atts := make([]interfaces.Attestation, numAtts)
for i := 0; i < len(atts); i++ {
att := util.NewAttestation()
att.Data.Slot = primitives.Slot(i)

View File

@@ -66,7 +66,7 @@ func (ds *Server) GetInclusionSlot(ctx context.Context, req *pbrpc.InclusionSlot
targetStates := make(map[[32]byte]state.ReadOnlyBeaconState)
for _, blk := range blks {
for _, a := range blk.Block().Body().Attestations() {
tr := bytesutil.ToBytes32(a.Data.Target.Root)
tr := bytesutil.ToBytes32(a.GetData().Target.Root)
s, ok := targetStates[tr]
if !ok {
s, err = ds.StateGen.StateByRoot(ctx, tr)
@@ -75,16 +75,16 @@ func (ds *Server) GetInclusionSlot(ctx context.Context, req *pbrpc.InclusionSlot
}
targetStates[tr] = s
}
c, err := helpers.BeaconCommitteeFromState(ctx, s, a.Data.Slot, a.Data.CommitteeIndex)
c, err := helpers.BeaconCommitteeFromState(ctx, s, a.GetData().Slot, a.GetData().CommitteeIndex)
if err != nil {
return nil, status.Errorf(codes.Internal, "Could not get committee: %v", err)
}
indices, err := attestation.AttestingIndices(a.AggregationBits, c)
indices, err := attestation.AttestingIndices(a.GetAggregationBits(), c)
if err != nil {
return nil, err
}
for _, i := range indices {
if req.Id == i && req.Slot == a.Data.Slot {
if req.Id == i && req.Slot == a.GetData().Slot {
inclusionSlot = blk.Block().Slot()
break
}

View File

@@ -2,6 +2,7 @@ package validator
import (
"context"
"fmt"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/rpc/core"
@@ -85,22 +86,26 @@ func (vs *Server) SubmitAggregateSelectionProof(ctx context.Context, req *ethpb.
// The aggregator should prefer an attestation that they have signed. We check this by
// looking at the attestation's committee index against the validator's committee index
// and check the aggregate bits to ensure the validator's index is set.
if aggregatedAtt.Data.CommitteeIndex == req.CommitteeIndex &&
aggregatedAtt.AggregationBits.BitAt(indexInCommittee) &&
(!best.AggregationBits.BitAt(indexInCommittee) ||
aggregatedAtt.AggregationBits.Count() > best.AggregationBits.Count()) {
if aggregatedAtt.GetData().CommitteeIndex == req.CommitteeIndex &&
aggregatedAtt.GetAggregationBits().BitAt(indexInCommittee) &&
(!best.GetAggregationBits().BitAt(indexInCommittee) ||
aggregatedAtt.GetAggregationBits().Count() > best.GetAggregationBits().Count()) {
best = aggregatedAtt
}
// If the "best" still doesn't contain the validator's index, check the aggregation bits to
// choose the attestation with the most bits set.
if !best.AggregationBits.BitAt(indexInCommittee) &&
aggregatedAtt.AggregationBits.Count() > best.AggregationBits.Count() {
if !best.GetAggregationBits().BitAt(indexInCommittee) &&
aggregatedAtt.GetAggregationBits().Count() > best.GetAggregationBits().Count() {
best = aggregatedAtt
}
}
att, ok := best.(*ethpb.Attestation)
if !ok {
return nil, fmt.Errorf("best attestation has wrong type (expected %T, got %T)", &ethpb.Attestation{}, best)
}
a := &ethpb.AggregateAttestationAndProof{
Aggregate: best,
Aggregate: att,
SelectionProof: req.SlotSignature,
AggregatorIndex: validatorIndex,
}

View File

@@ -18,6 +18,7 @@ import (
mockSync "github.com/prysmaticlabs/prysm/v5/beacon-chain/sync/initial-sync/testing"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -336,7 +337,7 @@ func TestSubmitAggregateAndProof_PreferOwnAttestation(t *testing.T) {
pubKey := v.PublicKey
req := &ethpb.AggregateSelectionRequest{CommitteeIndex: 1, SlotSignature: sig.Marshal(), PublicKey: pubKey}
err = aggregatorServer.AttPool.SaveAggregatedAttestations([]*ethpb.Attestation{
err = aggregatorServer.AttPool.SaveAggregatedAttestations([]interfaces.Attestation{
att0,
att1,
att2,
@@ -387,7 +388,7 @@ func TestSubmitAggregateAndProof_SelectsMostBitsWhenOwnAttestationNotPresent(t *
pubKey := v.PublicKey
req := &ethpb.AggregateSelectionRequest{CommitteeIndex: 1, SlotSignature: sig.Marshal(), PublicKey: pubKey}
err = aggregatorServer.AttPool.SaveAggregatedAttestations([]*ethpb.Attestation{
err = aggregatorServer.AttPool.SaveAggregatedAttestations([]interfaces.Attestation{
att0,
att1,
})

View File

@@ -202,17 +202,23 @@ func (vs *Server) BuildBlockParallel(ctx context.Context, sBlk interfaces.Signed
deposits, atts, err := vs.packDepositsAndAttestations(ctx, head, eth1Data) // TODO: split attestations and deposits
if err != nil {
sBlk.SetDeposits([]*ethpb.Deposit{})
sBlk.SetAttestations([]*ethpb.Attestation{})
if err := sBlk.SetAttestations([]interfaces.Attestation{}); err != nil {
log.WithError(err).Error("Could not set attestations on block")
}
log.WithError(err).Error("Could not pack deposits and attestations")
} else {
sBlk.SetDeposits(deposits)
sBlk.SetAttestations(atts)
if err := sBlk.SetAttestations(atts); err != nil {
log.WithError(err).Error("Could not set attestations on block")
}
}
// Set slashings.
validProposerSlashings, validAttSlashings := vs.getSlashings(ctx, head)
sBlk.SetProposerSlashings(validProposerSlashings)
sBlk.SetAttesterSlashings(validAttSlashings)
if err := sBlk.SetAttesterSlashings(validAttSlashings); err != nil {
log.WithError(err).Error("Could not set attester slashings on block")
}
// Set exits.
sBlk.SetVoluntaryExits(vs.getExits(head, sBlk.Block().Slot()))

View File

@@ -10,16 +10,16 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/helpers"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation"
attaggregation "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation/attestations"
"go.opencensus.io/trace"
)
type proposerAtts []*ethpb.Attestation
type proposerAtts []interfaces.Attestation
func (vs *Server) packAttestations(ctx context.Context, latestState state.BeaconState) ([]*ethpb.Attestation, error) {
func (vs *Server) packAttestations(ctx context.Context, latestState state.BeaconState) ([]interfaces.Attestation, error) {
ctx, span := trace.StartSpan(ctx, "ProposerServer.packAttestations")
defer span.End()
@@ -46,16 +46,16 @@ func (vs *Server) packAttestations(ctx context.Context, latestState state.Beacon
return nil, err
}
attsByDataRoot := make(map[[32]byte][]*ethpb.Attestation, len(atts))
attsByDataRoot := make(map[[32]byte][]interfaces.Attestation, len(atts))
for _, att := range atts {
attDataRoot, err := att.Data.HashTreeRoot()
attDataRoot, err := att.GetData().HashTreeRoot()
if err != nil {
return nil, err
}
attsByDataRoot[attDataRoot] = append(attsByDataRoot[attDataRoot], att)
}
attsForInclusion := proposerAtts(make([]*ethpb.Attestation, 0))
attsForInclusion := proposerAtts(make([]interfaces.Attestation, 0))
for _, as := range attsByDataRoot {
as, err := attaggregation.Aggregate(as)
if err != nil {
@@ -79,8 +79,8 @@ func (vs *Server) packAttestations(ctx context.Context, latestState state.Beacon
// The first group passes the all the required checks for attestation to be considered for proposing.
// And attestations from the second group should be deleted.
func (a proposerAtts) filter(ctx context.Context, st state.BeaconState) (proposerAtts, proposerAtts) {
validAtts := make([]*ethpb.Attestation, 0, len(a))
invalidAtts := make([]*ethpb.Attestation, 0, len(a))
validAtts := make([]interfaces.Attestation, 0, len(a))
invalidAtts := make([]interfaces.Attestation, 0, len(a))
for _, att := range a {
if err := blocks.VerifyAttestationNoVerifySignature(ctx, st, att); err == nil {
@@ -107,10 +107,10 @@ func (a proposerAtts) sortByProfitabilityUsingMaxCover() (proposerAtts, error) {
var slots []primitives.Slot
attsBySlot := map[primitives.Slot]proposerAtts{}
for _, att := range a {
if _, ok := attsBySlot[att.Data.Slot]; !ok {
slots = append(slots, att.Data.Slot)
if _, ok := attsBySlot[att.GetData().Slot]; !ok {
slots = append(slots, att.GetData().Slot)
}
attsBySlot[att.Data.Slot] = append(attsBySlot[att.Data.Slot], att)
attsBySlot[att.GetData().Slot] = append(attsBySlot[att.GetData().Slot], att)
}
selectAtts := func(atts proposerAtts) (proposerAtts, error) {
@@ -120,7 +120,7 @@ func (a proposerAtts) sortByProfitabilityUsingMaxCover() (proposerAtts, error) {
candidates := make([]*bitfield.Bitlist64, len(atts))
for i := 0; i < len(atts); i++ {
var err error
candidates[i], err = atts[i].AggregationBits.ToBitlist64()
candidates[i], err = atts[i].GetAggregationBits().ToBitlist64()
if err != nil {
return nil, err
}
@@ -139,10 +139,10 @@ func (a proposerAtts) sortByProfitabilityUsingMaxCover() (proposerAtts, error) {
leftoverAtts[i] = atts[key]
}
sort.Slice(selectedAtts, func(i, j int) bool {
return selectedAtts[i].AggregationBits.Count() > selectedAtts[j].AggregationBits.Count()
return selectedAtts[i].GetAggregationBits().Count() > selectedAtts[j].GetAggregationBits().Count()
})
sort.Slice(leftoverAtts, func(i, j int) bool {
return leftoverAtts[i].AggregationBits.Count() > leftoverAtts[j].AggregationBits.Count()
return leftoverAtts[i].GetAggregationBits().Count() > leftoverAtts[j].GetAggregationBits().Count()
})
return append(selectedAtts, leftoverAtts...), nil
}
@@ -182,22 +182,22 @@ func (a proposerAtts) dedup() (proposerAtts, error) {
if len(a) < 2 {
return a, nil
}
attsByDataRoot := make(map[[32]byte][]*ethpb.Attestation, len(a))
attsByDataRoot := make(map[[32]byte][]interfaces.Attestation, len(a))
for _, att := range a {
attDataRoot, err := att.Data.HashTreeRoot()
attDataRoot, err := att.GetData().HashTreeRoot()
if err != nil {
continue
}
attsByDataRoot[attDataRoot] = append(attsByDataRoot[attDataRoot], att)
}
uniqAtts := make([]*ethpb.Attestation, 0, len(a))
uniqAtts := make([]interfaces.Attestation, 0, len(a))
for _, atts := range attsByDataRoot {
for i := 0; i < len(atts); i++ {
a := atts[i]
for j := i + 1; j < len(atts); j++ {
b := atts[j]
if c, err := a.AggregationBits.Contains(b.AggregationBits); err != nil {
if c, err := a.GetAggregationBits().Contains(b.GetAggregationBits()); err != nil {
return nil, err
} else if c {
// a contains b, b is redundant.
@@ -205,7 +205,7 @@ func (a proposerAtts) dedup() (proposerAtts, error) {
atts[len(atts)-1] = nil
atts = atts[:len(atts)-1]
j--
} else if c, err := b.AggregationBits.Contains(a.AggregationBits); err != nil {
} else if c, err := b.GetAggregationBits().Contains(a.GetAggregationBits()); err != nil {
return nil, err
} else if c {
// b contains a, a is redundant.
@@ -224,7 +224,7 @@ func (a proposerAtts) dedup() (proposerAtts, error) {
}
// This filters the input attestations to return a list of valid attestations to be packaged inside a beacon block.
func (vs *Server) validateAndDeleteAttsInPool(ctx context.Context, st state.BeaconState, atts []*ethpb.Attestation) ([]*ethpb.Attestation, error) {
func (vs *Server) validateAndDeleteAttsInPool(ctx context.Context, st state.BeaconState, atts []interfaces.Attestation) ([]interfaces.Attestation, error) {
ctx, span := trace.StartSpan(ctx, "ProposerServer.validateAndDeleteAttsInPool")
defer span.End()
@@ -237,7 +237,7 @@ func (vs *Server) validateAndDeleteAttsInPool(ctx context.Context, st state.Beac
// The input attestations are processed and seen by the node, this deletes them from pool
// so proposers don't include them in a block for the future.
func (vs *Server) deleteAttsInPool(ctx context.Context, atts []*ethpb.Attestation) error {
func (vs *Server) deleteAttsInPool(ctx context.Context, atts []interfaces.Attestation) error {
ctx, span := trace.StartSpan(ctx, "ProposerServer.deleteAttsInPool")
defer span.End()

View File

@@ -6,6 +6,7 @@ import (
"testing"
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
@@ -14,7 +15,7 @@ import (
)
func TestProposer_ProposerAtts_sortByProfitability(t *testing.T) {
atts := proposerAtts([]*ethpb.Attestation{
atts := proposerAtts([]interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 4}, AggregationBits: bitfield.Bitlist{0b11100000}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b11000000}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 2}, AggregationBits: bitfield.Bitlist{0b11100000}}),
@@ -22,7 +23,7 @@ func TestProposer_ProposerAtts_sortByProfitability(t *testing.T) {
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b11100000}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b11000000}}),
})
want := proposerAtts([]*ethpb.Attestation{
want := proposerAtts([]interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 4}, AggregationBits: bitfield.Bitlist{0b11110000}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 4}, AggregationBits: bitfield.Bitlist{0b11100000}}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 3}, AggregationBits: bitfield.Bitlist{0b11000000}}),
@@ -411,13 +412,13 @@ func TestProposer_ProposerAtts_dedup(t *testing.T) {
t.Error(err)
}
sort.Slice(atts, func(i, j int) bool {
if atts[i].AggregationBits.Count() == atts[j].AggregationBits.Count() {
if atts[i].Data.Slot == atts[j].Data.Slot {
return bytes.Compare(atts[i].AggregationBits, atts[j].AggregationBits) <= 0
if atts[i].GetAggregationBits().Count() == atts[j].GetAggregationBits().Count() {
if atts[i].GetData().Slot == atts[j].GetData().Slot {
return bytes.Compare(atts[i].GetAggregationBits(), atts[j].GetAggregationBits()) <= 0
}
return atts[i].Data.Slot > atts[j].Data.Slot
return atts[i].GetData().Slot > atts[j].GetData().Slot
}
return atts[i].AggregationBits.Count() > atts[j].AggregationBits.Count()
return atts[i].GetAggregationBits().Count() > atts[j].GetAggregationBits().Count()
})
assert.DeepEqual(t, tt.want, atts)
})

View File

@@ -9,6 +9,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/cache"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/container/trie"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/sirupsen/logrus"
@@ -18,10 +19,10 @@ import (
"google.golang.org/grpc/status"
)
func (vs *Server) packDepositsAndAttestations(ctx context.Context, head state.BeaconState, eth1Data *ethpb.Eth1Data) ([]*ethpb.Deposit, []*ethpb.Attestation, error) {
func (vs *Server) packDepositsAndAttestations(ctx context.Context, head state.BeaconState, eth1Data *ethpb.Eth1Data) ([]*ethpb.Deposit, []interfaces.Attestation, error) {
eg, egctx := errgroup.WithContext(ctx)
var deposits []*ethpb.Deposit
var atts []*ethpb.Attestation
var atts []interfaces.Attestation
eg.Go(func() error {
// Pack ETH1 deposits which have not been included in the beacon chain.

View File

@@ -6,10 +6,11 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/blocks"
v "github.com/prysmaticlabs/prysm/v5/beacon-chain/core/validators"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
func (vs *Server) getSlashings(ctx context.Context, head state.BeaconState) ([]*ethpb.ProposerSlashing, []*ethpb.AttesterSlashing) {
func (vs *Server) getSlashings(ctx context.Context, head state.BeaconState) ([]*ethpb.ProposerSlashing, []interfaces.AttesterSlashing) {
proposerSlashings := vs.SlashingsPool.PendingProposerSlashings(ctx, head, false /*noLimit*/)
validProposerSlashings := make([]*ethpb.ProposerSlashing, 0, len(proposerSlashings))
for _, slashing := range proposerSlashings {
@@ -21,7 +22,7 @@ func (vs *Server) getSlashings(ctx context.Context, head state.BeaconState) ([]*
validProposerSlashings = append(validProposerSlashings, slashing)
}
attSlashings := vs.SlashingsPool.PendingAttesterSlashings(ctx, head, false /*noLimit*/)
validAttSlashings := make([]*ethpb.AttesterSlashing, 0, len(attSlashings))
validAttSlashings := make([]interfaces.AttesterSlashing, 0, len(attSlashings))
for _, slashing := range attSlashings {
_, err := blocks.ProcessAttesterSlashing(ctx, head, slashing, v.SlashValidator)
if err != nil {

View File

@@ -6,6 +6,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/operations/slashings"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -28,7 +29,7 @@ func TestServer_getSlashings(t *testing.T) {
require.NoError(t, err)
}
attSlashings := make([]*ethpb.AttesterSlashing, params.BeaconConfig().MaxAttesterSlashings)
attSlashings := make([]interfaces.AttesterSlashing, params.BeaconConfig().MaxAttesterSlashings)
for i := uint64(0); i < params.BeaconConfig().MaxAttesterSlashings; i++ {
attesterSlashing, err := util.GenerateAttesterSlashingForValidator(
beaconState,

View File

@@ -38,6 +38,7 @@ import (
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/blocks"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/container/trie"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
@@ -2396,22 +2397,22 @@ func TestProposer_FilterAttestation(t *testing.T) {
tests := []struct {
name string
wantedErr string
inputAtts func() []*ethpb.Attestation
expectedAtts func(inputAtts []*ethpb.Attestation) []*ethpb.Attestation
inputAtts func() []interfaces.Attestation
expectedAtts func(inputAtts []interfaces.Attestation) []interfaces.Attestation
}{
{
name: "nil attestations",
inputAtts: func() []*ethpb.Attestation {
inputAtts: func() []interfaces.Attestation {
return nil
},
expectedAtts: func(inputAtts []*ethpb.Attestation) []*ethpb.Attestation {
return []*ethpb.Attestation{}
expectedAtts: func(inputAtts []interfaces.Attestation) []interfaces.Attestation {
return []interfaces.Attestation{}
},
},
{
name: "invalid attestations",
inputAtts: func() []*ethpb.Attestation {
atts := make([]*ethpb.Attestation, 10)
inputAtts: func() []interfaces.Attestation {
atts := make([]interfaces.Attestation, 10)
for i := 0; i < len(atts); i++ {
atts[i] = util.HydrateAttestation(&ethpb.Attestation{
Data: &ethpb.AttestationData{
@@ -2421,14 +2422,14 @@ func TestProposer_FilterAttestation(t *testing.T) {
}
return atts
},
expectedAtts: func(inputAtts []*ethpb.Attestation) []*ethpb.Attestation {
return []*ethpb.Attestation{}
expectedAtts: func(inputAtts []interfaces.Attestation) []interfaces.Attestation {
return []interfaces.Attestation{}
},
},
{
name: "filter aggregates ok",
inputAtts: func() []*ethpb.Attestation {
atts := make([]*ethpb.Attestation, 10)
inputAtts: func() []interfaces.Attestation {
atts := make([]interfaces.Attestation, 10)
for i := 0; i < len(atts); i++ {
atts[i] = util.HydrateAttestation(&ethpb.Attestation{
Data: &ethpb.AttestationData{
@@ -2437,29 +2438,29 @@ func TestProposer_FilterAttestation(t *testing.T) {
},
AggregationBits: bitfield.Bitlist{0b00010010},
})
committee, err := helpers.BeaconCommitteeFromState(context.Background(), st, atts[i].Data.Slot, atts[i].Data.CommitteeIndex)
committee, err := helpers.BeaconCommitteeFromState(context.Background(), st, atts[i].GetData().Slot, atts[i].GetData().CommitteeIndex)
assert.NoError(t, err)
attestingIndices, err := attestation.AttestingIndices(atts[i].AggregationBits, committee)
attestingIndices, err := attestation.AttestingIndices(atts[i].GetAggregationBits(), committee)
require.NoError(t, err)
assert.NoError(t, err)
domain, err := signing.Domain(st.Fork(), 0, params.BeaconConfig().DomainBeaconAttester, params.BeaconConfig().ZeroHash[:])
require.NoError(t, err)
sigs := make([]bls.Signature, len(attestingIndices))
var zeroSig [96]byte
atts[i].Signature = zeroSig[:]
atts[i].(*ethpb.Attestation).Signature = zeroSig[:]
for i, indice := range attestingIndices {
hashTreeRoot, err := signing.ComputeSigningRoot(atts[i].Data, domain)
hashTreeRoot, err := signing.ComputeSigningRoot(atts[i].GetData(), domain)
require.NoError(t, err)
sig := privKeys[indice].Sign(hashTreeRoot[:])
sigs[i] = sig
}
atts[i].Signature = bls.AggregateSignatures(sigs).Marshal()
atts[i].(*ethpb.Attestation).Signature = bls.AggregateSignatures(sigs).Marshal()
}
return atts
},
expectedAtts: func(inputAtts []*ethpb.Attestation) []*ethpb.Attestation {
return []*ethpb.Attestation{inputAtts[0], inputAtts[1]}
expectedAtts: func(inputAtts []interfaces.Attestation) []interfaces.Attestation {
return []interfaces.Attestation{inputAtts[0], inputAtts[1]}
},
},
}
@@ -2589,10 +2590,10 @@ func TestProposer_DeleteAttsInPool_Aggregated(t *testing.T) {
priv, err := bls.RandKey()
require.NoError(t, err)
sig := priv.Sign([]byte("foo")).Marshal()
aggregatedAtts := []*ethpb.Attestation{
aggregatedAtts := []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b10101}, Signature: sig}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b11010}, Signature: sig})}
unaggregatedAtts := []*ethpb.Attestation{
unaggregatedAtts := []interfaces.Attestation{
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b10010}, Signature: sig}),
util.HydrateAttestation(&ethpb.Attestation{Data: &ethpb.AttestationData{Slot: 1}, AggregationBits: bitfield.Bitlist{0b10100}, Signature: sig})}

View File

@@ -6,6 +6,7 @@ import (
"github.com/prysmaticlabs/go-bitfield"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
aggtesting "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1/attestation/aggregation/testing"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -44,10 +45,10 @@ func BenchmarkProposerAtts_sortByProfitability(b *testing.B) {
},
}
runner := func(atts []*ethpb.Attestation) {
runner := func(atts []interfaces.Attestation) {
attsCopy := make(proposerAtts, len(atts))
for i, att := range atts {
attsCopy[i] = ethpb.CopyAttestation(att)
attsCopy[i] = ethpb.CopyAttestation(att.(*ethpb.Attestation))
}
_, err := attsCopy.sortByProfitability()
require.NoError(b, err, "Could not sort attestations by profitability")

View File

@@ -36,6 +36,7 @@ go_library(
"//beacon-chain/sync:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//container/slice:go_default_library",
"//encoding/bytesutil:go_default_library",
@@ -78,6 +79,7 @@ go_test(
"//beacon-chain/sync/initial-sync/testing:go_default_library",
"//config/fieldparams:go_default_library",
"//config/params:go_default_library",
"//consensus-types/interfaces:go_default_library",
"//consensus-types/primitives:go_default_library",
"//crypto/bls:go_default_library",
"//crypto/bls/common:go_default_library",

View File

@@ -9,6 +9,7 @@ import (
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/db"
slashertypes "github.com/prysmaticlabs/prysm/v5/beacon-chain/slasher/types"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/sirupsen/logrus"
@@ -26,7 +27,7 @@ type Chunker interface {
slasherDB db.SlasherDatabase,
validatorIdx primitives.ValidatorIndex,
attestation *slashertypes.IndexedAttestationWrapper,
) (*ethpb.AttesterSlashing, error)
) (interfaces.AttesterSlashing, error)
Update(
chunkIndex uint64,
currentEpoch primitives.Epoch,
@@ -185,9 +186,9 @@ func (m *MinSpanChunksSlice) CheckSlashable(
slasherDB db.SlasherDatabase,
validatorIdx primitives.ValidatorIndex,
incomingAttWrapper *slashertypes.IndexedAttestationWrapper,
) (*ethpb.AttesterSlashing, error) {
sourceEpoch := incomingAttWrapper.IndexedAttestation.Data.Source.Epoch
targetEpoch := incomingAttWrapper.IndexedAttestation.Data.Target.Epoch
) (interfaces.AttesterSlashing, error) {
sourceEpoch := incomingAttWrapper.IndexedAttestation.GetData().Source.Epoch
targetEpoch := incomingAttWrapper.IndexedAttestation.GetData().Target.Epoch
minTarget, err := chunkDataAtEpoch(m.params, m.data, validatorIdx, sourceEpoch)
if err != nil {
@@ -221,7 +222,7 @@ func (m *MinSpanChunksSlice) CheckSlashable(
return nil, nil
}
if existingAttWrapper.IndexedAttestation.Data.Source.Epoch <= sourceEpoch {
if existingAttWrapper.IndexedAttestation.GetData().Source.Epoch <= sourceEpoch {
// This case should normally not happen, since if we have targetEpoch > minTarget,
// then there is at least one attestation we surround.
// However, it can happens if we have multiple attestation with the same target
@@ -232,16 +233,33 @@ func (m *MinSpanChunksSlice) CheckSlashable(
surroundingVotesTotal.Inc()
existing, ok := existingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"existing attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
existingAttWrapper.IndexedAttestation,
)
}
incoming, ok := incomingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"incoming attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
incomingAttWrapper.IndexedAttestation,
)
}
slashing := &ethpb.AttesterSlashing{
Attestation_1: existingAttWrapper.IndexedAttestation,
Attestation_2: incomingAttWrapper.IndexedAttestation,
Attestation_1: existing,
Attestation_2: incoming,
}
// Ensure the attestation with the lower data root is the first attestation.
if bytes.Compare(existingAttWrapper.DataRoot[:], incomingAttWrapper.DataRoot[:]) > 0 {
slashing = &ethpb.AttesterSlashing{
Attestation_1: incomingAttWrapper.IndexedAttestation,
Attestation_2: existingAttWrapper.IndexedAttestation,
Attestation_1: incoming,
Attestation_2: existing,
}
}
@@ -264,9 +282,9 @@ func (m *MaxSpanChunksSlice) CheckSlashable(
slasherDB db.SlasherDatabase,
validatorIdx primitives.ValidatorIndex,
incomingAttWrapper *slashertypes.IndexedAttestationWrapper,
) (*ethpb.AttesterSlashing, error) {
sourceEpoch := incomingAttWrapper.IndexedAttestation.Data.Source.Epoch
targetEpoch := incomingAttWrapper.IndexedAttestation.Data.Target.Epoch
) (interfaces.AttesterSlashing, error) {
sourceEpoch := incomingAttWrapper.IndexedAttestation.GetData().Source.Epoch
targetEpoch := incomingAttWrapper.IndexedAttestation.GetData().Target.Epoch
maxTarget, err := chunkDataAtEpoch(m.params, m.data, validatorIdx, sourceEpoch)
if err != nil {
@@ -300,7 +318,7 @@ func (m *MaxSpanChunksSlice) CheckSlashable(
return nil, nil
}
if existingAttWrapper.IndexedAttestation.Data.Source.Epoch >= sourceEpoch {
if existingAttWrapper.IndexedAttestation.GetData().Source.Epoch >= sourceEpoch {
// This case should normally not happen, since if we have targetEpoch < maxTarget,
// then there is at least one attestation that surrounds us.
// However, it can happens if we have multiple attestation with the same target
@@ -311,16 +329,33 @@ func (m *MaxSpanChunksSlice) CheckSlashable(
surroundedVotesTotal.Inc()
existing, ok := existingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"existing attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
existingAttWrapper.IndexedAttestation,
)
}
incoming, ok := incomingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"incoming attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
incomingAttWrapper.IndexedAttestation,
)
}
slashing := &ethpb.AttesterSlashing{
Attestation_1: existingAttWrapper.IndexedAttestation,
Attestation_2: incomingAttWrapper.IndexedAttestation,
Attestation_1: existing,
Attestation_2: incoming,
}
// Ensure the attestation with the lower data root is the first attestation.
if bytes.Compare(existingAttWrapper.DataRoot[:], incomingAttWrapper.DataRoot[:]) > 0 {
slashing = &ethpb.AttesterSlashing{
Attestation_1: incomingAttWrapper.IndexedAttestation,
Attestation_2: existingAttWrapper.IndexedAttestation,
Attestation_1: incoming,
Attestation_2: existing,
}
}

View File

@@ -115,11 +115,11 @@ func TestMinSpanChunksSlice_CheckSlashable(t *testing.T) {
// based on our min chunk for either validator.
slashing, err := chunk.CheckSlashable(ctx, slasherDB, validatorIdx, att)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
slashing, err = chunk.CheckSlashable(ctx, slasherDB, validatorIdx.Sub(1), att)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
// Next up we initialize an empty chunks slice and mark an attestation
// with (source 1, target 2) as attested.
@@ -141,11 +141,11 @@ func TestMinSpanChunksSlice_CheckSlashable(t *testing.T) {
slashing, err = chunk.CheckSlashable(ctx, slasherDB, validatorIdx, surroundingVote)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
// Next up, we save the old attestation record, then check if the
// surrounding vote is indeed slashable.
attData := att.IndexedAttestation.Data
attData := att.IndexedAttestation.GetData()
attRecord := createAttestationWrapperEmptySig(t, attData.Source.Epoch, attData.Target.Epoch, []uint64{uint64(validatorIdx)}, []byte{1})
err = slasherDB.SaveAttestationRecordsForValidators(
ctx,
@@ -193,11 +193,11 @@ func TestMaxSpanChunksSlice_CheckSlashable(t *testing.T) {
// based on our max chunk for either validator.
slashing, err := chunk.CheckSlashable(ctx, slasherDB, validatorIdx, att)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
slashing, err = chunk.CheckSlashable(ctx, slasherDB, validatorIdx.Sub(1), att)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
// Next up we initialize an empty chunks slice and mark an attestation
// with (source 0, target 3) as attested.
@@ -219,11 +219,11 @@ func TestMaxSpanChunksSlice_CheckSlashable(t *testing.T) {
slashing, err = chunk.CheckSlashable(ctx, slasherDB, validatorIdx, surroundedVote)
require.NoError(t, err)
require.Equal(t, (*ethpb.AttesterSlashing)(nil), slashing)
require.Equal(t, nil, slashing)
// Next up, we save the old attestation record, then check if the
// surroundedVote vote is indeed slashable.
attData := att.IndexedAttestation.Data
attData := att.IndexedAttestation.GetData()
signingRoot := [32]byte{1}
attRecord := createAttestationWrapperEmptySig(
t, attData.Source.Epoch, attData.Target.Epoch, []uint64{uint64(validatorIdx)}, signingRoot[:],

View File

@@ -8,6 +8,7 @@ import (
"github.com/pkg/errors"
slashertypes "github.com/prysmaticlabs/prysm/v5/beacon-chain/slasher/types"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"go.opencensus.io/trace"
@@ -18,8 +19,8 @@ import (
// found attester slashings to the caller.
func (s *Service) checkSlashableAttestations(
ctx context.Context, currentEpoch primitives.Epoch, atts []*slashertypes.IndexedAttestationWrapper,
) (map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing, error) {
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{}
) (map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing, error) {
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{}
// Double votes
doubleVoteSlashings, err := s.checkDoubleVotes(ctx, atts)
@@ -56,13 +57,13 @@ func (s *Service) checkSurroundVotes(
ctx context.Context,
attWrappers []*slashertypes.IndexedAttestationWrapper,
currentEpoch primitives.Epoch,
) (map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing, error) {
) (map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing, error) {
// With 256 validators and 16 epochs per chunk, there is 4096 `uint16` elements per chunk.
// 4096 `uint16` elements = 8192 bytes = 8KB
// 25_600 chunks * 8KB = 200MB
const maxChunkBeforeFlush = 25_600
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{}
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{}
// Group attestation wrappers by validator chunk index.
attWrappersByValidatorChunkIndex := s.groupByValidatorChunkIndex(attWrappers)
@@ -153,7 +154,7 @@ func (s *Service) checkSurroundVotes(
// Check for double votes in our database given a list of incoming attestations.
func (s *Service) checkDoubleVotes(
ctx context.Context, incomingAttWrappers []*slashertypes.IndexedAttestationWrapper,
) (map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing, error) {
) (map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing, error) {
ctx, span := trace.StartSpan(ctx, "Slasher.checkDoubleVotesOnDisk")
defer span.End()
@@ -162,15 +163,15 @@ func (s *Service) checkDoubleVotes(
epoch primitives.Epoch
}
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{}
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{}
// Check each incoming attestation for double votes against other incoming attestations.
existingAttWrappers := make(map[attestationInfo]*slashertypes.IndexedAttestationWrapper)
for _, incomingAttWrapper := range incomingAttWrappers {
targetEpoch := incomingAttWrapper.IndexedAttestation.Data.Target.Epoch
targetEpoch := incomingAttWrapper.IndexedAttestation.GetData().Target.Epoch
for _, validatorIndex := range incomingAttWrapper.IndexedAttestation.AttestingIndices {
for _, validatorIndex := range incomingAttWrapper.IndexedAttestation.GetAttestingIndices() {
info := attestationInfo{
validatorIndex: validatorIndex,
epoch: targetEpoch,
@@ -193,17 +194,33 @@ func (s *Service) checkDoubleVotes(
// This is a double vote.
doubleVotesTotal.Inc()
existing, ok := existingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"existing attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
existingAttWrapper.IndexedAttestation,
)
}
incoming, ok := incomingAttWrapper.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"incoming attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
incomingAttWrapper.IndexedAttestation,
)
}
slashing := &ethpb.AttesterSlashing{
Attestation_1: existingAttWrapper.IndexedAttestation,
Attestation_2: incomingAttWrapper.IndexedAttestation,
Attestation_1: existing,
Attestation_2: incoming,
}
// Ensure the attestation with the lower data root is the first attestation.
// It will be useful for comparing with other double votes.
if bytes.Compare(existingAttWrapper.DataRoot[:], incomingAttWrapper.DataRoot[:]) > 0 {
slashing = &ethpb.AttesterSlashing{
Attestation_1: incomingAttWrapper.IndexedAttestation,
Attestation_2: existingAttWrapper.IndexedAttestation,
Attestation_1: incoming,
Attestation_2: existing,
}
}
@@ -229,16 +246,33 @@ func (s *Service) checkDoubleVotes(
wrapper_1 := doubleVote.Wrapper_1
wrapper_2 := doubleVote.Wrapper_2
att_1, ok := wrapper_1.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"first attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
wrapper_1.IndexedAttestation,
)
}
att_2, ok := wrapper_2.IndexedAttestation.(*ethpb.IndexedAttestation)
if !ok {
return nil, fmt.Errorf(
"second attestation has wrong type (expected %T, got %T)",
&ethpb.IndexedAttestation{},
wrapper_2.IndexedAttestation,
)
}
slashing := &ethpb.AttesterSlashing{
Attestation_1: wrapper_1.IndexedAttestation,
Attestation_2: wrapper_2.IndexedAttestation,
Attestation_1: att_1,
Attestation_2: att_2,
}
// Ensure the attestation with the lower data root is the first attestation.
if bytes.Compare(wrapper_1.DataRoot[:], wrapper_2.DataRoot[:]) > 0 {
slashing = &ethpb.AttesterSlashing{
Attestation_1: wrapper_2.IndexedAttestation,
Attestation_2: wrapper_1.IndexedAttestation,
Attestation_1: att_2,
Attestation_2: att_1,
}
}
@@ -428,17 +462,17 @@ func (s *Service) updateSpans(
kind slashertypes.ChunkKind,
validatorChunkIndex uint64,
currentEpoch primitives.Epoch,
) (map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing, error) {
) (map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing, error) {
ctx, span := trace.StartSpan(ctx, "Slasher.updateSpans")
defer span.End()
// Apply the attestations to the related chunks and find any
// slashings along the way.
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{}
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{}
for _, attWrappers := range attWrapperByChunkIdx {
for _, attWrapper := range attWrappers {
for _, validatorIdx := range attWrapper.IndexedAttestation.AttestingIndices {
for _, validatorIdx := range attWrapper.IndexedAttestation.GetAttestingIndices() {
validatorIndex := primitives.ValidatorIndex(validatorIdx)
computedValidatorChunkIdx := s.params.validatorChunkIndex(validatorIndex)
@@ -493,14 +527,14 @@ func (s *Service) applyAttestationForValidator(
validatorChunkIndex uint64,
validatorIndex primitives.ValidatorIndex,
currentEpoch primitives.Epoch,
) (*ethpb.AttesterSlashing, error) {
) (interfaces.AttesterSlashing, error) {
ctx, span := trace.StartSpan(ctx, "Slasher.applyAttestationForValidator")
defer span.End()
var err error
sourceEpoch := attestation.IndexedAttestation.Data.Source.Epoch
targetEpoch := attestation.IndexedAttestation.Data.Target.Epoch
sourceEpoch := attestation.IndexedAttestation.GetData().Source.Epoch
targetEpoch := attestation.IndexedAttestation.GetData().Target.Epoch
attestationDistance.Observe(float64(targetEpoch) - float64(sourceEpoch))
chunkIndex := s.params.chunkIndex(sourceEpoch)

View File

@@ -668,8 +668,8 @@ func Test_processAttestations(t *testing.T) {
// Create the attester slashing.
expectedSlashing := &ethpb.AttesterSlashing{
Attestation_1: wrapper_1.IndexedAttestation,
Attestation_2: wrapper_2.IndexedAttestation,
Attestation_1: wrapper_1.IndexedAttestation.(*ethpb.IndexedAttestation),
Attestation_2: wrapper_2.IndexedAttestation.(*ethpb.IndexedAttestation),
}
root, err := expectedSlashing.HashTreeRoot()
@@ -821,7 +821,7 @@ func Test_processQueuedAttestations_OverlappingChunkIndices(t *testing.T) {
s.attsQueue = newAttestationsQueue()
s.attsQueue.push(att1)
s.attsQueue.push(att2)
slot, err := slots.EpochStart(att2.IndexedAttestation.Data.Target.Epoch)
slot, err := slots.EpochStart(att2.IndexedAttestation.GetData().Target.Epoch)
require.NoError(t, err)
mockChain.Slot = &slot
s.serviceCfg.HeadStateFetcher = mockChain
@@ -1164,7 +1164,7 @@ func Test_applyAttestationForValidator_MinSpanChunk(t *testing.T) {
)
require.NoError(t, err)
require.IsNil(t, slashing)
att.IndexedAttestation.AttestingIndices = []uint64{uint64(validatorIdx)}
att.IndexedAttestation.(*ethpb.IndexedAttestation).AttestingIndices = []uint64{uint64(validatorIdx)}
err = slasherDB.SaveAttestationRecordsForValidators(
ctx,
[]*slashertypes.IndexedAttestationWrapper{att},
@@ -1221,7 +1221,7 @@ func Test_applyAttestationForValidator_MaxSpanChunk(t *testing.T) {
)
require.NoError(t, err)
require.Equal(t, true, slashing == nil)
att.IndexedAttestation.AttestingIndices = []uint64{uint64(validatorIdx)}
att.IndexedAttestation.(*ethpb.IndexedAttestation).AttestingIndices = []uint64{uint64(validatorIdx)}
err = slasherDB.SaveAttestationRecordsForValidators(
ctx,
[]*slashertypes.IndexedAttestationWrapper{att},

View File

@@ -10,6 +10,7 @@ import (
slashertypes "github.com/prysmaticlabs/prysm/v5/beacon-chain/slasher/types"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/container/slice"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -28,7 +29,7 @@ func (s *Service) groupByValidatorChunkIndex(
for _, attestation := range attestations {
validatorChunkIndexes := make(map[uint64]bool)
for _, validatorIndex := range attestation.IndexedAttestation.AttestingIndices {
for _, validatorIndex := range attestation.IndexedAttestation.GetAttestingIndices() {
validatorChunkIndex := s.params.validatorChunkIndex(primitives.ValidatorIndex(validatorIndex))
validatorChunkIndexes[validatorChunkIndex] = true
}
@@ -51,7 +52,7 @@ func (s *Service) groupByChunkIndex(
attestationsByChunkIndex := make(map[uint64][]*slashertypes.IndexedAttestationWrapper)
for _, attestation := range attestations {
chunkIndex := s.params.chunkIndex(attestation.IndexedAttestation.Data.Source.Epoch)
chunkIndex := s.params.chunkIndex(attestation.IndexedAttestation.GetData().Source.Epoch)
attestationsByChunkIndex[chunkIndex] = append(attestationsByChunkIndex[chunkIndex], attestation)
}
@@ -74,13 +75,13 @@ func (s *Service) filterAttestations(
// If an attestation's source is epoch is older than the max history length
// we keep track of for slashing detection, we drop it.
if attWrapper.IndexedAttestation.Data.Source.Epoch+s.params.historyLength <= currentEpoch {
if attWrapper.IndexedAttestation.GetData().Source.Epoch+s.params.historyLength <= currentEpoch {
numDropped++
continue
}
// If an attestation's target epoch is in the future, we defer processing for later.
if attWrapper.IndexedAttestation.Data.Target.Epoch > currentEpoch {
if attWrapper.IndexedAttestation.GetData().Target.Epoch > currentEpoch {
validInFuture = append(validInFuture, attWrapper)
continue
}
@@ -95,17 +96,17 @@ func (s *Service) filterAttestations(
// source and target epochs, and that the source epoch of the attestation must
// be less than the target epoch, which is a precondition for performing slashing
// detection (except for the genesis epoch).
func validateAttestationIntegrity(att *ethpb.IndexedAttestation) bool {
func validateAttestationIntegrity(att ethpb.IndexedAtt) bool {
// If an attestation is malformed, we drop it.
if att == nil ||
att.Data == nil ||
att.Data.Source == nil ||
att.Data.Target == nil {
att.GetData() == nil ||
att.GetData().Source == nil ||
att.GetData().Target == nil {
return false
}
sourceEpoch := att.Data.Source.Epoch
targetEpoch := att.Data.Target.Epoch
sourceEpoch := att.GetData().Source.Epoch
targetEpoch := att.GetData().Target.Epoch
// The genesis epoch is a special case, since all attestations formed in it
// will have source and target 0, and they should be considered valid.
@@ -129,14 +130,14 @@ func validateBlockHeaderIntegrity(header *ethpb.SignedBeaconBlockHeader) bool {
return true
}
func logAttesterSlashing(slashing *ethpb.AttesterSlashing) {
indices := slice.IntersectionUint64(slashing.Attestation_1.AttestingIndices, slashing.Attestation_2.AttestingIndices)
func logAttesterSlashing(slashing interfaces.AttesterSlashing) {
indices := slice.IntersectionUint64(slashing.GetFirstAttestation().GetAttestingIndices(), slashing.GetSecondAttestation().GetAttestingIndices())
log.WithFields(logrus.Fields{
"validatorIndex": indices,
"prevSourceEpoch": slashing.Attestation_1.Data.Source.Epoch,
"prevTargetEpoch": slashing.Attestation_1.Data.Target.Epoch,
"sourceEpoch": slashing.Attestation_2.Data.Source.Epoch,
"targetEpoch": slashing.Attestation_2.Data.Target.Epoch,
"prevSourceEpoch": slashing.GetFirstAttestation().GetData().Source.Epoch,
"prevTargetEpoch": slashing.GetFirstAttestation().GetData().Target.Epoch,
"sourceEpoch": slashing.GetSecondAttestation().GetData().Source.Epoch,
"targetEpoch": slashing.GetSecondAttestation().GetData().Target.Epoch,
}).Info("Attester slashing detected")
}

View File

@@ -271,22 +271,22 @@ func Test_logSlashingEvent(t *testing.T) {
{
name: "Surrounding vote",
slashing: &ethpb.AttesterSlashing{
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
},
},
{
name: "Surrounded vote",
slashing: &ethpb.AttesterSlashing{
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
},
},
{
name: "Double vote",
slashing: &ethpb.AttesterSlashing{
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation,
Attestation_1: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
Attestation_2: createAttestationWrapperEmptySig(t, 0, 0, nil, nil).IndexedAttestation.(*ethpb.IndexedAttestation),
},
},
}

View File

@@ -6,6 +6,7 @@ import (
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/blocks"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
)
@@ -13,9 +14,9 @@ import (
// Verifies attester slashings, logs them, and submits them to the slashing operations pool
// in the beacon node if they pass validation.
func (s *Service) processAttesterSlashings(
ctx context.Context, slashings map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing,
) (map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing, error) {
processedSlashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{}
ctx context.Context, slashings map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing,
) (map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing, error) {
processedSlashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{}
// If no slashings, return early.
if len(slashings) == 0 {
@@ -30,8 +31,8 @@ func (s *Service) processAttesterSlashings(
for root, slashing := range slashings {
// Verify the signature of the first attestation.
if err := s.verifyAttSignature(ctx, slashing.Attestation_1); err != nil {
log.WithError(err).WithField("a", slashing.Attestation_1).Warn(
if err := s.verifyAttSignature(ctx, slashing.GetFirstAttestation()); err != nil {
log.WithError(err).WithField("a", slashing.GetFirstAttestation()).Warn(
"Invalid signature for attestation in detected slashing offense",
)
@@ -39,8 +40,8 @@ func (s *Service) processAttesterSlashings(
}
// Verify the signature of the second attestation.
if err := s.verifyAttSignature(ctx, slashing.Attestation_2); err != nil {
log.WithError(err).WithField("b", slashing.Attestation_2).Warn(
if err := s.verifyAttSignature(ctx, slashing.GetSecondAttestation()); err != nil {
log.WithError(err).WithField("b", slashing.GetSecondAttestation()).Warn(
"Invalid signature for attestation in detected slashing offense",
)
@@ -110,8 +111,8 @@ func (s *Service) verifyBlockSignature(ctx context.Context, header *ethpb.Signed
return blocks.VerifyBlockHeaderSignature(parentState, header)
}
func (s *Service) verifyAttSignature(ctx context.Context, att *ethpb.IndexedAttestation) error {
preState, err := s.serviceCfg.AttestationStateFetcher.AttestationTargetState(ctx, att.Data.Target)
func (s *Service) verifyAttSignature(ctx context.Context, att ethpb.IndexedAtt) error {
preState, err := s.serviceCfg.AttestationStateFetcher.AttestationTargetState(ctx, att.GetData().Target)
if err != nil {
return err
}

View File

@@ -12,6 +12,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state/stategen"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
@@ -84,7 +85,7 @@ func TestService_processAttesterSlashings(t *testing.T) {
root, err := slashing.HashTreeRoot()
require.NoError(tt, err, "failed to hash tree root")
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{
root: slashing,
}
@@ -108,7 +109,7 @@ func TestService_processAttesterSlashings(t *testing.T) {
root, err := slashing.HashTreeRoot()
require.NoError(tt, err, "failed to hash tree root")
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{
root: slashing,
}
@@ -132,7 +133,7 @@ func TestService_processAttesterSlashings(t *testing.T) {
root, err := slashing.HashTreeRoot()
require.NoError(tt, err, "failed to hash tree root")
slashings := map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing{
slashings := map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing{
root: slashing,
}

View File

@@ -7,6 +7,7 @@ import (
"github.com/pkg/errors"
slashertypes "github.com/prysmaticlabs/prysm/v5/beacon-chain/slasher/types"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/time/slots"
@@ -22,7 +23,7 @@ const (
// Receive indexed attestations from some source event feed,
// validating their integrity before appending them to an attestation queue
// for batch processing in a separate routine.
func (s *Service) receiveAttestations(ctx context.Context, indexedAttsChan chan *ethpb.IndexedAttestation) {
func (s *Service) receiveAttestations(ctx context.Context, indexedAttsChan chan ethpb.IndexedAtt) {
defer s.wg.Done()
sub := s.serviceCfg.IndexedAttestationsFeed.Subscribe(indexedAttsChan)
@@ -33,7 +34,7 @@ func (s *Service) receiveAttestations(ctx context.Context, indexedAttsChan chan
if !validateAttestationIntegrity(att) {
continue
}
dataRoot, err := att.Data.HashTreeRoot()
dataRoot, err := att.GetData().HashTreeRoot()
if err != nil {
log.WithError(err).Error("Could not get hash tree root of attestation")
continue
@@ -108,7 +109,7 @@ func (s *Service) processAttestations(
ctx context.Context,
attestations []*slashertypes.IndexedAttestationWrapper,
currentSlot primitives.Slot,
) map[[fieldparams.RootLength]byte]*ethpb.AttesterSlashing {
) map[[fieldparams.RootLength]byte]interfaces.AttesterSlashing {
// Get the current epoch from the current slot.
currentEpoch := slots.ToEpoch(currentSlot)

View File

@@ -29,7 +29,7 @@ func TestSlasher_receiveAttestations_OK(t *testing.T) {
},
attsQueue: newAttestationsQueue(),
}
indexedAttsChan := make(chan *ethpb.IndexedAttestation)
indexedAttsChan := make(chan ethpb.IndexedAtt)
defer close(indexedAttsChan)
s.wg.Add(1)
@@ -212,7 +212,7 @@ func TestSlasher_receiveAttestations_OnlyValidAttestations(t *testing.T) {
},
attsQueue: newAttestationsQueue(),
}
indexedAttsChan := make(chan *ethpb.IndexedAttestation)
indexedAttsChan := make(chan ethpb.IndexedAtt)
defer close(indexedAttsChan)
s.wg.Add(1)

View File

@@ -48,7 +48,7 @@ type ServiceConfig struct {
type Service struct {
params *Parameters
serviceCfg *ServiceConfig
indexedAttsChan chan *ethpb.IndexedAttestation
indexedAttsChan chan ethpb.IndexedAtt
beaconBlockHeadersChan chan *ethpb.SignedBeaconBlockHeader
attsQueue *attestationsQueue
blksQueue *blocksQueue
@@ -68,7 +68,7 @@ func New(ctx context.Context, srvCfg *ServiceConfig) (*Service, error) {
return &Service{
params: DefaultParams(),
serviceCfg: srvCfg,
indexedAttsChan: make(chan *ethpb.IndexedAttestation, 1),
indexedAttsChan: make(chan ethpb.IndexedAtt, 1),
beaconBlockHeadersChan: make(chan *ethpb.SignedBeaconBlockHeader, 1),
attsQueue: newAttestationsQueue(),
blksQueue: newBlocksQueue(),
@@ -117,7 +117,7 @@ func (s *Service) run() {
"Finished retrieving last epoch written per validator",
)
indexedAttsChan := make(chan *ethpb.IndexedAttestation, 1)
indexedAttsChan := make(chan ethpb.IndexedAtt, 1)
beaconBlockHeadersChan := make(chan *ethpb.SignedBeaconBlockHeader, 1)
s.wg.Add(1)

View File

@@ -29,7 +29,7 @@ func (c ChunkKind) String() string {
// IndexedAttestationWrapper contains an indexed attestation with its
// data root to reduce duplicated computation.
type IndexedAttestationWrapper struct {
IndexedAttestation *ethpb.IndexedAttestation
IndexedAttestation ethpb.IndexedAtt
DataRoot [32]byte
}

View File

@@ -9,6 +9,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/operations/attestations"
lruwrpr "github.com/prysmaticlabs/prysm/v5/cache/lru"
fieldparams "github.com/prysmaticlabs/prysm/v5/config/fieldparams"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"github.com/prysmaticlabs/prysm/v5/testing/assert"
"github.com/prysmaticlabs/prysm/v5/testing/require"
@@ -34,7 +35,7 @@ func TestBeaconAggregateProofSubscriber_CanSaveAggregatedAttestation(t *testing.
Signature: make([]byte, fieldparams.BLSSignatureLength),
}
require.NoError(t, r.beaconAggregateProofSubscriber(context.Background(), a))
assert.DeepSSZEqual(t, []*ethpb.Attestation{a.Message.Aggregate}, r.cfg.attPool.AggregatedAttestations(), "Did not save aggregated attestation")
assert.DeepSSZEqual(t, []interfaces.Attestation{a.Message.Aggregate}, r.cfg.attPool.AggregatedAttestations(), "Did not save aggregated attestation")
}
func TestBeaconAggregateProofSubscriber_CanSaveUnaggregatedAttestation(t *testing.T) {
@@ -59,5 +60,5 @@ func TestBeaconAggregateProofSubscriber_CanSaveUnaggregatedAttestation(t *testin
atts, err := r.cfg.attPool.UnaggregatedAttestations()
require.NoError(t, err)
assert.DeepEqual(t, []*ethpb.Attestation{a.Message.Aggregate}, atts, "Did not save unaggregated attestation")
assert.DeepEqual(t, []interfaces.Attestation{a.Message.Aggregate}, atts, "Did not save unaggregated attestation")
}

View File

@@ -5,6 +5,7 @@ import (
"fmt"
"github.com/pkg/errors"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
"google.golang.org/protobuf/proto"
)
@@ -25,13 +26,13 @@ func (s *Service) voluntaryExitSubscriber(_ context.Context, msg proto.Message)
}
func (s *Service) attesterSlashingSubscriber(ctx context.Context, msg proto.Message) error {
aSlashing, ok := msg.(*ethpb.AttesterSlashing)
aSlashing, ok := msg.(interfaces.AttesterSlashing)
if !ok {
return fmt.Errorf("wrong type, expected: *ethpb.AttesterSlashing got: %T", msg)
}
// Do some nil checks to prevent easy DoS'ing of this handler.
aSlashing1IsNil := aSlashing == nil || aSlashing.Attestation_1 == nil || aSlashing.Attestation_1.AttestingIndices == nil
aSlashing2IsNil := aSlashing == nil || aSlashing.Attestation_2 == nil || aSlashing.Attestation_2.AttestingIndices == nil
aSlashing1IsNil := aSlashing == nil || aSlashing.GetFirstAttestation() == nil || aSlashing.GetFirstAttestation().GetAttestingIndices() == nil
aSlashing2IsNil := aSlashing == nil || aSlashing.GetSecondAttestation() == nil || aSlashing.GetSecondAttestation().GetAttestingIndices() == nil
if !aSlashing1IsNil && !aSlashing2IsNil {
headState, err := s.cfg.chain.HeadState(ctx)
if err != nil {
@@ -40,7 +41,7 @@ func (s *Service) attesterSlashingSubscriber(ctx context.Context, msg proto.Mess
if err := s.cfg.slashingPool.InsertAttesterSlashing(ctx, headState, aSlashing); err != nil {
return errors.Wrap(err, "could not insert attester slashing into pool")
}
s.setAttesterSlashingIndicesSeen(aSlashing.Attestation_1.AttestingIndices, aSlashing.Attestation_2.AttestingIndices)
s.setAttesterSlashingIndicesSeen(aSlashing.GetFirstAttestation().GetAttestingIndices(), aSlashing.GetSecondAttestation().GetAttestingIndices())
}
return nil
}

View File

@@ -15,6 +15,7 @@ import (
"github.com/prysmaticlabs/prysm/v5/beacon-chain/core/signing"
"github.com/prysmaticlabs/prysm/v5/beacon-chain/state"
"github.com/prysmaticlabs/prysm/v5/config/params"
"github.com/prysmaticlabs/prysm/v5/consensus-types/interfaces"
"github.com/prysmaticlabs/prysm/v5/consensus-types/primitives"
"github.com/prysmaticlabs/prysm/v5/crypto/bls"
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
@@ -176,7 +177,7 @@ func (s *Service) validateAggregatedAtt(ctx context.Context, signed *ethpb.Signe
tracing.AnnotateError(span, wrappedErr)
return pubsub.ValidationIgnore, wrappedErr
}
attSigSet, err := blocks.AttestationSignatureBatch(ctx, bs, []*ethpb.Attestation{signed.Message.Aggregate})
attSigSet, err := blocks.AttestationSignatureBatch(ctx, bs, []interfaces.Attestation{signed.Message.Aggregate})
if err != nil {
wrappedErr := errors.Wrapf(err, "Could not verify aggregator signature %d", signed.Message.AggregatorIndex)
tracing.AnnotateError(span, wrappedErr)
@@ -225,7 +226,7 @@ func (s *Service) setAggregatorIndexEpochSeen(epoch primitives.Epoch, aggregator
// - [REJECT] The aggregate attestation has participants -- that is, len(get_attesting_indices(state, aggregate.data, aggregate.aggregation_bits)) >= 1.
// - [REJECT] The aggregator's validator index is within the committee --
// i.e. `aggregate_and_proof.aggregator_index in get_beacon_committee(state, aggregate.data.slot, aggregate.data.index)`.
func (s *Service) validateIndexInCommittee(ctx context.Context, bs state.ReadOnlyBeaconState, a *ethpb.Attestation, validatorIndex primitives.ValidatorIndex) (pubsub.ValidationResult, error) {
func (s *Service) validateIndexInCommittee(ctx context.Context, bs state.ReadOnlyBeaconState, a interfaces.Attestation, validatorIndex primitives.ValidatorIndex) (pubsub.ValidationResult, error) {
ctx, span := trace.StartSpan(ctx, "sync.validateIndexInCommittee")
defer span.End()
@@ -239,7 +240,7 @@ func (s *Service) validateIndexInCommittee(ctx context.Context, bs state.ReadOnl
return result, err
}
if a.AggregationBits.Count() == 0 {
if a.GetAggregationBits().Count() == 0 {
return pubsub.ValidationReject, errors.New("no attesting indices")
}

Some files were not shown because too many files have changed in this diff Show More