diff --git a/Cargo.lock b/Cargo.lock index bae22dfdabf59a..c77ccdacc65b0b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6157,6 +6157,7 @@ dependencies = [ "itertools 0.12.1", "lazy_static", "log", + "rand 0.8.5", "rustc_version 0.4.0", "solana-address-lookup-table-program", "solana-bpf-loader-program", diff --git a/cost-model/Cargo.toml b/cost-model/Cargo.toml index 52e10447387eeb..e16d324eac6e68 100644 --- a/cost-model/Cargo.toml +++ b/cost-model/Cargo.toml @@ -33,6 +33,7 @@ name = "solana_cost_model" [dev-dependencies] itertools = { workspace = true } +rand = "0.8.5" solana-logger = { workspace = true } solana-sdk = { workspace = true, features = ["dev-context-only-utils"] } static_assertions = { workspace = true } diff --git a/cost-model/benches/block_cost_limit.rs b/cost-model/benches/block_cost_limit.rs new file mode 100644 index 00000000000000..2118b413a9dfa4 --- /dev/null +++ b/cost-model/benches/block_cost_limit.rs @@ -0,0 +1,55 @@ +#![feature(test)] +extern crate test; +use { + rand::Rng, + solana_cost_model::block_cost_limits::BUILTIN_INSTRUCTION_COSTS, + solana_sdk::{ + address_lookup_table, bpf_loader, bpf_loader_deprecated, bpf_loader_upgradeable, + compute_budget, ed25519_program, loader_v4, pubkey::Pubkey, secp256k1_program, + }, + test::Bencher, +}; + +struct BenchSetup { + pubkeys: [Pubkey; 12], +} + +const NUM_TRANSACTIONS_PER_ITER: usize = 1024; +const DEFAULT_INSTRUCTION_COMPUTE_UNIT_LIMIT: u32 = 200_000; + +fn setup() -> BenchSetup { + let pubkeys: [Pubkey; 12] = [ + solana_stake_program::id(), + solana_config_program::id(), + solana_vote_program::id(), + solana_system_program::id(), + compute_budget::id(), + address_lookup_table::program::id(), + bpf_loader_upgradeable::id(), + bpf_loader_deprecated::id(), + bpf_loader::id(), + loader_v4::id(), + secp256k1_program::id(), + ed25519_program::id(), + ]; + + BenchSetup { pubkeys } +} + +#[bench] +fn bench_hash_find(bencher: &mut Bencher) { + let BenchSetup { pubkeys } = setup(); + + bencher.iter(|| { + for _t in 0..NUM_TRANSACTIONS_PER_ITER { + let idx = rand::thread_rng().gen_range(0..pubkeys.len()); + let ix_execution_cost = + if let Some(builtin_cost) = BUILTIN_INSTRUCTION_COSTS.get(&pubkeys[idx]) { + *builtin_cost + } else { + u64::from(DEFAULT_INSTRUCTION_COMPUTE_UNIT_LIMIT) + }; + assert!(ix_execution_cost != DEFAULT_INSTRUCTION_COMPUTE_UNIT_LIMIT as u64); + } + }); +} diff --git a/cost-model/src/block_cost_limits.rs b/cost-model/src/block_cost_limits.rs index 30120e8ca2af77..3a8fe433c13b82 100644 --- a/cost-model/src/block_cost_limits.rs +++ b/cost-model/src/block_cost_limits.rs @@ -1,12 +1,12 @@ //! defines block cost related limits //! use { + ahash::AHashMap, lazy_static::lazy_static, solana_sdk::{ address_lookup_table, bpf_loader, bpf_loader_deprecated, bpf_loader_upgradeable, compute_budget, ed25519_program, loader_v4, pubkey::Pubkey, secp256k1_program, }, - std::collections::HashMap, }; /// Static configurations: @@ -37,7 +37,7 @@ pub const INSTRUCTION_DATA_BYTES_COST: u64 = 140 /*bytes per us*/ / COMPUTE_UNIT // Number of compute units for each built-in programs lazy_static! { /// Number of compute units for each built-in programs - pub static ref BUILTIN_INSTRUCTION_COSTS: HashMap = [ + pub static ref BUILTIN_INSTRUCTION_COSTS: AHashMap = [ (solana_stake_program::id(), solana_stake_program::stake_instruction::DEFAULT_COMPUTE_UNITS), (solana_config_program::id(), solana_config_program::config_processor::DEFAULT_COMPUTE_UNITS), (solana_vote_program::id(), solana_vote_program::vote_processor::DEFAULT_COMPUTE_UNITS),