Skip to content

Commit 4cab472

Browse files
committed
fix: remove arc and clones
1 parent 0078625 commit 4cab472

File tree

7 files changed

+136
-19
lines changed

7 files changed

+136
-19
lines changed

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,3 +65,4 @@ tokio = { version = "1.36.0", features = ["full", "macros", "rt-multi-thread"] }
6565
async-trait = "0.1.80"
6666
oauth2 = "4.4.2"
6767
chrono = "0.4.41"
68+
tokio-stream = "0.1.17"

bin/builder.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@ use builder::{
66
use init4_bin_base::{deps::tracing, utils::from_env::FromEnv};
77
use signet_sim::SimCache;
88
use signet_types::constants::SignetSystemConstants;
9-
use std::sync::Arc;
109
use tokio::select;
1110
use tracing::info_span;
1211

@@ -44,12 +43,12 @@ async fn main() -> eyre::Result<()> {
4443
let sim_items = SimCache::new();
4544
let slot_calculator = config.slot_calculator;
4645

47-
let sim = Arc::new(Simulator::new(&config, ru_provider.clone(), slot_calculator));
46+
let sim = Simulator::new(&config, ru_provider.clone(), slot_calculator);
4847

4948
let (basefee_jh, sim_cache_jh) =
5049
sim.spawn_cache_tasks(tx_receiver, bundle_receiver, sim_items.clone());
5150

52-
let build_jh = sim.clone().spawn_simulator_task(constants, sim_items.clone(), submit_channel);
51+
let build_jh = sim.spawn_simulator_task(constants, sim_items.clone(), submit_channel);
5352

5453
let server = serve_builder(([0, 0, 0, 0], config.builder_port));
5554

src/config.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,12 @@ use oauth2::url;
2020
use signet_zenith::Zenith;
2121
use std::borrow::Cow;
2222

23+
/// Type alias for the provider used to simulate against rollup state.
24+
pub type RuProvider = RootProvider<Ethereum>;
25+
26+
/// A [`Zenith`] contract instance using [`Provider`] as the provider.
27+
pub type ZenithInstance<P = HostProvider> = Zenith::ZenithInstance<(), P, alloy::network::Ethereum>;
28+
2329
/// Type alias for the provider used to build and submit blocks to the host.
2430
pub type HostProvider = FillProvider<
2531
JoinFill<
@@ -158,12 +164,6 @@ pub struct BuilderConfig {
158164
pub slot_calculator: SlotCalculator,
159165
}
160166

161-
/// Type alias for the provider used to simulate against rollup state.
162-
pub type RuProvider = RootProvider<Ethereum>;
163-
164-
/// A [`Zenith`] contract instance using [`Provider`] as the provider.
165-
pub type ZenithInstance<P = HostProvider> = Zenith::ZenithInstance<(), P, alloy::network::Ethereum>;
166-
167167
impl BuilderConfig {
168168
/// Connect to the Builder signer.
169169
pub async fn connect_builder_signer(&self) -> Result<LocalOrAws, SignerError> {

src/tasks/block/sim.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -202,12 +202,12 @@ impl Simulator {
202202
///
203203
/// A `JoinHandle` for the spawned task.
204204
pub fn spawn_simulator_task(
205-
self: Arc<Self>,
205+
self,
206206
constants: SignetSystemConstants,
207207
cache: SimCache,
208208
submit_sender: mpsc::UnboundedSender<BuiltBlock>,
209209
) -> JoinHandle<()> {
210-
debug!("starting builder task");
210+
debug!("starting simulator task");
211211

212212
tokio::spawn(async move { self.run_simulator(constants, cache, submit_sender).await })
213213
}
@@ -227,7 +227,7 @@ impl Simulator {
227227
/// - `cache`: The simulation cache containing transactions and bundles.
228228
/// - `submit_sender`: A channel sender used to submit built blocks.
229229
async fn run_simulator(
230-
self: Arc<Self>,
230+
self,
231231
constants: SignetSystemConstants,
232232
cache: SimCache,
233233
submit_sender: mpsc::UnboundedSender<BuiltBlock>,

src/tasks/env.rs

Lines changed: 117 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
use crate::config::{BuilderConfig, RuProvider};
2+
use alloy::{
3+
consensus::Header,
4+
eips::eip1559::BaseFeeParams,
5+
primitives::{B256, U256},
6+
providers::Provider,
7+
};
8+
use init4_bin_base::deps::tracing::{self, Instrument, debug, error, info_span};
9+
use std::time::Duration;
10+
use tokio::sync::watch;
11+
use tokio_stream::StreamExt;
12+
use trevm::revm::{context::BlockEnv, context_interface::block::BlobExcessGasAndPrice};
13+
14+
/// A task that constructs a BlockEnv for the next block in the rollup chain.
15+
#[derive(Debug, Clone)]
16+
pub struct EnvTask {
17+
config: BuilderConfig,
18+
provider: RuProvider,
19+
}
20+
21+
impl EnvTask {
22+
/// Create a new EnvTask with the given config and provider.
23+
pub const fn new(config: BuilderConfig, provider: RuProvider) -> Self {
24+
Self { config, provider }
25+
}
26+
27+
/// Construct a BlockEnv by making calls to the provider.
28+
pub fn construct_block_env(&self, previous: &Header) -> BlockEnv {
29+
BlockEnv {
30+
number: previous.number + 1,
31+
beneficiary: self.config.builder_rewards_address,
32+
// NB: EXACTLY the same as the previous block
33+
timestamp: previous.number + self.config.slot_calculator.slot_duration(),
34+
gas_limit: self.config.rollup_block_gas_limit,
35+
basefee: previous
36+
.next_block_base_fee(BaseFeeParams::ethereum())
37+
.expect("signet has no non-1559 headers"),
38+
difficulty: U256::ZERO,
39+
prevrandao: Some(B256::random()),
40+
blob_excess_gas_and_price: Some(BlobExcessGasAndPrice {
41+
excess_blob_gas: 0,
42+
blob_gasprice: 0,
43+
}),
44+
}
45+
}
46+
47+
/// Construct the BlockEnv and send it to the sender.
48+
pub async fn task_fut(self, sender: watch::Sender<Option<BlockEnv>>) {
49+
let span = info_span!("EnvTask::task_fut::init");
50+
let mut poller = match self.provider.watch_blocks().instrument(span.clone()).await {
51+
Ok(poller) => poller,
52+
Err(err) => {
53+
let _span = span.enter();
54+
error!(%err, "Failed to watch blocks");
55+
return;
56+
}
57+
};
58+
59+
poller.set_poll_interval(Duration::from_millis(250));
60+
61+
let mut blocks = poller.into_stream();
62+
63+
while let Some(blocks) =
64+
blocks.next().instrument(info_span!("EnvTask::task_fut::stream")).await
65+
{
66+
let Some(block) = blocks.last() else {
67+
// This case occurs when there are no changes to the block,
68+
// so we do nothing.
69+
debug!("empty filter changes");
70+
continue;
71+
};
72+
let span = info_span!("EnvTask::task_fut::loop", hash = %block, number = tracing::field::Empty);
73+
74+
let previous = match self
75+
.provider
76+
.get_block((*block).into())
77+
.into_future()
78+
.instrument(span.clone())
79+
.await
80+
{
81+
Ok(Some(block)) => block.header.inner,
82+
Ok(None) => {
83+
let _span = span.enter();
84+
let _ = sender.send(None);
85+
debug!("block not found");
86+
// This may mean the chain had a rollback, so the next poll
87+
// should find something.
88+
continue;
89+
}
90+
Err(err) => {
91+
let _span = span.enter();
92+
let _ = sender.send(None);
93+
error!(%err, "Failed to get latest block");
94+
// Error may be transient, so we should not break the loop.
95+
continue;
96+
}
97+
};
98+
span.record("number", previous.number);
99+
100+
let env = self.construct_block_env(&previous);
101+
debug!(?env, "constructed block env");
102+
if sender.send(Some(env)).is_err() {
103+
// The receiver has been dropped, so we can stop the task.
104+
break;
105+
}
106+
}
107+
}
108+
109+
/// Spawn the task and return a watch::Receiver for the BlockEnv.
110+
pub fn spawn(self) -> watch::Receiver<Option<BlockEnv>> {
111+
let (sender, receiver) = watch::channel(None);
112+
let fut = self.task_fut(sender);
113+
tokio::spawn(fut);
114+
115+
receiver
116+
}
117+
}

src/tasks/mod.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,3 +15,6 @@ pub mod tx_poller;
1515

1616
/// Block simulation and environment
1717
pub mod block;
18+
19+
/// Constructs the simualtion environment.
20+
pub mod env;

tests/block_builder_test.rs

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,7 @@ mod tests {
1515
use init4_bin_base::utils::calc::SlotCalculator;
1616
use signet_sim::{SimCache, SimItem};
1717
use signet_types::constants::SignetSystemConstants;
18-
use std::{
19-
sync::Arc,
20-
time::{Duration, Instant, SystemTime, UNIX_EPOCH},
21-
};
18+
use std::time::{Duration, Instant, SystemTime, UNIX_EPOCH};
2219
use tokio::{sync::mpsc::unbounded_channel, time::timeout};
2320

2421
/// Tests the `handle_build` method of the `Simulator`.
@@ -108,16 +105,16 @@ mod tests {
108105
// Create a rollup provider
109106
let ru_provider = RootProvider::<Ethereum>::new_http(anvil_instance.endpoint_url());
110107

111-
let sim = Arc::new(Simulator::new(&config, ru_provider.clone(), config.slot_calculator));
108+
let sim = Simulator::new(&config, ru_provider.clone(), config.slot_calculator);
112109

113110
// Create a shared sim cache
114111
let sim_cache = SimCache::new();
115112

116113
// Create a sim cache and start filling it with items
117-
sim.clone().spawn_cache_tasks(tx_receiver, bundle_receiver, sim_cache.clone());
114+
sim.spawn_cache_tasks(tx_receiver, bundle_receiver, sim_cache.clone());
118115

119116
// Finally, Kick off the block builder task.
120-
sim.clone().spawn_simulator_task(constants, sim_cache.clone(), block_sender);
117+
sim.spawn_simulator_task(constants, sim_cache.clone(), block_sender);
121118

122119
// Feed in transactions to the tx_sender and wait for the block to be simulated
123120
let tx_1 = new_signed_tx(&test_key_0, 0, U256::from(1_f64), 11_000).unwrap();

0 commit comments

Comments
 (0)