use {
solana_account::{
Account, AccountSharedData, InheritableAccountFields, DUMMY_INHERITABLE_ACCOUNT_FIELDS,
},
solana_hash::Hash,
solana_instructions_sysvar::construct_instructions_data,
solana_message::SanitizedMessage,
solana_sha256_hasher::Hasher,
solana_transaction_error::TransactionError,
};
pub mod inner_instructions;
pub mod rent;
#[cfg(feature = "serde")]
pub mod serde_with_str;
pub(crate) const TRANSACTION_ACCOUNT_BASE_SIZE: usize = 64;
pub(crate) const ADDRESS_LOOKUP_TABLE_BASE_SIZE: usize = 8248;
pub fn create_blockhash(bytes: &[u8]) -> Hash {
let mut hasher = Hasher::default();
hasher.hash(bytes);
hasher.result()
}
pub fn construct_instructions_account(
message: &SanitizedMessage,
) -> Result<AccountSharedData, TransactionError> {
let data = construct_instructions_data(&message.decompile_instructions())
.map_err(|_| TransactionError::SanitizeFailure)?;
Ok(AccountSharedData::from(Account {
data,
owner: solana_sdk_ids::sysvar::id(),
..Account::default()
}))
}
pub(crate) fn create_loadable_account_with_fields(
name: &str,
(lamports, rent_epoch): InheritableAccountFields,
) -> AccountSharedData {
AccountSharedData::from(Account {
lamports,
owner: solana_sdk_ids::native_loader::id(),
data: name.as_bytes().to_vec(),
executable: true,
rent_epoch,
})
}
pub(crate) fn create_loadable_account_for_test(name: &str) -> AccountSharedData {
create_loadable_account_with_fields(name, DUMMY_INHERITABLE_ACCOUNT_FIELDS)
}
#[derive(PartialEq, Eq, Debug, Clone)]
pub(crate) struct LoadedTransactionDataSize {
loaded_accounts_data_size: u32,
requested_loaded_accounts_data_size_limit: u32,
}
impl LoadedTransactionDataSize {
pub(crate) fn with_max_size(requested_loaded_accounts_data_size_limit: u32) -> Self {
Self {
loaded_accounts_data_size: 0,
requested_loaded_accounts_data_size_limit,
}
}
pub(crate) fn increase_calculated_data_size(
&mut self,
data_size_delta: usize,
) -> Result<(), TransactionError> {
let Ok(data_size_delta) = u32::try_from(data_size_delta) else {
self.loaded_accounts_data_size = u32::MAX;
return Err(TransactionError::MaxLoadedAccountsDataSizeExceeded);
};
self.loaded_accounts_data_size = self
.loaded_accounts_data_size
.saturating_add(data_size_delta);
if self.loaded_accounts_data_size > self.requested_loaded_accounts_data_size_limit {
Err(TransactionError::MaxLoadedAccountsDataSizeExceeded)
} else {
Ok(())
}
}
}