mirror of
https://github.com/sigp/lighthouse.git
synced 2026-07-01 20:04:41 +00:00
Add timing for block availability (#5510)
* Add timing for block availability * Attestation metrics analysis * Prettier printing * Add some metrics and timings to track late blocks * Update to latest unstable * fmt * Merge latest unstable * Small tweaks * Try pushing blob timing down into verification * Simplify for clippy
This commit is contained in:
@@ -2953,7 +2953,7 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
}
|
||||
|
||||
/// Wraps `process_block` in logic to cache the block's commitments in the processing cache
|
||||
/// and evict if the block was imported or erred.
|
||||
/// and evict if the block was imported or errored.
|
||||
pub async fn process_block_with_early_caching<B: IntoExecutionPendingBlock<T>>(
|
||||
self: &Arc<Self>,
|
||||
block_root: Hash256,
|
||||
@@ -2998,22 +2998,20 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
// Increment the Prometheus counter for block processing requests.
|
||||
metrics::inc_counter(&metrics::BLOCK_PROCESSING_REQUESTS);
|
||||
|
||||
let block_slot = unverified_block.block().slot();
|
||||
|
||||
// Set observed time if not already set. Usually this should be set by gossip or RPC,
|
||||
// but just in case we set it again here (useful for tests).
|
||||
if let (Some(seen_timestamp), Some(current_slot)) =
|
||||
(self.slot_clock.now_duration(), self.slot_clock.now())
|
||||
{
|
||||
if let Some(seen_timestamp) = self.slot_clock.now_duration() {
|
||||
self.block_times_cache.write().set_time_observed(
|
||||
block_root,
|
||||
current_slot,
|
||||
block_slot,
|
||||
seen_timestamp,
|
||||
None,
|
||||
None,
|
||||
);
|
||||
}
|
||||
|
||||
let block_slot = unverified_block.block().slot();
|
||||
|
||||
// A small closure to group the verification and import errors.
|
||||
let chain = self.clone();
|
||||
let import_block = async move {
|
||||
@@ -3024,6 +3022,15 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
)?;
|
||||
publish_fn()?;
|
||||
let executed_block = chain.into_executed_block(execution_pending).await?;
|
||||
// Record the time it took to ask the execution layer.
|
||||
if let Some(seen_timestamp) = self.slot_clock.now_duration() {
|
||||
self.block_times_cache.write().set_execution_time(
|
||||
block_root,
|
||||
block_slot,
|
||||
seen_timestamp,
|
||||
)
|
||||
}
|
||||
|
||||
match executed_block {
|
||||
ExecutedBlock::Available(block) => {
|
||||
self.import_available_block(Box::new(block)).await
|
||||
@@ -3090,8 +3097,8 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
}
|
||||
}
|
||||
|
||||
/// Accepts a fully-verified block and awaits on it's payload verification handle to
|
||||
/// get a fully `ExecutedBlock`
|
||||
/// Accepts a fully-verified block and awaits on its payload verification handle to
|
||||
/// get a fully `ExecutedBlock`.
|
||||
///
|
||||
/// An error is returned if the verification handle couldn't be awaited.
|
||||
pub async fn into_executed_block(
|
||||
@@ -3224,10 +3231,6 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
) -> Result<AvailabilityProcessingStatus, BlockError<T::EthSpec>> {
|
||||
match availability {
|
||||
Availability::Available(block) => {
|
||||
// This is the time since start of the slot where all the components of the block have become available
|
||||
let delay =
|
||||
get_slot_delay_ms(timestamp_now(), block.block.slot(), &self.slot_clock);
|
||||
metrics::observe_duration(&metrics::BLOCK_AVAILABILITY_DELAY, delay);
|
||||
// Block is fully available, import into fork choice
|
||||
self.import_available_block(block).await
|
||||
}
|
||||
@@ -3256,6 +3259,15 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
consensus_context,
|
||||
} = import_data;
|
||||
|
||||
// Record the time at which this block's blobs became available.
|
||||
if let Some(blobs_available) = block.blobs_available_timestamp() {
|
||||
self.block_times_cache.write().set_time_blob_observed(
|
||||
block_root,
|
||||
block.slot(),
|
||||
blobs_available,
|
||||
);
|
||||
}
|
||||
|
||||
// import
|
||||
let chain = self.clone();
|
||||
let block_root = self
|
||||
@@ -3396,6 +3408,14 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
"Early attester cache insert failed";
|
||||
"error" => ?e
|
||||
);
|
||||
} else {
|
||||
let attestable_timestamp =
|
||||
self.slot_clock.now_duration().unwrap_or_default();
|
||||
self.block_times_cache.write().set_time_attestable(
|
||||
block_root,
|
||||
signed_block.slot(),
|
||||
attestable_timestamp,
|
||||
)
|
||||
}
|
||||
} else {
|
||||
warn!(
|
||||
@@ -3885,25 +3905,6 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
);
|
||||
}
|
||||
|
||||
// Do not store metrics if the block was > 4 slots old, this helps prevent noise during
|
||||
// sync.
|
||||
if block_delay_total < self.slot_clock.slot_duration() * 4 {
|
||||
// Observe the delay between when we observed the block and when we imported it.
|
||||
let block_delays = self.block_times_cache.read().get_block_delays(
|
||||
block_root,
|
||||
self.slot_clock
|
||||
.start_of(current_slot)
|
||||
.unwrap_or_else(|| Duration::from_secs(0)),
|
||||
);
|
||||
|
||||
metrics::observe_duration(
|
||||
&metrics::BEACON_BLOCK_IMPORTED_OBSERVED_DELAY_TIME,
|
||||
block_delays
|
||||
.imported
|
||||
.unwrap_or_else(|| Duration::from_secs(0)),
|
||||
);
|
||||
}
|
||||
|
||||
if let Some(event_handler) = self.event_handler.as_ref() {
|
||||
if event_handler.has_block_subscribers() {
|
||||
event_handler.register(EventKind::Block(SseBlock {
|
||||
|
||||
Reference in New Issue
Block a user