Skip to content

Commit

Permalink
chore(blockifier_reexecution): serialize reexecution data to file
Browse files Browse the repository at this point in the history
  • Loading branch information
aner-starkware committed Nov 4, 2024
1 parent 18d6b55 commit 590e518
Show file tree
Hide file tree
Showing 8 changed files with 93 additions and 15 deletions.
1 change: 1 addition & 0 deletions crates/blockifier/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ description = "The transaction-executing component in the Starknet sequencer."
workspace = true

[features]
reexecution = []
cairo_native = ["dep:cairo-native"]
jemalloc = ["dep:tikv-jemallocator"]
testing = ["rand", "rstest", "starknet_api/testing"]
Expand Down
7 changes: 7 additions & 0 deletions crates/blockifier/src/state/cached_state.rs
Original file line number Diff line number Diff line change
Expand Up @@ -294,6 +294,13 @@ impl Default for CachedState<crate::test_utils::dict_state_reader::DictStateRead
}
}

#[cfg(feature = "reexecution")]
impl<S: StateReader> CachedState<S> {
pub fn get_initial_reads(&self) -> StateResult<StateMaps> {
Ok(self.cache.borrow().initial_reads.clone())
}
}

pub type StorageEntry = (ContractAddress, StorageKey);

#[derive(Debug, Default, derive_more::IntoIterator)]
Expand Down
2 changes: 1 addition & 1 deletion crates/blockifier_reexecution/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ license.workspace = true
blockifier_regression_https_testing = []

[dependencies]
blockifier = { workspace = true, features = ["transaction_serde"] }
blockifier = { workspace = true, features = ["reexecution", "transaction_serde"] }
cairo-lang-starknet-classes.workspace = true
cairo-lang-utils.workspace = true
clap = { workspace = true, features = ["cargo", "derive"] }
Expand Down
65 changes: 64 additions & 1 deletion crates/blockifier_reexecution/src/main.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
use blockifier_reexecution::state_reader::reexecution_state_reader::ReexecutionStateReader;
use blockifier_reexecution::state_reader::test_state_reader::{
ConsecutiveStateReaders,
ConsecutiveTestStateReaders,
SerializableOfflineReexecutionData,
};
use blockifier_reexecution::state_reader::utils::JSON_RPC_VERSION;
use clap::{Args, Parser, Subcommand};
Expand Down Expand Up @@ -93,6 +95,67 @@ fn main() {

println!("RPC test passed successfully.");
}
Command::WriteRpcRepliesToJson { .. } => todo!(),

