Merge remote-tracking branch 'origin/unstable' into gloas-walk-always

This commit is contained in:
Michael Sproul
2026-03-26 10:07:46 +11:00
26 changed files with 1781 additions and 17 deletions

View File

@@ -377,6 +377,16 @@ impl<E: EthSpec, Payload: AbstractExecPayload<E>> SignedBeaconBlock<E, Payload>
.map(|bid| bid.message.block_hash)
}
/// Convenience accessor for the block's bid's `parent_block_hash`.
///
/// This method returns an error prior to Gloas.
pub fn payload_bid_parent_block_hash(&self) -> Result<ExecutionBlockHash, BeaconStateError> {
self.message()
.body()
.signed_execution_payload_bid()
.map(|bid| bid.message.parent_block_hash)
}
/// Check if the `parent_hash` in this block's `signed_payload_bid` matches `parent_block_hash`.
///
/// This function is useful post-Gloas for determining if the parent block is full, *without*

View File

@@ -295,6 +295,7 @@ pub struct ChainSpec {
/*
* Networking Gloas
*/
pub max_request_payloads: u64,
/*
* Networking Derived
@@ -305,6 +306,7 @@ pub struct ChainSpec {
pub max_blocks_by_root_request_deneb: usize,
pub max_blobs_by_root_request: usize,
pub max_data_columns_by_root_request: usize,
pub max_payload_envelopes_by_root_request: usize,
/*
* Application params
@@ -700,6 +702,10 @@ impl ChainSpec {
}
}
pub fn max_request_payloads(&self) -> usize {
self.max_request_payloads as usize
}
pub fn max_request_blob_sidecars(&self, fork_name: ForkName) -> usize {
if fork_name.electra_enabled() {
self.max_request_blob_sidecars_electra as usize
@@ -964,6 +970,8 @@ impl ChainSpec {
max_blobs_by_root_request_common(self.max_request_blob_sidecars);
self.max_data_columns_by_root_request =
max_data_columns_by_root_request_common::<E>(self.max_request_blocks_deneb);
self.max_payload_envelopes_by_root_request =
max_blocks_by_root_request_common(self.max_request_payloads);
self
}
@@ -1228,6 +1236,7 @@ impl ChainSpec {
builder_payment_threshold_numerator: 6,
builder_payment_threshold_denominator: 10,
min_builder_withdrawability_delay: Epoch::new(4096),
max_request_payloads: 128,
/*
* Network specific
@@ -1293,6 +1302,7 @@ impl ChainSpec {
min_epochs_for_data_column_sidecars_requests:
default_min_epochs_for_data_column_sidecars_requests(),
max_data_columns_by_root_request: default_data_columns_by_root_request(),
max_payload_envelopes_by_root_request: default_max_payload_envelopes_by_root_request(),
/*
* Application specific
@@ -1622,6 +1632,7 @@ impl ChainSpec {
builder_payment_threshold_numerator: 6,
builder_payment_threshold_denominator: 10,
min_builder_withdrawability_delay: Epoch::new(4096),
max_request_payloads: 128,
/*
* Network specific
@@ -1678,6 +1689,7 @@ impl ChainSpec {
min_epochs_for_data_column_sidecars_requests:
default_min_epochs_for_data_column_sidecars_requests(),
max_data_columns_by_root_request: default_data_columns_by_root_request(),
max_payload_envelopes_by_root_request: default_max_payload_envelopes_by_root_request(),
/*
* Application specific
@@ -2342,6 +2354,14 @@ fn default_data_columns_by_root_request() -> usize {
max_data_columns_by_root_request_common::<MainnetEthSpec>(default_max_request_blocks_deneb())
}
fn default_max_payload_envelopes_by_root_request() -> usize {
max_blocks_by_root_request_common(default_max_request_payloads())
}
fn default_max_request_payloads() -> u64 {
128
}
impl Default for Config {
fn default() -> Self {
let chain_spec = MainnetEthSpec::default_spec();

View File

@@ -3,7 +3,9 @@ use crate::test_utils::TestRandom;
use crate::{EthSpec, ForkName, Hash256, SignedRoot, Slot};
use context_deserialize::context_deserialize;
use educe::Educe;
use fixed_bytes::FixedBytesExtended;
use serde::{Deserialize, Serialize};
use ssz::{BYTES_PER_LENGTH_OFFSET, Encode as SszEncode};
use ssz_derive::{Decode, Encode};
use test_random_derive::TestRandom;
use tree_hash_derive::TreeHash;
@@ -22,6 +24,44 @@ pub struct ExecutionPayloadEnvelope<E: EthSpec> {
pub state_root: Hash256,
}
impl<E: EthSpec> ExecutionPayloadEnvelope<E> {
/// Returns an empty envelope with all fields zeroed. Used for SSZ size calculations.
pub fn empty() -> Self {
Self {
payload: ExecutionPayloadGloas::default(),
execution_requests: ExecutionRequests::default(),
builder_index: 0,
beacon_block_root: Hash256::zero(),
slot: Slot::new(0),
state_root: Hash256::zero(),
}
}
/// Returns the minimum SSZ-encoded size (all variable-length fields empty).
pub fn min_size() -> usize {
Self::empty().as_ssz_bytes().len()
}
/// Returns the maximum SSZ-encoded size.
#[allow(clippy::arithmetic_side_effects)]
pub fn max_size() -> usize {
Self::min_size()
// ExecutionPayloadGloas variable-length fields:
+ (E::max_extra_data_bytes() * <u8 as SszEncode>::ssz_fixed_len())
+ (E::max_transactions_per_payload()
* (BYTES_PER_LENGTH_OFFSET + E::max_bytes_per_transaction()))
+ (E::max_withdrawals_per_payload()
* <crate::Withdrawal as SszEncode>::ssz_fixed_len())
// ExecutionRequests variable-length fields:
+ (E::max_deposit_requests_per_payload()
* <crate::DepositRequest as SszEncode>::ssz_fixed_len())
+ (E::max_withdrawal_requests_per_payload()
* <crate::WithdrawalRequest as SszEncode>::ssz_fixed_len())
+ (E::max_consolidation_requests_per_payload()
* <crate::ConsolidationRequest as SszEncode>::ssz_fixed_len())
}
}
impl<E: EthSpec> SignedRoot for ExecutionPayloadEnvelope<E> {}
#[cfg(test)]

View File

@@ -8,6 +8,7 @@ use bls::{PublicKey, Signature};
use context_deserialize::context_deserialize;
use educe::Educe;
use serde::{Deserialize, Serialize};
use ssz::Encode;
use ssz_derive::{Decode, Encode};
use test_random_derive::TestRandom;
use tree_hash_derive::TreeHash;
@@ -22,6 +23,24 @@ pub struct SignedExecutionPayloadEnvelope<E: EthSpec> {
}
impl<E: EthSpec> SignedExecutionPayloadEnvelope<E> {
/// Returns the minimum SSZ-encoded size (all variable-length fields empty).
pub fn min_size() -> usize {
Self {
message: ExecutionPayloadEnvelope::empty(),
signature: Signature::empty(),
}
.as_ssz_bytes()
.len()
}
/// Returns the maximum SSZ-encoded size.
#[allow(clippy::arithmetic_side_effects)]
pub fn max_size() -> usize {
// Signature is fixed-size, so the variable-length delta is entirely from the envelope.
Self::min_size() + ExecutionPayloadEnvelope::<E>::max_size()
- ExecutionPayloadEnvelope::<E>::min_size()
}
pub fn slot(&self) -> Slot {
self.message.slot
}