mirror of
https://github.com/OffchainLabs/prysm.git
synced 2026-01-09 13:28:01 -05:00
* config params into pkg * gaz Co-authored-by: prylabs-bulldozer[bot] <58059840+prylabs-bulldozer[bot]@users.noreply.github.com>
216 lines
10 KiB
Go
216 lines
10 KiB
Go
package precompute_test
|
|
|
|
import (
|
|
"context"
|
|
"testing"
|
|
|
|
"github.com/prysmaticlabs/go-bitfield"
|
|
"github.com/prysmaticlabs/prysm/beacon-chain/core/epoch/precompute"
|
|
"github.com/prysmaticlabs/prysm/beacon-chain/core/helpers"
|
|
"github.com/prysmaticlabs/prysm/config/params"
|
|
ethpb "github.com/prysmaticlabs/prysm/proto/prysm/v1alpha1"
|
|
"github.com/prysmaticlabs/prysm/proto/prysm/v1alpha1/attestation"
|
|
"github.com/prysmaticlabs/prysm/shared/testutil"
|
|
"github.com/prysmaticlabs/prysm/shared/testutil/assert"
|
|
"github.com/prysmaticlabs/prysm/shared/testutil/require"
|
|
)
|
|
|
|
func TestUpdateValidator_Works(t *testing.T) {
|
|
e := params.BeaconConfig().FarFutureSlot
|
|
vp := []*precompute.Validator{{}, {InclusionSlot: e}, {}, {InclusionSlot: e}, {}, {InclusionSlot: e}}
|
|
record := &precompute.Validator{IsCurrentEpochAttester: true, IsCurrentEpochTargetAttester: true,
|
|
IsPrevEpochAttester: true, IsPrevEpochTargetAttester: true, IsPrevEpochHeadAttester: true}
|
|
a := ðpb.PendingAttestation{InclusionDelay: 1, ProposerIndex: 2}
|
|
|
|
// Indices 1 3 and 5 attested
|
|
vp = precompute.UpdateValidator(vp, record, []uint64{1, 3, 5}, a, 100)
|
|
|
|
wanted := &precompute.Validator{IsCurrentEpochAttester: true, IsCurrentEpochTargetAttester: true,
|
|
IsPrevEpochAttester: true, IsPrevEpochTargetAttester: true, IsPrevEpochHeadAttester: true,
|
|
ProposerIndex: 2, InclusionDistance: 1, InclusionSlot: 101}
|
|
wantedVp := []*precompute.Validator{{}, wanted, {}, wanted, {}, wanted}
|
|
assert.DeepEqual(t, wantedVp, vp, "Incorrect attesting validator calculations")
|
|
}
|
|
|
|
func TestUpdateValidator_InclusionOnlyCountsPrevEpoch(t *testing.T) {
|
|
e := params.BeaconConfig().FarFutureSlot
|
|
vp := []*precompute.Validator{{InclusionSlot: e}}
|
|
record := &precompute.Validator{IsCurrentEpochAttester: true, IsCurrentEpochTargetAttester: true}
|
|
a := ðpb.PendingAttestation{InclusionDelay: 1, ProposerIndex: 2}
|
|
|
|
// Verify inclusion info doesnt get updated.
|
|
vp = precompute.UpdateValidator(vp, record, []uint64{0}, a, 100)
|
|
wanted := &precompute.Validator{IsCurrentEpochAttester: true, IsCurrentEpochTargetAttester: true, InclusionSlot: e}
|
|
wantedVp := []*precompute.Validator{wanted}
|
|
assert.DeepEqual(t, wantedVp, vp, "Incorrect attesting validator calculations")
|
|
}
|
|
|
|
func TestUpdateBalance(t *testing.T) {
|
|
vp := []*precompute.Validator{
|
|
{IsCurrentEpochAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsCurrentEpochTargetAttester: true, IsCurrentEpochAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsCurrentEpochTargetAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsPrevEpochAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsPrevEpochAttester: true, IsPrevEpochTargetAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsPrevEpochHeadAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsPrevEpochAttester: true, IsPrevEpochHeadAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
{IsSlashed: true, IsCurrentEpochAttester: true, CurrentEpochEffectiveBalance: 100 * params.BeaconConfig().EffectiveBalanceIncrement},
|
|
}
|
|
wantedPBal := &precompute.Balance{
|
|
ActiveCurrentEpoch: params.BeaconConfig().EffectiveBalanceIncrement,
|
|
ActivePrevEpoch: params.BeaconConfig().EffectiveBalanceIncrement,
|
|
CurrentEpochAttested: 200 * params.BeaconConfig().EffectiveBalanceIncrement,
|
|
CurrentEpochTargetAttested: 200 * params.BeaconConfig().EffectiveBalanceIncrement,
|
|
PrevEpochAttested: 300 * params.BeaconConfig().EffectiveBalanceIncrement,
|
|
PrevEpochTargetAttested: 100 * params.BeaconConfig().EffectiveBalanceIncrement,
|
|
PrevEpochHeadAttested: 200 * params.BeaconConfig().EffectiveBalanceIncrement,
|
|
}
|
|
pBal := precompute.UpdateBalance(vp, &precompute.Balance{})
|
|
assert.DeepEqual(t, wantedPBal, pBal, "Incorrect balance calculations")
|
|
}
|
|
|
|
func TestSameHead(t *testing.T) {
|
|
beaconState, _ := testutil.DeterministicGenesisState(t, 100)
|
|
require.NoError(t, beaconState.SetSlot(1))
|
|
att := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 0}}}
|
|
r := [32]byte{'A'}
|
|
br := beaconState.BlockRoots()
|
|
br[0] = r[:]
|
|
require.NoError(t, beaconState.SetBlockRoots(br))
|
|
att.Data.BeaconBlockRoot = r[:]
|
|
same, err := precompute.SameHead(beaconState, ðpb.PendingAttestation{Data: att.Data})
|
|
require.NoError(t, err)
|
|
assert.Equal(t, true, same, "Head in state does not match head in attestation")
|
|
newRoot := [32]byte{'B'}
|
|
att.Data.BeaconBlockRoot = newRoot[:]
|
|
same, err = precompute.SameHead(beaconState, ðpb.PendingAttestation{Data: att.Data})
|
|
require.NoError(t, err)
|
|
assert.Equal(t, false, same, "Head in state matches head in attestation")
|
|
}
|
|
|
|
func TestSameTarget(t *testing.T) {
|
|
beaconState, _ := testutil.DeterministicGenesisState(t, 100)
|
|
require.NoError(t, beaconState.SetSlot(1))
|
|
att := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 0}}}
|
|
r := [32]byte{'A'}
|
|
br := beaconState.BlockRoots()
|
|
br[0] = r[:]
|
|
require.NoError(t, beaconState.SetBlockRoots(br))
|
|
att.Data.Target.Root = r[:]
|
|
same, err := precompute.SameTarget(beaconState, ðpb.PendingAttestation{Data: att.Data}, 0)
|
|
require.NoError(t, err)
|
|
assert.Equal(t, true, same, "Head in state does not match head in attestation")
|
|
newRoot := [32]byte{'B'}
|
|
att.Data.Target.Root = newRoot[:]
|
|
same, err = precompute.SameTarget(beaconState, ðpb.PendingAttestation{Data: att.Data}, 0)
|
|
require.NoError(t, err)
|
|
assert.Equal(t, false, same, "Head in state matches head in attestation")
|
|
}
|
|
|
|
func TestAttestedPrevEpoch(t *testing.T) {
|
|
beaconState, _ := testutil.DeterministicGenesisState(t, 100)
|
|
require.NoError(t, beaconState.SetSlot(params.BeaconConfig().SlotsPerEpoch))
|
|
att := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 0}}}
|
|
r := [32]byte{'A'}
|
|
br := beaconState.BlockRoots()
|
|
br[0] = r[:]
|
|
require.NoError(t, beaconState.SetBlockRoots(br))
|
|
att.Data.Target.Root = r[:]
|
|
att.Data.BeaconBlockRoot = r[:]
|
|
votedEpoch, votedTarget, votedHead, err := precompute.AttestedPrevEpoch(beaconState, ðpb.PendingAttestation{Data: att.Data})
|
|
require.NoError(t, err)
|
|
assert.Equal(t, true, votedEpoch, "Did not vote epoch")
|
|
assert.Equal(t, true, votedTarget, "Did not vote target")
|
|
assert.Equal(t, true, votedHead, "Did not vote head")
|
|
}
|
|
|
|
func TestAttestedCurrentEpoch(t *testing.T) {
|
|
beaconState, _ := testutil.DeterministicGenesisState(t, 100)
|
|
require.NoError(t, beaconState.SetSlot(params.BeaconConfig().SlotsPerEpoch+1))
|
|
att := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 1}}}
|
|
r := [32]byte{'A'}
|
|
|
|
br := beaconState.BlockRoots()
|
|
br[params.BeaconConfig().SlotsPerEpoch] = r[:]
|
|
require.NoError(t, beaconState.SetBlockRoots(br))
|
|
att.Data.Target.Root = r[:]
|
|
att.Data.BeaconBlockRoot = r[:]
|
|
votedEpoch, votedTarget, err := precompute.AttestedCurrentEpoch(beaconState, ðpb.PendingAttestation{Data: att.Data})
|
|
require.NoError(t, err)
|
|
assert.Equal(t, true, votedEpoch, "Did not vote epoch")
|
|
assert.Equal(t, true, votedTarget, "Did not vote target")
|
|
}
|
|
|
|
func TestProcessAttestations(t *testing.T) {
|
|
params.UseMinimalConfig()
|
|
defer params.UseMainnetConfig()
|
|
|
|
validators := uint64(128)
|
|
beaconState, _ := testutil.DeterministicGenesisState(t, validators)
|
|
require.NoError(t, beaconState.SetSlot(params.BeaconConfig().SlotsPerEpoch))
|
|
c := helpers.SlotCommitteeCount(validators)
|
|
bf := bitfield.NewBitlist(c)
|
|
att1 := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 0}},
|
|
AggregationBits: bf}
|
|
att2 := ðpb.Attestation{Data: ðpb.AttestationData{
|
|
Target: ðpb.Checkpoint{Epoch: 0}},
|
|
AggregationBits: bf}
|
|
rt := [32]byte{'A'}
|
|
att1.Data.Target.Root = rt[:]
|
|
att1.Data.BeaconBlockRoot = rt[:]
|
|
br := beaconState.BlockRoots()
|
|
newRt := [32]byte{'B'}
|
|
br[0] = newRt[:]
|
|
require.NoError(t, beaconState.SetBlockRoots(br))
|
|
att2.Data.Target.Root = newRt[:]
|
|
att2.Data.BeaconBlockRoot = newRt[:]
|
|
err := beaconState.AppendPreviousEpochAttestations(ðpb.PendingAttestation{Data: att1.Data, AggregationBits: bf, InclusionDelay: 1})
|
|
require.NoError(t, err)
|
|
err = beaconState.AppendCurrentEpochAttestations(ðpb.PendingAttestation{Data: att2.Data, AggregationBits: bf, InclusionDelay: 1})
|
|
require.NoError(t, err)
|
|
|
|
pVals := make([]*precompute.Validator, validators)
|
|
for i := 0; i < len(pVals); i++ {
|
|
pVals[i] = &precompute.Validator{CurrentEpochEffectiveBalance: 100}
|
|
}
|
|
pVals, _, err = precompute.ProcessAttestations(context.Background(), beaconState, pVals, &precompute.Balance{})
|
|
require.NoError(t, err)
|
|
|
|
committee, err := helpers.BeaconCommitteeFromState(beaconState, att1.Data.Slot, att1.Data.CommitteeIndex)
|
|
require.NoError(t, err)
|
|
indices, err := attestation.AttestingIndices(att1.AggregationBits, committee)
|
|
require.NoError(t, err)
|
|
for _, i := range indices {
|
|
if !pVals[i].IsPrevEpochAttester {
|
|
t.Error("Not a prev epoch attester")
|
|
}
|
|
}
|
|
committee, err = helpers.BeaconCommitteeFromState(beaconState, att2.Data.Slot, att2.Data.CommitteeIndex)
|
|
require.NoError(t, err)
|
|
indices, err = attestation.AttestingIndices(att2.AggregationBits, committee)
|
|
require.NoError(t, err)
|
|
for _, i := range indices {
|
|
assert.Equal(t, true, pVals[i].IsPrevEpochAttester, "Not a prev epoch attester")
|
|
assert.Equal(t, true, pVals[i].IsPrevEpochTargetAttester, "Not a prev epoch target attester")
|
|
assert.Equal(t, true, pVals[i].IsPrevEpochHeadAttester, "Not a prev epoch head attester")
|
|
}
|
|
}
|
|
|
|
func TestEnsureBalancesLowerBound(t *testing.T) {
|
|
b := &precompute.Balance{}
|
|
b = precompute.EnsureBalancesLowerBound(b)
|
|
balanceIncrement := params.BeaconConfig().EffectiveBalanceIncrement
|
|
assert.Equal(t, balanceIncrement, b.ActiveCurrentEpoch, "Did not get wanted active current balance")
|
|
assert.Equal(t, balanceIncrement, b.ActivePrevEpoch, "Did not get wanted active previous balance")
|
|
assert.Equal(t, balanceIncrement, b.CurrentEpochAttested, "Did not get wanted current attested balance")
|
|
assert.Equal(t, balanceIncrement, b.CurrentEpochTargetAttested, "Did not get wanted target attested balance")
|
|
assert.Equal(t, balanceIncrement, b.PrevEpochAttested, "Did not get wanted prev attested balance")
|
|
assert.Equal(t, balanceIncrement, b.PrevEpochTargetAttested, "Did not get wanted prev target attested balance")
|
|
assert.Equal(t, balanceIncrement, b.PrevEpochHeadAttested, "Did not get wanted prev head attested balance")
|
|
}
|