initial straightforward merge changes

This commit is contained in:
Daniel Knopik
2026-04-27 11:36:09 +02:00
195 changed files with 12380 additions and 2607 deletions

View File

@@ -239,6 +239,7 @@ pub fn test_da_checker<E: EthSpec>(
kzg,
custody_context,
spec,
true,
)
.expect("should initialise data availability checker")
}
@@ -770,6 +771,36 @@ where
.execution_block_generator()
}
/// Create a switch-to-compounding `ConsolidationRequest` for the given validator.
///
/// Panics if the validator doesn't exist, doesn't have eth1 withdrawal credentials,
/// or doesn't have an execution withdrawal address.
pub fn make_switch_to_compounding_request(
&self,
validator_index: usize,
) -> ConsolidationRequest {
let head = self.chain.canonical_head.cached_head();
let head_state = &head.snapshot.beacon_state;
let validator = head_state
.get_validator(validator_index)
.expect("validator should exist");
assert!(
validator.has_eth1_withdrawal_credential(&self.spec),
"validator {validator_index} should have eth1 withdrawal credentials"
);
let source_address = validator
.get_execution_withdrawal_address(&self.spec)
.expect("validator should have execution withdrawal address");
ConsolidationRequest {
source_address,
source_pubkey: validator.pubkey,
target_pubkey: validator.pubkey,
}
}
pub fn set_mock_builder(
&mut self,
beacon_url: SensitiveUrl,
@@ -1043,6 +1074,13 @@ where
assert_ne!(slot, 0, "can't produce a block at slot 0");
assert!(slot >= state.slot());
// For Gloas forks, delegate to make_block_with_envelope and discard the envelope.
if self.spec.fork_name_at_slot::<E>(slot).gloas_enabled() {
let (block_contents, _envelope, state) =
Box::pin(self.make_block_with_envelope(state, slot)).await;
return (block_contents, state);
}
complete_state_advance(&mut state, None, slot, &self.spec)
.expect("should be able to advance state to slot");
@@ -1095,7 +1133,7 @@ where
}
/// Returns a newly created block, signed by the proposer for the given slot,
/// along with the execution payload envelope (for Gloas) and the pending state.
/// along with the execution payload envelope (for Gloas) and the post-block state.
///
/// For pre-Gloas forks, the envelope is `None` and this behaves like `make_block`.
pub async fn make_block_with_envelope(
@@ -1124,11 +1162,24 @@ where
GraffitiSettings::new(Some(graffiti), Some(GraffitiPolicy::PreserveUserGraffiti));
let randao_reveal = self.sign_randao_reveal(&state, proposer_index, slot);
let (block, pending_state, _consensus_block_value) = self
// Load the parent's payload envelope and status from the cached head.
// TODO(gloas): we may want to pass these as arguments to support cases where we build
// on alternate chains to the head.
let (parent_payload_status, parent_envelope) = {
let head = self.chain.canonical_head.cached_head();
(
head.head_payload_status(),
head.snapshot.execution_envelope.clone(),
)
};
let (block, post_block_state, _consensus_block_value) = self
.chain
.produce_block_on_state_gloas(
state,
None,
parent_payload_status,
parent_envelope,
slot,
randao_reveal,
graffiti_settings,
@@ -1139,8 +1190,8 @@ where
let signed_block = Arc::new(block.sign(
&self.validator_keypairs[proposer_index].sk,
&pending_state.fork(),
pending_state.genesis_validators_root(),
&post_block_state.fork(),
post_block_state.genesis_validators_root(),
&self.spec,
));
@@ -1155,8 +1206,8 @@ where
let domain = self.spec.get_domain(
epoch,
Domain::BeaconBuilder,
&pending_state.fork(),
pending_state.genesis_validators_root(),
&post_block_state.fork(),
post_block_state.genesis_validators_root(),
);
let message = envelope.signing_root(domain);
let signature = self.validator_keypairs[proposer_index].sk.sign(message);
@@ -1167,7 +1218,7 @@ where
});
let block_contents: SignedBlockContentsTuple<E> = (signed_block, None);
(block_contents, signed_envelope, pending_state)
(block_contents, signed_envelope, post_block_state)
} else {
let (block_contents, state) = self.make_block(state, slot).await;
(block_contents, None, state)
@@ -1400,6 +1451,7 @@ where
epoch,
root: target_root,
},
false,
&self.spec,
)?;
@@ -1509,6 +1561,7 @@ where
epoch,
root: target_root,
},
false,
&self.spec,
)?)
}
@@ -2681,32 +2734,27 @@ where
Ok(block_hash)
}
/// Process an execution payload envelope for a Gloas block.
/// Verify and process (with fork choice) an execution payload envelope for a Gloas block.
pub async fn process_envelope(
&self,
block_root: Hash256,
signed_envelope: SignedExecutionPayloadEnvelope<E>,
pending_state: &mut BeaconState<E>,
) -> Hash256 {
let state_root = signed_envelope.message.state_root;
state: &BeaconState<E>,
block_state_root: Hash256,
) {
debug!(
slot = %signed_envelope.message.slot,
?state_root,
slot = %signed_envelope.slot(),
"Processing execution payload envelope"
);
let block_state_root = pending_state
.update_tree_hash_cache()
.expect("should compute pending state root");
state_processing::envelope_processing::process_execution_payload_envelope(
pending_state,
Some(block_state_root),
state_processing::envelope_processing::verify_execution_payload_envelope(
state,
&signed_envelope,
state_processing::VerifySignatures::True,
state_processing::envelope_processing::VerifyStateRoot::True,
block_state_root,
&self.spec,
)
.expect("should process envelope");
.expect("should verify envelope");
// Notify the EL of the new payload so forkchoiceUpdated can reference it.
let block = self
@@ -2747,16 +2795,18 @@ where
// Store the envelope.
self.chain
.store
.put_payload_envelope(&block_root, signed_envelope)
.put_payload_envelope(&block_root, &signed_envelope)
.expect("should store envelope");
// Store the Full state.
// Update fork choice so it knows the payload was received.
self.chain
.store
.put_state(&state_root, pending_state)
.expect("should store full state");
.canonical_head
.fork_choice_write_lock()
.on_valid_payload_envelope_received(block_root)
.expect("should update fork choice with envelope");
state_root
// Run fork choice because the envelope could become the head.
self.chain.recompute_head_at_current_slot().await;
}
/// Builds a `RangeSyncBlock` from a `SignedBeaconBlock` and blobs or data columns retrieved from
@@ -2970,7 +3020,8 @@ where
BlockError,
> {
self.set_current_slot(slot);
let (block_contents, new_state) = self.make_block(state, slot).await;
let (block_contents, opt_envelope, new_state) =
self.make_block_with_envelope(state, slot).await;
let block_hash = self
.process_block(
@@ -2979,6 +3030,12 @@ where
block_contents.clone(),
)
.await?;
if let Some(envelope) = opt_envelope {
let block_state_root = block_contents.0.state_root();
self.process_envelope(block_hash.into(), envelope, &new_state, block_state_root)
.await;
}
Ok((block_hash, block_contents, new_state))
}
@@ -3713,11 +3770,8 @@ pub fn generate_rand_block_and_blobs<E: EthSpec>(
blobs,
} = bundle;
for (index, ((blob, kzg_commitment), kzg_proof)) in blobs
.into_iter()
.zip(commitments.into_iter())
.zip(proofs.into_iter())
.enumerate()
for (index, ((blob, kzg_commitment), kzg_proof)) in
blobs.into_iter().zip(commitments).zip(proofs).enumerate()
{
blob_sidecars.push(BlobSidecar {
index: index as u64,