Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor: move VersionedConstants macro, errors from Blockifier to StarknetAPI #3195

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions crates/blockifier/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -88,3 +88,7 @@ required-features = ["testing"]
name = "feature_contracts_compatibility_test"
path = "tests/feature_contracts_compatibility_test.rs"
required-features = ["testing"]

[package.metadata.cargo-machete]
# `paste` is used in the `define_versioned_constants!` macro but may be falsely detected as unused.
ignored = ["paste"]
89 changes: 8 additions & 81 deletions crates/blockifier/src/versioned_constants.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use std::collections::{BTreeMap, HashMap, HashSet};
use std::path::{Path, PathBuf};
use std::sync::{Arc, LazyLock};
use std::{fs, io};
use std::io;
use std::path::Path;
use std::sync::Arc;

use cairo_vm::types::builtin_name::BuiltinName;
use cairo_vm::vm::runners::cairo_runner::ExecutionResources;
Expand All @@ -10,17 +10,16 @@ use num_rational::Ratio;
use num_traits::Inv;
use papyrus_config::dumping::{ser_param, SerializeConfig};
use papyrus_config::{ParamPath, ParamPrivacyInput, SerializedParam};
use paste::paste;
use semver::Version;
use serde::de::Error as DeserializationError;
use serde::{Deserialize, Deserializer, Serialize};
use serde_json::{Map, Number, Value};
use starknet_api::block::{GasPrice, StarknetVersion};
use starknet_api::contract_class::SierraVersion;
use starknet_api::core::ContractAddress;
use starknet_api::define_versioned_constants;
use starknet_api::execution_resources::{GasAmount, GasVector};
use starknet_api::transaction::fields::GasVectorComputationMode;
use starknet_infra_utils::compile_time_cargo_manifest_dir;
use strum::IntoEnumIterator;
use thiserror::Error;

Expand All @@ -36,89 +35,17 @@ use crate::utils::u64_from_usize;
#[path = "versioned_constants_test.rs"]
pub mod test;

/// Auto-generate getters for listed versioned constants versions.
macro_rules! define_versioned_constants {
($(($variant:ident, $path_to_json:expr)),* $(,)?) => {
// Static (lazy) instances of the versioned constants.
// For internal use only; for access to a static instance use the `StarknetVersion` enum.
paste! {
$(
pub(crate) const [<VERSIONED_CONSTANTS_ $variant:upper _JSON>]: &str =
include_str!($path_to_json);
pub static [<VERSIONED_CONSTANTS_ $variant:upper>]: LazyLock<VersionedConstants> = LazyLock::new(|| {
serde_json::from_str([<VERSIONED_CONSTANTS_ $variant:upper _JSON>])
.expect(&format!("Versioned constants {} is malformed.", $path_to_json))
});
)*
}

/// API to access a static instance of the versioned constants.
impl TryFrom<StarknetVersion> for &'static VersionedConstants {
type Error = VersionedConstantsError;

fn try_from(version: StarknetVersion) -> VersionedConstantsResult<Self> {
match version {
$(
StarknetVersion::$variant => {
Ok(& paste! { [<VERSIONED_CONSTANTS_ $variant:upper>] })
}
)*
_ => Err(VersionedConstantsError::InvalidStarknetVersion(version)),
}
}
}

impl VersionedConstants {
pub fn path_to_json(version: &StarknetVersion) -> VersionedConstantsResult<&'static str> {
match version {
$(StarknetVersion::$variant => Ok($path_to_json),)*
_ => Err(VersionedConstantsError::InvalidStarknetVersion(*version)),
}
}

/// Gets the constants that shipped with the current version of the Blockifier.
/// To use custom constants, initialize the struct from a file using `from_path`.
pub fn latest_constants() -> &'static Self {
Self::get(&StarknetVersion::LATEST)
.expect("Latest version should support VC.")
}

/// Gets the constants for the specified Starknet version.
pub fn get(version: &StarknetVersion) -> VersionedConstantsResult<&'static Self> {
match version {
$(
StarknetVersion::$variant => Ok(
& paste! { [<VERSIONED_CONSTANTS_ $variant:upper>] }
),
)*
_ => Err(VersionedConstantsError::InvalidStarknetVersion(*version)),
}
}
}

