Skip to content

Commit 2f6368c

Browse files
committed
wip 2
1 parent 29ab04d commit 2f6368c

6 files changed

Lines changed: 320 additions & 297 deletions

File tree

crates/consensus/src/follow/engine.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,6 @@ impl<TUpstream> Config<TUpstream> {
164164
.clone(),
165165
marshal: marshal_mailbox.clone(),
166166
epoch_strategy: epoch_strategy.clone(),
167-
floor: last_finalized_height,
168167
fcu_heartbeat_interval: self.fcu_heartbeat_interval,
169168
},
170169
);

crates/consensus/src/follow/executor/actor.rs

Lines changed: 58 additions & 109 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ use tracing::{Level, debug, error, instrument};
2525

2626
use super::{
2727
Config, ExecutionEngine, FinalizedBlockProvider, Marshal,
28-
fcu::{ForkchoiceTargets, ForkchoiceTracker, Target},
28+
fcu::{BlockForkchoice, FinalityPlan, ForkchoiceTargets, ForkchoiceTracker},
2929
ingress::Message,
3030
};
3131
use crate::{consensus::block::Block, utils::OptionFuture};
@@ -41,7 +41,6 @@ pub(crate) struct Actor<TContext, P, E, M = crate::alias::marshal::Mailbox> {
4141
marshal: M,
4242

4343
epoch_strategy: FixedEpocher,
44-
floor: Height,
4544

4645
forkchoice: ForkchoiceTracker,
4746

@@ -71,22 +70,20 @@ where
7170
execution_engine,
7271
marshal,
7372
epoch_strategy,
74-
floor,
7573
fcu_heartbeat_interval,
7674
} = config;
7775

7876
let finalized_header = execution_provider
7977
.finalized_header()
8078
.expect("failed reading finalized execution header");
81-
let forkchoice = ForkchoiceTracker::new(Target::from_header(&finalized_header));
79+
let forkchoice = ForkchoiceTracker::new(&finalized_header);
8280

8381
Self {
8482
context: ContextCell::new(context),
8583

8684
mailbox,
8785
marshal,
8886
epoch_strategy,
89-
floor,
9087
execution_provider,
9188
execution_engine,
9289

@@ -118,15 +115,15 @@ where
118115
result = &mut self.execution_task => {
119116
self.execution_task = OptionFuture::none();
120117
match result {
121-
ExecutionTaskResult::Completed(submitted_fcu) => {
118+
Ok(submitted_fcu) => {
122119
if let Some(submitted_fcu) = submitted_fcu {
123120
self.forkchoice.note_submitted(submitted_fcu);
124121
}
125122

126123
// Emits an event on error.
127124
let _: Result<_, _> = self.try_advance_floor().await;
128125
}
129-
ExecutionTaskResult::Fatal(error) => {
126+
Err(error) => {
130127
error!(%error, "execution task failed");
131128
break;
132129
}
@@ -149,12 +146,10 @@ where
149146
if self.floor_candidate.is_none() {
150147
self.floor_candidate = Some(height);
151148
}
152-
self.forkchoice
153-
.advance_head(Target::from_finalization(round, digest));
149+
self.forkchoice.observe_certificate(round, digest);
154150
}
155151
Message::Finalization { round, digest } => {
156-
let candidate = Target::from_finalization(round, digest);
157-
self.forkchoice.advance_head(candidate);
152+
self.forkchoice.observe_certificate(round, digest);
158153
}
159154
}
160155
}
@@ -182,33 +177,19 @@ where
182177
return;
183178
}
184179

185-
let request = if let Some((block, ack)) = self.block_queue.pop_front() {
186-
let block_target = Target::from_block(&block);
187-
let finality_anchor =
188-
self.forkchoice
189-
.advance_finalized(block_target)
190-
.then_some(ForkchoiceTargets {
191-
head: block_target,
192-
finalized: block_target,
193-
});
194-
let latest_forkchoice = (self.forkchoice.requires_update() || heartbeat)
195-
.then_some(self.forkchoice.latest());
196-
ExecutionRequest::Block {
197-
block,
198-
latest_forkchoice,
199-
finality_anchor,
200-
ack,
201-
}
202-
} else if self.forkchoice.requires_update() || heartbeat {
203-
ExecutionRequest::Forkchoice(self.forkchoice.latest())
180+
let execution_engine = self.execution_engine.clone();
181+
let task = if let Some((block, ack)) = self.block_queue.pop_front() {
182+
let forkchoice = self.forkchoice.plan_block(&block, heartbeat);
183+
let context = self.context.child("execute_block");
184+
execute_block(context, execution_engine, block, forkchoice, ack).boxed()
185+
} else if let Some(forkchoice) = self.forkchoice.plan_update(heartbeat) {
186+
let context = self.context.child("execute_head_update");
187+
execute_head_update(context, execution_engine, forkchoice).boxed()
204188
} else {
205189
return;
206190
};
207191

208-
let context = self.context.child("execute_request");
209-
let execution_engine = self.execution_engine.clone();
210-
self.execution_task
211-
.replace(execute_request(context, execution_engine, request).boxed());
192+
self.execution_task.replace(task);
212193
}
213194

214195
#[instrument(skip_all, err(level = Level::WARN))]
@@ -253,103 +234,73 @@ where
253234

254235
self.marshal.set_floor(finalization);
255236

256-
self.floor = floor_height;
257237
self.floor_candidate = None;
258238

259239
Ok(())
260240
}
261241
}
262242