Command::WriteRpcRepliesToJson {
url_and_block_number: SharedArgs { node_url, block_number },
directory_path,
} => {
let directory_path = directory_path.unwrap_or(format!(
"./crates/blockifier_reexecution/resources/block_{block_number}/"
));

// TODO(Aner): refactor to reduce code duplication.
let config = RpcStateReaderConfig {
url: node_url,
json_rpc_version: JSON_RPC_VERSION.to_string(),
};

let ConsecutiveTestStateReaders { last_block_state_reader, next_block_state_reader } =
ConsecutiveTestStateReaders::new(BlockNumber(block_number - 1), Some(config), true);

let block_info_next_block = next_block_state_reader.get_block_info().unwrap();

let starknet_version = next_block_state_reader.get_starknet_version().unwrap();

let state_diff_next_block = next_block_state_reader.get_state_diff().unwrap();

let transactions_next_block = next_block_state_reader.get_all_txs_in_block().unwrap();

let blockifier_transactions_next_block = &last_block_state_reader
.api_txs_to_blockifier_txs_next_block(transactions_next_block.clone())
.unwrap();

let mut transaction_executor = last_block_state_reader
.get_transaction_executor(
next_block_state_reader.get_block_context().unwrap(),
None,
)
.unwrap();

transaction_executor.execute_txs(blockifier_transactions_next_block);

let block_state = transaction_executor.block_state.unwrap();
let initial_reads = block_state.get_initial_reads().unwrap();

let contract_class_mapping =
block_state.state.get_contract_class_mapping_dumper().unwrap();

let serializable_offline_reexecution_data = SerializableOfflineReexecutionData {
state_maps: initial_reads.into(),
block_info_next_block,
starknet_version,
transactions_next_block,
contract_class_mapping,
state_diff_next_block,
};

serializable_offline_reexecution_data
.write_to_file(&directory_path, "reexecution_data.json")
.unwrap();

println!(
"RPC replies required for reexecuting block {block_number} written to json file."
);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ use super::compile::{legacy_to_contract_class_v0, sierra_to_contact_class_v1};
use crate::state_reader::errors::ReexecutionError;
use crate::state_reader::test_state_reader::ReexecutionResult;

pub(crate) trait ReexecutionStateReader {
pub trait ReexecutionStateReader {
fn get_contract_class(&self, class_hash: &ClassHash) -> StateResult<StarknetContractClass>;

fn get_class_info(&self, class_hash: ClassHash) -> ReexecutionResult<ClassInfo> {
Expand All @@ -33,7 +33,7 @@ pub(crate) trait ReexecutionStateReader {
}

// TODO(Aner): extend/refactor to accomodate all types of transactions.
fn api_txs_to_blockifier_txs(
fn api_txs_to_blockifier_txs_next_block(
&self,
txs_and_hashes: Vec<(Transaction, TransactionHash)>,
) -> ReexecutionResult<Vec<BlockifierTransaction>> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -187,5 +187,7 @@ pub fn test_get_statediff_rpc(test_state_reader: TestStateReader) {
#[case(EXAMPLE_DECLARE_V3_BLOCK_NUMBER)]
pub fn test_get_all_blockifier_tx_in_block(#[case] block_number: u64) {
let state_reader = TestStateReader::new_for_testing(BlockNumber(block_number));
state_reader.api_txs_to_blockifier_txs(state_reader.get_all_txs_in_block().unwrap()).unwrap();
state_reader
.api_txs_to_blockifier_txs_next_block(state_reader.get_all_txs_in_block().unwrap())
.unwrap();
}
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,12 @@ pub struct OfflineReexecutionData {

#[derive(Serialize, Deserialize)]
pub struct SerializableOfflineReexecutionData {
state_maps: ReexecutionStateMaps,
contract_class_mapping: StarknetContractClassMapping,
block_info_next_block: BlockInfo,
starknet_version: StarknetVersion,
transactions_next_block: Vec<(Transaction, TransactionHash)>,
state_diff_next_block: CommitmentStateDiff,
pub state_maps: ReexecutionStateMaps,
pub block_info_next_block: BlockInfo,
pub starknet_version: StarknetVersion,
pub transactions_next_block: Vec<(Transaction, TransactionHash)>,
pub state_diff_next_block: CommitmentStateDiff,
pub contract_class_mapping: StarknetContractClassMapping,
}

impl SerializableOfflineReexecutionData {
Expand All @@ -80,7 +80,7 @@ impl From<SerializableOfflineReexecutionData> for OfflineReexecutionData {
contract_class_mapping: value.contract_class_mapping,
};
let transactions_next_block = offline_state_reader_prev_block
.api_txs_to_blockifier_txs(value.transactions_next_block)
.api_txs_to_blockifier_txs_next_block(value.transactions_next_block)
.expect("Failed to convert starknet-api transactions to blockifier transactions.");
Self {
offline_state_reader_prev_block,
Expand Down Expand Up @@ -299,6 +299,10 @@ impl TestStateReader {
class_hash_to_compiled_class_hash: declared_classes,
})
}

pub fn get_contract_class_mapping_dumper(&self) -> Option<StarknetContractClassMapping> {
self.contract_class_mapping_dumper.lock().unwrap().clone()
}
}

impl ReexecutionStateReader for TestStateReader {
Expand Down Expand Up @@ -372,8 +376,9 @@ impl ConsecutiveStateReaders<TestStateReader> for ConsecutiveTestStateReaders {
}

fn get_next_block_txs(&self) -> ReexecutionResult<Vec<BlockifierTransaction>> {
self.next_block_state_reader
.api_txs_to_blockifier_txs(self.next_block_state_reader.get_all_txs_in_block()?)
self.next_block_state_reader.api_txs_to_blockifier_txs_next_block(
self.next_block_state_reader.get_all_txs_in_block()?,
)
}

fn get_next_block_state_diff(&self) -> ReexecutionResult<CommitmentStateDiff> {
Expand Down
2 changes: 1 addition & 1 deletion crates/blockifier_reexecution/src/state_reader/utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ pub(crate) fn disjoint_hashmap_union<K: std::hash::Hash + std::cmp::Eq, V>(
}

#[derive(Debug, PartialEq, Eq, Serialize, Deserialize)]
pub(crate) struct ReexecutionStateMaps {
pub struct ReexecutionStateMaps {
nonces: HashMap<ContractAddress, Nonce>,
class_hashes: HashMap<ContractAddress, ClassHash>,
storage: HashMap<ContractAddress, HashMap<StorageKey, Felt>>,
Expand Down

0 comments on commit 590e518

Please sign in to comment.