pub static VERSIONED_CONSTANTS_LATEST_JSON: LazyLock<String> = LazyLock::new(|| {
let latest_variant = StarknetVersion::LATEST;
let path_to_json: PathBuf = [
compile_time_cargo_manifest_dir!(),
"src".into(),
VersionedConstants::path_to_json(&latest_variant)
.expect("Latest variant should have a path to json.").into()
].iter().collect();
fs::read_to_string(path_to_json.clone())
.expect(&format!("Failed to read file {}.", path_to_json.display()))
});
};
}

define_versioned_constants! {
define_versioned_constants!(
VersionedConstants,
VersionedConstantsError,
(V0_13_0, "../resources/versioned_constants_0_13_0.json"),
(V0_13_1, "../resources/versioned_constants_0_13_1.json"),
(V0_13_1_1, "../resources/versioned_constants_0_13_1_1.json"),
(V0_13_2, "../resources/versioned_constants_0_13_2.json"),
(V0_13_2_1, "../resources/versioned_constants_0_13_2_1.json"),
(V0_13_3, "../resources/versioned_constants_0_13_3.json"),
(V0_13_4, "../resources/versioned_constants_0_13_4.json"),
}
);

pub type ResourceCost = Ratio<u64>;

Expand Down
4 changes: 4 additions & 0 deletions crates/blockifier/src/versioned_constants_test.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
use std::path::PathBuf;

use glob::{glob, Paths};
use pretty_assertions::assert_eq;
use starknet_api::block::StarknetVersion;
use starknet_infra_utils::compile_time_cargo_manifest_dir;

use super::*;

Expand Down
1 change: 1 addition & 0 deletions crates/starknet_api/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ pub mod test_utils;
pub mod transaction;
pub mod transaction_hash;
pub mod type_utils;
pub mod versioned_constants_logic;

use std::num::ParseIntError;

Expand Down
62 changes: 62 additions & 0 deletions crates/starknet_api/src/versioned_constants_logic.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
/// Auto-generate getters for listed versioned constants versions.
#[macro_export]
macro_rules! define_versioned_constants {
($struct_name:ident, $error_type:ident, $(($variant:ident, $path_to_json:expr)),* $(,)?) => {
// Static (lazy) instances of the versioned constants.
// For internal use only; for access to a static instance use the `StarknetVersion` enum.
paste::paste! {
$(
pub(crate) const [<VERSIONED_CONSTANTS_ $variant:upper _JSON>]: &str =
include_str!($path_to_json);
/// Static instance of the versioned constants for the Starknet version.
pub static [<VERSIONED_CONSTANTS_ $variant:upper>]: std::sync::LazyLock<$struct_name> =
std::sync::LazyLock::new(|| {
serde_json::from_str([<VERSIONED_CONSTANTS_ $variant:upper _JSON>])
.expect(&format!("Versioned constants {} is malformed.", $path_to_json))
});
)*
}

impl $struct_name {
/// Gets the path to the JSON file for the specified Starknet version.
pub fn path_to_json(version: &starknet_api::block::StarknetVersion) -> Result<&'static str, $error_type> {
match version {
$(starknet_api::block::StarknetVersion::$variant => Ok($path_to_json),)*
_ => Err($error_type::InvalidStarknetVersion(*version)),
}
}

/// Gets the constants that shipped with the current version of the Starknet.
/// To use custom constants, initialize the struct from a file using `from_path`.
pub fn latest_constants() -> &'static Self {
Self::get(&starknet_api::block::StarknetVersion::LATEST)
.expect("Latest version should support VC.")
}

/// Gets the constants for the specified Starknet version.
pub fn get(version: &starknet_api::block::StarknetVersion) -> Result<&'static Self, $error_type> {
match version {
$(
starknet_api::block::StarknetVersion::$variant => Ok(
& paste::paste! { [<VERSIONED_CONSTANTS_ $variant:upper>] }
),
)*
_ => Err($error_type::InvalidStarknetVersion(*version)),
}
}
}

/// Gets a string of the constants of the latest version of Starknet.
pub static VERSIONED_CONSTANTS_LATEST_JSON: std::sync::LazyLock<String> = std::sync::LazyLock::new(|| {
let latest_variant = StarknetVersion::LATEST;
let path_to_json: std::path::PathBuf = [
starknet_infra_utils::compile_time_cargo_manifest_dir!(),
"src".into(),
$struct_name::path_to_json(&latest_variant)
.expect("Latest variant should have a path to json.").into()
].iter().collect();
std::fs::read_to_string(path_to_json.clone())
.expect(&format!("Failed to read file {}.", path_to_json.display()))
});
};
}
Loading