263-
enum ExecutionRequest {
264-
Forkchoice(ForkchoiceTargets),
265-
Block {
266-
/// A finalized block delivered by marshal for execution.
267-
block: Block,
268-
/// The latest combined head and finalized targets, if an update is due.
269-
latest_forkchoice: Option<ForkchoiceTargets>,
270-
/// The delivered block as both head and finalized when it advances finality.
271-
finality_anchor: Option<ForkchoiceTargets>,
272-
/// Signals marshal after the payload and required forkchoice update complete.
273-
ack: Exact,
274-
},
275-
}
276-
277-
enum ExecutionTaskResult {
278-
Completed(Option<ForkchoiceTargets>),
279-
Fatal(Report),
280-
}
243+
type ExecutionTaskResult = eyre::Result<Option<ForkchoiceTargets>>;
281244

282245
enum ForkchoiceOutcome {
283246
Valid,
284247
Syncing,
285248
}
286249

287-
async fn execute_request<TContext: Pacer, E: ExecutionEngine + 'static>(
250+
async fn execute_head_update<TContext: Pacer, E: ExecutionEngine + 'static>(
288251
context: TContext,
289252
execution_engine: E,
290-
request: ExecutionRequest,
253+
forkchoice: ForkchoiceTargets,
291254
) -> ExecutionTaskResult {
292-
match request {
293-
ExecutionRequest::Forkchoice(forkchoice) => {
294-
let result = submit_forkchoice_update(&context, &execution_engine, &forkchoice).await;
295-
match result {
296-
Ok(ForkchoiceOutcome::Valid | ForkchoiceOutcome::Syncing) => {
297-
ExecutionTaskResult::Completed(Some(forkchoice))
298-
}
299-
Err(error) => ExecutionTaskResult::Fatal(error),
300-
}
255+
submit_forkchoice_update(&context, &execution_engine, &forkchoice).await?;
256+
Ok(Some(forkchoice))
257+
}
258+
259+
async fn execute_block<TContext: Pacer, E: ExecutionEngine + 'static>(
260+
context: TContext,
261+
execution_engine: E,
262+
block: Block,
263+
forkchoice: BlockForkchoice,
264+
ack: Exact,
265+
) -> ExecutionTaskResult {
266+
submit_new_payload(&context, &execution_engine, block).await?;
267+
268+
let submitted = match forkchoice {
269+
BlockForkchoice::Guide(targets) => {
270+
submit_forkchoice_update(&context, &execution_engine, &targets).await?;
271+
Some(targets)
301272
}
302-
ExecutionRequest::Block {
303-
block,
304-
latest_forkchoice,
305-
finality_anchor,
306-
ack,
307-
} => {
308-
if let Err(error) = submit_new_payload(&context, &execution_engine, block).await {
309-
return ExecutionTaskResult::Fatal(error);
310-
}
273+
BlockForkchoice::Finalize(plan) => {
274+
Some(apply_finality(&context, &execution_engine, plan).await?)
275+
}
276+
BlockForkchoice::None => None,
277+
};
311278

312-
let submitted_fcu = match latest_forkchoice {
313-
Some(latest_forkchoice) => {
314-
let result =
315-
submit_forkchoice_update(&context, &execution_engine, &latest_forkchoice)
316-
.await;
317-
match result {
318-
Ok(ForkchoiceOutcome::Valid) => Some(latest_forkchoice),
319-
Ok(ForkchoiceOutcome::Syncing) => match finality_anchor {
320-
Some(finality_anchor) => {
321-
if let Err(error) = submit_finality_anchor(
322-
&context,
323-
&execution_engine,
324-
&finality_anchor,
325-
)
326-
.await
327-
{
328-
return ExecutionTaskResult::Fatal(error);
329-
}
330-
Some(finality_anchor)
331-
}
332-
None => Some(latest_forkchoice),
333-
},
334-
Err(error) => return ExecutionTaskResult::Fatal(error),
335-
}
336-
}
337-
None => None,
338-
};
279+
ack.acknowledge();
280+
Ok(submitted)
281+
}
339282

340-
ack.acknowledge();
341-
ExecutionTaskResult::Completed(submitted_fcu)
283+
async fn apply_finality<TContext: Pacer, E: ExecutionEngine + ?Sized>(
284+
context: &TContext,
285+
execution_engine: &E,
286+
plan: FinalityPlan,
287+
) -> eyre::Result<ForkchoiceTargets> {
288+
match submit_forkchoice_update(context, execution_engine, &plan.preferred).await? {
289+
ForkchoiceOutcome::Valid => Ok(plan.preferred),
290+
ForkchoiceOutcome::Syncing => {
291+
submit_until_valid(context, execution_engine, &plan.anchor).await?;
292+
Ok(plan.anchor)
342293
}
343294
}
344295
}
345296

346-
async fn submit_finality_anchor<TContext: Pacer, E: ExecutionEngine + ?Sized>(
297+
async fn submit_until_valid<TContext: Pacer, E: ExecutionEngine + ?Sized>(
347298
context: &TContext,
348299
execution_engine: &E,
349-
finality_anchor: &ForkchoiceTargets,
300+
forkchoice: &ForkchoiceTargets,
350301
) -> eyre::Result<()> {
351302
loop {
352-
let outcome = submit_forkchoice_update(context, execution_engine, finality_anchor).await?;
303+
let outcome = submit_forkchoice_update(context, execution_engine, forkchoice).await?;
353304
match outcome {
354305
ForkchoiceOutcome::Valid => return Ok(()),
355306
ForkchoiceOutcome::Syncing => {
@@ -397,10 +348,8 @@ async fn submit_new_payload<TContext: Pacer, E: ExecutionEngine + ?Sized>(
397348
#[instrument(
398349
skip_all,
399350
fields(
400-
head.round = ?forkchoice.head.round,
401-
head.digest = %forkchoice.head.digest,
402-
finalized.round = ?forkchoice.finalized.round,
403-
finalized.digest = %forkchoice.finalized.digest,
351+
head.digest = %forkchoice.head,
352+
finalized.digest = %forkchoice.finalized,
404353
)
405354
)]
406355
async fn submit_forkchoice_update<TContext: Pacer, E: ExecutionEngine + ?Sized>(

0 commit comments

Comments
 (0)