@@ -38,7 +38,7 @@ use crate::{
38
38
block_times_cache:: BlockTimesCache ,
39
39
events:: ServerSentEventHandler ,
40
40
metrics,
41
- validator_monitor:: { get_slot_delay_ms, timestamp_now } ,
41
+ validator_monitor:: get_slot_delay_ms,
42
42
BeaconChain , BeaconChainError as Error , BeaconChainTypes , BeaconSnapshot ,
43
43
} ;
44
44
use eth2:: types:: { EventKind , SseChainReorg , SseFinalizedCheckpoint , SseHead , SseLateHead } ;
@@ -1287,7 +1287,10 @@ fn observe_head_block_delays<E: EthSpec, S: SlotClock>(
1287
1287
slot_clock : & S ,
1288
1288
event_handler : Option < & ServerSentEventHandler < E > > ,
1289
1289
) {
1290
- let block_time_set_as_head = timestamp_now ( ) ;
1290
+ let Some ( block_time_set_as_head) = slot_clock. now_duration ( ) else {
1291
+ // Practically unreachable: the slot clock's time should not be before the UNIX epoch.
1292
+ return ;
1293
+ } ;
1291
1294
let head_block_root = head_block. root ;
1292
1295
let head_block_slot = head_block. slot ;
1293
1296
let head_block_is_optimistic = head_block. execution_status . is_optimistic_or_invalid ( ) ;
@@ -1308,10 +1311,6 @@ fn observe_head_block_delays<E: EthSpec, S: SlotClock>(
1308
1311
// If a block comes in from over 4 slots ago, it is most likely a block from sync.
1309
1312
let block_from_sync = block_delay_total > slot_clock. slot_duration ( ) * 4 ;
1310
1313
1311
- // Determine whether the block has been set as head too late for proper attestation
1312
- // production.
1313
- let late_head = block_delay_total >= slot_clock. unagg_attestation_production_delay ( ) ;
1314
-
1315
1314
// Do not store metrics if the block was > 4 slots old, this helps prevent noise during
1316
1315
// sync.
1317
1316
if !block_from_sync {
@@ -1410,6 +1409,14 @@ fn observe_head_block_delays<E: EthSpec, S: SlotClock>(
1410
1409
. as_millis ( ) as i64 ,
1411
1410
) ;
1412
1411
1412
+ // Consider the block late if the time it became attestable is after the attestation
1413
+ // deadline. If the block was not made attestable, use the set-as-head time.
1414
+ let attestable_delay = block_delays. attestable . unwrap_or ( block_delay_total) ;
1415
+
1416
+ // Determine whether the block has been set as head too late for proper attestation
1417
+ // production.
1418
+ let late_head = attestable_delay >= slot_clock. unagg_attestation_production_delay ( ) ;
1419
+
1413
1420
// If the block was enshrined as head too late for attestations to be created for it,
1414
1421
// log a debug warning and increment a metric.
1415
1422
let format_delay = |delay : & Option < Duration > | {
@@ -1432,6 +1439,24 @@ fn observe_head_block_delays<E: EthSpec, S: SlotClock>(
1432
1439
set_as_head_time_ms = format_delay( & block_delays. set_as_head) ,
1433
1440
"Delayed head block"
1434
1441
) ;
1442
+ if let Some ( event_handler) = event_handler {
1443
+ if event_handler. has_late_head_subscribers ( ) {
1444
+ let peer_info = block_times_cache. get_peer_info ( head_block_root) ;
1445
+ event_handler. register ( EventKind :: LateHead ( SseLateHead {
1446
+ slot : head_block_slot,
1447
+ block : head_block_root,
1448
+ peer_id : peer_info. id ,
1449
+ peer_client : peer_info. client ,
1450
+ proposer_index : head_block_proposer_index,
1451
+ proposer_graffiti : head_block_graffiti,
1452
+ block_delay : block_delay_total,
1453
+ observed_delay : block_delays. observed ,
1454
+ imported_delay : block_delays. imported ,
1455
+ set_as_head_delay : block_delays. set_as_head ,
1456
+ execution_optimistic : head_block_is_optimistic,
1457
+ } ) ) ;
1458
+ }
1459
+ }
1435
1460
} else {
1436
1461
debug ! (
1437
1462
block_root = ?head_block_root,
@@ -1450,29 +1475,4 @@ fn observe_head_block_delays<E: EthSpec, S: SlotClock>(
1450
1475
) ;
1451
1476
}
1452
1477
}
1453
-
1454
- if let Some ( event_handler) = event_handler {
1455
- if !block_from_sync && late_head && event_handler. has_late_head_subscribers ( ) {
1456
- let peer_info = block_times_cache. get_peer_info ( head_block_root) ;
1457
- let block_delays = block_times_cache. get_block_delays (
1458
- head_block_root,
1459
- slot_clock
1460
- . start_of ( head_block_slot)
1461
- . unwrap_or_else ( || Duration :: from_secs ( 0 ) ) ,
1462
- ) ;
1463
- event_handler. register ( EventKind :: LateHead ( SseLateHead {
1464
- slot : head_block_slot,
1465
- block : head_block_root,
1466
- peer_id : peer_info. id ,
1467
- peer_client : peer_info. client ,
1468
- proposer_index : head_block_proposer_index,
1469
- proposer_graffiti : head_block_graffiti,
1470
- block_delay : block_delay_total,
1471
- observed_delay : block_delays. observed ,
1472
- imported_delay : block_delays. imported ,
1473
- set_as_head_delay : block_delays. set_as_head ,
1474
- execution_optimistic : head_block_is_optimistic,
1475
- } ) ) ;
1476
- }
1477
- }
1478
1478
}
0 commit comments