diff --git a/consensus/state_processing/src/per_block_processing.rs b/consensus/state_processing/src/per_block_processing.rs index b70579c826..43414f7085 100644 --- a/consensus/state_processing/src/per_block_processing.rs +++ b/consensus/state_processing/src/per_block_processing.rs @@ -20,7 +20,7 @@ pub use verify_attestation::{ }; pub use verify_bls_to_execution_change::verify_bls_to_execution_change; pub use verify_deposit::{ - get_existing_validator_index, verify_deposit_merkle_proof, verify_deposit_signature, + get_existing_validator_index, is_valid_deposit_signature, verify_deposit_merkle_proof, }; pub use verify_exit::verify_exit; diff --git a/consensus/state_processing/src/per_block_processing/process_operations.rs b/consensus/state_processing/src/per_block_processing/process_operations.rs index 9aaef8f965..35a0c0ffad 100644 --- a/consensus/state_processing/src/per_block_processing/process_operations.rs +++ b/consensus/state_processing/src/per_block_processing/process_operations.rs @@ -6,6 +6,7 @@ use crate::common::{ use crate::per_block_processing::errors::{BlockProcessingError, IntoWithIndex}; use crate::VerifySignatures; use types::consts::altair::{PARTICIPATION_FLAG_WEIGHTS, PROPOSER_WEIGHT, WEIGHT_DENOMINATOR}; +use types::validator::is_compounding_withdrawal_credential; pub fn process_operations>( state: &mut BeaconState, @@ -431,15 +432,47 @@ pub fn apply_deposit( let amount = deposit.data.amount; if let Some(index) = validator_index { - // Update the existing validator balance. - increase_balance(state, index as usize, amount)?; + // [Modified in Electra:EIP7251] + if let Ok(pending_balance_deposits) = state.pending_balance_deposits_mut() { + pending_balance_deposits.push(PendingBalanceDeposit { index, amount })?; + + let validator = state + .validators() + .get(index as usize) + .ok_or(BeaconStateError::UnknownValidator(index as usize))?; + + if is_compounding_withdrawal_credential(deposit.data.withdrawal_credentials, spec) + && validator.has_eth1_withdrawal_credential(spec) + && is_valid_deposit_signature(&deposit.data, spec).is_ok() + { + state.switch_to_compounding_validator(index as usize, spec)?; + } + } else { + // Update the existing validator balance. + increase_balance(state, index as usize, amount)?; + } } else { // The signature should be checked for new validators. Return early for a bad // signature. - if verify_deposit_signature(&deposit.data, spec).is_err() { + if is_valid_deposit_signature(&deposit.data, spec).is_err() { return Ok(()); } + let new_validator_index = state.validators().len(); + + // [Modified in Electra:EIP7251] + let (effective_balance, state_balance) = if state.fork_name_unchecked() >= ForkName::Electra + { + (0, 0) + } else { + ( + std::cmp::min( + amount.safe_sub(amount.safe_rem(spec.effective_balance_increment)?)?, + spec.max_effective_balance, + ), + amount, + ) + }; // Create a new validator. let validator = Validator { pubkey: deposit.data.pubkey, @@ -448,14 +481,11 @@ pub fn apply_deposit( activation_epoch: spec.far_future_epoch, exit_epoch: spec.far_future_epoch, withdrawable_epoch: spec.far_future_epoch, - effective_balance: std::cmp::min( - amount.safe_sub(amount.safe_rem(spec.effective_balance_increment)?)?, - spec.max_effective_balance, - ), + effective_balance, slashed: false, }; state.validators_mut().push(validator)?; - state.balances_mut().push(deposit.data.amount)?; + state.balances_mut().push(state_balance)?; // Altair or later initializations. if let Ok(previous_epoch_participation) = state.previous_epoch_participation_mut() { @@ -467,6 +497,14 @@ pub fn apply_deposit( if let Ok(inactivity_scores) = state.inactivity_scores_mut() { inactivity_scores.push(0)?; } + + // [New in Electra:EIP7251] + if let Ok(pending_balance_deposits) = state.pending_balance_deposits_mut() { + pending_balance_deposits.push(PendingBalanceDeposit { + index: new_validator_index as u64, + amount, + })?; + } } Ok(()) diff --git a/consensus/state_processing/src/per_block_processing/verify_deposit.rs b/consensus/state_processing/src/per_block_processing/verify_deposit.rs index a964f3b574..c996e580a7 100644 --- a/consensus/state_processing/src/per_block_processing/verify_deposit.rs +++ b/consensus/state_processing/src/per_block_processing/verify_deposit.rs @@ -14,7 +14,7 @@ fn error(reason: DepositInvalid) -> BlockOperationError { /// Verify `Deposit.pubkey` signed `Deposit.signature`. /// /// Spec v0.12.1 -pub fn verify_deposit_signature(deposit_data: &DepositData, spec: &ChainSpec) -> Result<()> { +pub fn is_valid_deposit_signature(deposit_data: &DepositData, spec: &ChainSpec) -> Result<()> { let (public_key, signature, msg) = deposit_pubkey_signature_message(deposit_data, spec) .ok_or_else(|| error(DepositInvalid::BadBlsBytes))?;