@@ -542,6 +542,9 @@ typedef struct {
542
542
fd_histf_t first_microblock_delay [ 1 ];
543
543
fd_histf_t slot_done_delay [ 1 ];
544
544
fd_histf_t bundle_init_delay [ 1 ];
545
+
546
+ ulong features_activation_avail ;
547
+ fd_shred_features_activation_t features_activation [1 ];
545
548
} fd_poh_ctx_t ;
546
549
547
550
/* The PoH recorder is implemented in Firedancer but for now needs to
@@ -1224,7 +1227,10 @@ no_longer_leader( fd_poh_ctx_t * ctx ) {
1224
1227
CALLED_FROM_RUST void
1225
1228
fd_ext_poh_reset ( ulong completed_bank_slot , /* The slot that successfully produced a block */
1226
1229
uchar const * reset_blockhash , /* The hash of the last tick in the produced block */
1227
- ulong hashcnt_per_tick /* The hashcnt per tick of the bank that completed */ ) {
1230
+ ulong hashcnt_per_tick , /* The hashcnt per tick of the bank that completed */
1231
+ uchar const * parent_block_id , /* The block id of the parent block */
1232
+ ulong const * features_activation /* The activation slot of shred-tile features */ ) {
1233
+ (void )parent_block_id ;
1228
1234
fd_poh_ctx_t * ctx = fd_ext_poh_write_lock ();
1229
1235
1230
1236
ulong slot_before_reset = ctx -> slot ;
@@ -1316,6 +1322,16 @@ fd_ext_poh_reset( ulong completed_bank_slot, /* The slot that successful
1316
1322
if ( FD_UNLIKELY ( leader_before_reset ) ) publish_plugin_slot_end ( ctx , slot_before_reset , ctx -> cus_used );
1317
1323
}
1318
1324
1325
+ /* There is a subset of FD_SHRED_FEATURES_ACTIVATION_... slots that
1326
+ the shred tile needs to be aware of. Since their computation
1327
+ requires the bank, we are forced (so far) to receive them here
1328
+ from the Rust side, before forwarding them to the shred tile as
1329
+ POH_PKT_TYPE_FEAT_ACT_SLOT. This is not elegant, and it should
1330
+ be revised in the future (TODO), but it provides a "temporary"
1331
+ working solution to handle features activation. */
1332
+ fd_memcpy ( ctx -> features_activation -> slots , features_activation , sizeof (fd_shred_features_activation_t ) );
1333
+ ctx -> features_activation_avail = 1UL ;
1334
+
1319
1335
fd_ext_poh_write_unlock ();
1320
1336
}
1321
1337
@@ -1403,6 +1419,21 @@ publish_tick( fd_poh_ctx_t * ctx,
1403
1419
}
1404
1420
}
1405
1421
1422
+ static inline void
1423
+ publish_features_activation ( fd_poh_ctx_t * ctx ,
1424
+ fd_stem_context_t * stem ) {
1425
+ uchar * dst = (uchar * )fd_chunk_to_laddr ( ctx -> shred_out -> mem , ctx -> shred_out -> chunk );
1426
+ fd_shred_features_activation_t * act_data = (fd_shred_features_activation_t * )dst ;
1427
+ fd_memcpy ( act_data , ctx -> features_activation , sizeof (fd_shred_features_activation_t ) );
1428
+
1429
+ ulong tspub = (ulong )fd_frag_meta_ts_comp ( fd_tickcount () );
1430
+ ulong sz = sizeof (fd_shred_features_activation_t );
1431
+ ulong sig = fd_disco_poh_sig ( ctx -> slot , POH_PKT_TYPE_FEAT_ACT_SLOT , 0UL );
1432
+ fd_stem_publish ( stem , ctx -> shred_out -> idx , sig , ctx -> shred_out -> chunk , sz , 0UL , 0UL , tspub );
1433
+ ctx -> shred_seq = stem -> seqs [ ctx -> shred_out -> idx ];
1434
+ ctx -> shred_out -> chunk = fd_dcache_compact_next ( ctx -> shred_out -> chunk , sz , ctx -> shred_out -> chunk0 , ctx -> shred_out -> wmark );
1435
+ }
1436
+
1406
1437
static inline void
1407
1438
after_credit ( fd_poh_ctx_t * ctx ,
1408
1439
fd_stem_context_t * stem ,
@@ -1426,6 +1457,14 @@ after_credit( fd_poh_ctx_t * ctx,
1426
1457
}
1427
1458
FD_COMPILER_MFENCE ();
1428
1459
1460
+ if ( FD_UNLIKELY ( ctx -> features_activation_avail ) ) {
1461
+ /* If we have received an update on features_activation, then
1462
+ forward them to the shred tile. In principle, this should
1463
+ happen at most once per slot. */
1464
+ publish_features_activation ( ctx , stem );
1465
+ ctx -> features_activation_avail = 0UL ;
1466
+ }
1467
+
1429
1468
int is_leader = ctx -> next_leader_slot != ULONG_MAX && ctx -> slot >=ctx -> next_leader_slot ;
1430
1469
if ( FD_UNLIKELY ( is_leader && !ctx -> current_leader_bank ) ) {
1431
1470
/* If we are the leader, but we didn't yet learn what the leader
@@ -2272,14 +2311,18 @@ unprivileged_init( fd_topo_t * topo,
2272
2311
* ctx -> plugin_out = out1 ( topo , tile , "poh_plugin" );
2273
2312
}
2274
2313
2314
+ ctx -> features_activation_avail = 0UL ;
2315
+ for ( ulong i = 0UL ; i < FD_SHRED_FEATURES_ACTIVATION_SLOT_CNT ; i ++ )
2316
+ ctx -> features_activation -> slots [i ] = FD_SHRED_FEATURES_ACTIVATION_SLOT_DISABLED ;
2317
+
2275
2318
ulong scratch_top = FD_SCRATCH_ALLOC_FINI ( l , 1UL );
2276
2319
if ( FD_UNLIKELY ( scratch_top > (ulong )scratch + scratch_footprint ( tile ) ) )
2277
2320
FD_LOG_ERR (( "scratch overflow %lu %lu %lu" , scratch_top - (ulong )scratch - scratch_footprint ( tile ), scratch_top , (ulong )scratch + scratch_footprint ( tile ) ));
2278
2321
}
2279
2322
2280
2323
/* One tick, one microblock, one plugin slot end, one plugin slot start,
2281
- and one leader update. */
2282
- #define STEM_BURST (5UL )
2324
+ one leader update, and one features activation . */
2325
+ #define STEM_BURST (6UL )
2283
2326
2284
2327
/* See explanation in fd_pack */
2285
2328
#define STEM_LAZY (128L*3000L)
0 commit comments