solana-with-rpc-optimizations/accounts-db/benches/bench_hashing.rs

86 lines
3.1 KiB
Rust

use {
criterion::{criterion_group, criterion_main, BatchSize, BenchmarkId, Criterion, Throughput},
rand::seq::SliceRandom,
solana_accounts_db::{
accounts_db::AccountsDb,
accounts_hash::{AccountHash, AccountsHasher},
},
solana_sdk::{account::AccountSharedData, hash::Hash, pubkey::Pubkey},
};
const KB: usize = 1024;
const MB: usize = KB * KB;
const DATA_SIZES: [usize; 6] = [
0, // the smallest account
165, // the size of an spl token account
200, // the size of a stake account
KB, // a medium sized account
MB, // a large sized account
10 * MB, // the largest account
];
/// The number of bytes of *non account data* that are also hashed as
/// part of computing an account's hash.
///
/// Ensure this constant stays in sync with the value of `META_SIZE` in
/// AccountsDb::hash_account_data().
const META_SIZE: usize = 81;
fn bench_hash_account(c: &mut Criterion) {
let lamports = 123_456_789;
let owner = Pubkey::default();
let address = Pubkey::default();
let mut group = c.benchmark_group("hash_account");
for data_size in DATA_SIZES {
let num_bytes = META_SIZE.checked_add(data_size).unwrap();
group.throughput(Throughput::Bytes(num_bytes as u64));
let account = AccountSharedData::new(lamports, data_size, &owner);
group.bench_function(BenchmarkId::new("data_size", data_size), |b| {
b.iter(|| AccountsDb::hash_account(&account, &address));
});
}
}
fn bench_accounts_delta_hash(c: &mut Criterion) {
const ACCOUNTS_COUNTS: [usize; 4] = [
1, // the smallest count; will bench overhead
100, // number of accounts written per slot on mnb (with *no* rent rewrites)
1_000, // number of accounts written slot on mnb (with rent rewrites)
10_000, // reasonable largest number of accounts written per slot
];
fn create_account_hashes(accounts_count: usize) -> Vec<(Pubkey, AccountHash)> {
let mut account_hashes: Vec<_> = std::iter::repeat_with(|| {
let address = Pubkey::new_unique();
let hash = AccountHash(Hash::new_unique());
(address, hash)
})
.take(accounts_count)
.collect();
// since the accounts delta hash needs to sort the accounts first, ensure we're not
// creating a pre-sorted vec.
let mut rng = rand::thread_rng();
account_hashes.shuffle(&mut rng);
account_hashes
}
let mut group = c.benchmark_group("accounts_delta_hash");
for accounts_count in ACCOUNTS_COUNTS {
group.throughput(Throughput::Elements(accounts_count as u64));
let account_hashes = create_account_hashes(accounts_count);
group.bench_function(BenchmarkId::new("accounts_count", accounts_count), |b| {
b.iter_batched(
|| account_hashes.clone(),
AccountsHasher::accumulate_account_hashes,
BatchSize::SmallInput,
);
});
}
}
criterion_group!(benches, bench_hash_account, bench_accounts_delta_hash);
criterion_main!(benches);