mirror of
https://github.com/OffchainLabs/prysm.git
synced 2026-01-10 13:58:09 -05:00
Electra: updated compute_proposer_index
This commit is contained in:
@@ -79,6 +79,7 @@ go_test(
|
||||
"//crypto/hash:go_default_library",
|
||||
"//encoding/bytesutil:go_default_library",
|
||||
"//proto/prysm/v1alpha1:go_default_library",
|
||||
"//runtime/version:go_default_library",
|
||||
"//testing/assert:go_default_library",
|
||||
"//testing/require:go_default_library",
|
||||
"//testing/util:go_default_library",
|
||||
|
||||
@@ -17,6 +17,7 @@ import (
|
||||
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
|
||||
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
|
||||
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
|
||||
"github.com/prysmaticlabs/prysm/v5/runtime/version"
|
||||
"github.com/prysmaticlabs/prysm/v5/time/slots"
|
||||
log "github.com/sirupsen/logrus"
|
||||
"go.opencensus.io/trace"
|
||||
@@ -357,10 +358,11 @@ func BeaconProposerIndexAtSlot(ctx context.Context, state state.ReadOnlyBeaconSt
|
||||
// candidate_index = indices[compute_shuffled_index(i % total, total, seed)]
|
||||
// random_byte = hash(seed + uint_to_bytes(uint64(i // 32)))[i % 32]
|
||||
// effective_balance = state.validators[candidate_index].effective_balance
|
||||
// if effective_balance * MAX_RANDOM_BYTE >= MAX_EFFECTIVE_BALANCE * random_byte:
|
||||
// # [Modified in Electra:EIP7251]
|
||||
// if effective_balance * MAX_RANDOM_BYTE >= MAX_EFFECTIVE_BALANCE_ELECTRA * random_byte:
|
||||
// return candidate_index
|
||||
// i += 1
|
||||
func ComputeProposerIndex(bState state.ReadOnlyValidators, activeIndices []primitives.ValidatorIndex, seed [32]byte) (primitives.ValidatorIndex, error) {
|
||||
func ComputeProposerIndex(bState state.ReadOnlyBeaconState, activeIndices []primitives.ValidatorIndex, seed [32]byte) (primitives.ValidatorIndex, error) {
|
||||
length := uint64(len(activeIndices))
|
||||
if length == 0 {
|
||||
return 0, errors.New("empty active indices list")
|
||||
@@ -385,7 +387,12 @@ func ComputeProposerIndex(bState state.ReadOnlyValidators, activeIndices []primi
|
||||
}
|
||||
effectiveBal := v.EffectiveBalance()
|
||||
|
||||
if effectiveBal*maxRandomByte >= params.BeaconConfig().MaxEffectiveBalance*uint64(randomByte) {
|
||||
maxEB := params.BeaconConfig().MaxEffectiveBalanceElectra
|
||||
if bState.Version() < version.Electra {
|
||||
maxEB = params.BeaconConfig().MaxEffectiveBalance
|
||||
}
|
||||
|
||||
if effectiveBal*maxRandomByte >= maxEB*uint64(randomByte) {
|
||||
return candidateIndex, nil
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@ import (
|
||||
"github.com/prysmaticlabs/prysm/v5/crypto/hash"
|
||||
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
|
||||
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
|
||||
"github.com/prysmaticlabs/prysm/v5/runtime/version"
|
||||
"github.com/prysmaticlabs/prysm/v5/testing/assert"
|
||||
"github.com/prysmaticlabs/prysm/v5/testing/require"
|
||||
)
|
||||
@@ -595,6 +596,7 @@ func TestComputeProposerIndex(t *testing.T) {
|
||||
validators []*ethpb.Validator
|
||||
indices []primitives.ValidatorIndex
|
||||
seed [32]byte
|
||||
minVersion int
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
@@ -682,21 +684,81 @@ func TestComputeProposerIndex(t *testing.T) {
|
||||
},
|
||||
want: 7,
|
||||
},
|
||||
{
|
||||
name: "all_active_indices_above_min_activation_balance",
|
||||
args: args{
|
||||
validators: []*ethpb.Validator{
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
},
|
||||
indices: []primitives.ValidatorIndex{0, 1, 2, 3, 4},
|
||||
seed: seed,
|
||||
minVersion: version.Electra,
|
||||
},
|
||||
want: 2,
|
||||
},
|
||||
{
|
||||
name: "second_half_active_above_min_activation_balance",
|
||||
args: args{
|
||||
validators: []*ethpb.Validator{
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
{EffectiveBalance: params.BeaconConfig().MaxEffectiveBalanceElectra},
|
||||
},
|
||||
indices: []primitives.ValidatorIndex{5, 6, 7, 8, 9},
|
||||
seed: seed,
|
||||
minVersion: version.Electra,
|
||||
},
|
||||
want: 7,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
helpers.ClearCache()
|
||||
t.Run("phase0", func(t *testing.T) {
|
||||
if tt.args.minVersion > version.Phase0 {
|
||||
t.Skip("scenario does not apply to phase0")
|
||||
}
|
||||
helpers.ClearCache()
|
||||
bState := ðpb.BeaconState{Validators: tt.args.validators}
|
||||
stTrie, err := state_native.InitializeFromProtoUnsafePhase0(bState)
|
||||
require.NoError(t, err)
|
||||
got, err := helpers.ComputeProposerIndex(stTrie, tt.args.indices, tt.args.seed)
|
||||
if tt.wantedErr != "" {
|
||||
assert.ErrorContains(t, tt.wantedErr, err)
|
||||
return
|
||||
}
|
||||
assert.NoError(t, err, "received unexpected error")
|
||||
assert.Equal(t, tt.want, got, "ComputeProposerIndex()")
|
||||
})
|
||||
t.Run("electra", func(t *testing.T) {
|
||||
if tt.args.minVersion > version.Electra {
|
||||
t.Skip("scenario does not apply to electra")
|
||||
}
|
||||
helpers.ClearCache()
|
||||
bState := ðpb.BeaconStateElectra{Validators: tt.args.validators}
|
||||
stTrie, err := state_native.InitializeFromProtoUnsafeElectra(bState)
|
||||
require.NoError(t, err)
|
||||
|
||||
bState := ðpb.BeaconState{Validators: tt.args.validators}
|
||||
stTrie, err := state_native.InitializeFromProtoUnsafePhase0(bState)
|
||||
require.NoError(t, err)
|
||||
got, err := helpers.ComputeProposerIndex(stTrie, tt.args.indices, tt.args.seed)
|
||||
if tt.wantedErr != "" {
|
||||
assert.ErrorContains(t, tt.wantedErr, err)
|
||||
return
|
||||
}
|
||||
assert.NoError(t, err, "received unexpected error")
|
||||
assert.Equal(t, tt.want, got, "ComputeProposerIndex()")
|
||||
require.Equal(t, stTrie.Version(), version.Electra)
|
||||
|
||||
got, err := helpers.ComputeProposerIndex(stTrie, tt.args.indices, tt.args.seed)
|
||||
if tt.wantedErr != "" {
|
||||
assert.ErrorContains(t, tt.wantedErr, err)
|
||||
return
|
||||
}
|
||||
assert.NoError(t, err, "received unexpected error")
|
||||
assert.Equal(t, tt.want, got, "ComputeProposerIndex()")
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user