use callback for account and account_default_if_zero_lamport (#819)
use callback for `account` and `account_default_if_zero_lamport`
This commit is contained in:
parent
7a15ec99cd
commit
ee5fb5102d
|
@ -73,8 +73,8 @@ impl<'a: 'b, 'b, U: StorableAccounts<'a>, V: Borrow<AccountHash>>
|
||||||
let item = self.hashes.as_ref().unwrap();
|
let item = self.hashes.as_ref().unwrap();
|
||||||
item[index].borrow()
|
item[index].borrow()
|
||||||
};
|
};
|
||||||
let account = self.accounts.account_default_if_zero_lamport(index);
|
self.accounts
|
||||||
callback((account, pubkey, hash))
|
.account_default_if_zero_lamport(index, |account| callback((account, pubkey, hash)))
|
||||||
}
|
}
|
||||||
|
|
||||||
/// None if account at index has lamports == 0
|
/// None if account at index has lamports == 0
|
||||||
|
@ -83,9 +83,10 @@ impl<'a: 'b, 'b, U: StorableAccounts<'a>, V: Borrow<AccountHash>>
|
||||||
pub fn account<Ret>(
|
pub fn account<Ret>(
|
||||||
&self,
|
&self,
|
||||||
index: usize,
|
index: usize,
|
||||||
mut callback: impl FnMut(Option<AccountForStorage<'a>>) -> Ret,
|
callback: impl FnMut(Option<AccountForStorage<'a>>) -> Ret,
|
||||||
) -> Ret {
|
) -> Ret {
|
||||||
callback(self.accounts.account_default_if_zero_lamport(index))
|
self.accounts
|
||||||
|
.account_default_if_zero_lamport(index, callback)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// # accounts to write
|
/// # accounts to write
|
||||||
|
|
|
@ -6397,29 +6397,31 @@ impl AccountsDb {
|
||||||
txn_iter
|
txn_iter
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.map(|(i, txn)| {
|
.map(|(i, txn)| {
|
||||||
let account = accounts_and_meta_to_store
|
let mut account_info = AccountInfo::default();
|
||||||
.account_default_if_zero_lamport(i)
|
accounts_and_meta_to_store.account_default_if_zero_lamport(i, |account| {
|
||||||
.map(|account| account.to_account_shared_data())
|
let account = account
|
||||||
.unwrap_or_default();
|
.map(|account| account.to_account_shared_data())
|
||||||
let pubkey = accounts_and_meta_to_store.pubkey(i);
|
.unwrap_or_default();
|
||||||
let account_info = AccountInfo::new(StorageLocation::Cached, account.lamports());
|
let pubkey = accounts_and_meta_to_store.pubkey(i);
|
||||||
|
account_info = AccountInfo::new(StorageLocation::Cached, account.lamports());
|
||||||
|
|
||||||
self.notify_account_at_accounts_update(
|
self.notify_account_at_accounts_update(
|
||||||
slot,
|
slot,
|
||||||
&account,
|
&account,
|
||||||
txn,
|
txn,
|
||||||
pubkey,
|
pubkey,
|
||||||
&mut write_version_producer,
|
&mut write_version_producer,
|
||||||
);
|
);
|
||||||
|
|
||||||
let cached_account = self.accounts_cache.store(slot, pubkey, account);
|
let cached_account = self.accounts_cache.store(slot, pubkey, account);
|
||||||
// hash this account in the bg
|
// hash this account in the bg
|
||||||
match &self.sender_bg_hasher {
|
match &self.sender_bg_hasher {
|
||||||
Some(ref sender) => {
|
Some(ref sender) => {
|
||||||
let _ = sender.send(cached_account);
|
let _ = sender.send(cached_account);
|
||||||
}
|
}
|
||||||
None => (),
|
None => (),
|
||||||
};
|
};
|
||||||
|
});
|
||||||
account_info
|
account_info
|
||||||
})
|
})
|
||||||
.collect()
|
.collect()
|
||||||
|
@ -6484,10 +6486,11 @@ impl AccountsDb {
|
||||||
let len = accounts.len();
|
let len = accounts.len();
|
||||||
let mut hashes = Vec::with_capacity(len);
|
let mut hashes = Vec::with_capacity(len);
|
||||||
for index in 0..accounts.len() {
|
for index in 0..accounts.len() {
|
||||||
let (pubkey, account) =
|
let pubkey = accounts.pubkey(index);
|
||||||
(accounts.pubkey(index), accounts.account(index));
|
accounts.account(index, |account| {
|
||||||
let hash = Self::hash_account(&account, pubkey);
|
let hash = Self::hash_account(&account, pubkey);
|
||||||
hashes.push(hash);
|
hashes.push(hash);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
hash_time.stop();
|
hash_time.stop();
|
||||||
self.stats
|
self.stats
|
||||||
|
@ -7785,19 +7788,20 @@ impl AccountsDb {
|
||||||
|
|
||||||
(start..end).for_each(|i| {
|
(start..end).for_each(|i| {
|
||||||
let info = infos[i];
|
let info = infos[i];
|
||||||
let pubkey_account = (accounts.pubkey(i), accounts.account(i));
|
let pubkey = accounts.pubkey(i);
|
||||||
let pubkey = pubkey_account.0;
|
accounts.account(i, |account| {
|
||||||
let old_slot = accounts.slot(i);
|
let old_slot = accounts.slot(i);
|
||||||
self.accounts_index.upsert(
|
self.accounts_index.upsert(
|
||||||
target_slot,
|
target_slot,
|
||||||
old_slot,
|
old_slot,
|
||||||
pubkey,
|
pubkey,
|
||||||
&pubkey_account.1,
|
&account,
|
||||||
&self.account_indexes,
|
&self.account_indexes,
|
||||||
info,
|
info,
|
||||||
&mut reclaims,
|
&mut reclaims,
|
||||||
reclaim,
|
reclaim,
|
||||||
);
|
);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
reclaims
|
reclaims
|
||||||
};
|
};
|
||||||
|
@ -8213,9 +8217,10 @@ impl AccountsDb {
|
||||||
let mut stats = BankHashStats::default();
|
let mut stats = BankHashStats::default();
|
||||||
let mut total_data = 0;
|
let mut total_data = 0;
|
||||||
(0..accounts.len()).for_each(|index| {
|
(0..accounts.len()).for_each(|index| {
|
||||||
let account = accounts.account(index);
|
accounts.account(index, |account| {
|
||||||
total_data += account.data().len();
|
total_data += account.data().len();
|
||||||
stats.update(&account);
|
stats.update(&account);
|
||||||
|
})
|
||||||
});
|
});
|
||||||
|
|
||||||
self.stats
|
self.stats
|
||||||
|
@ -9637,8 +9642,12 @@ pub mod tests {
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
self.1[index].0
|
self.1[index].0
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
self.1[index].1.into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback(self.1[index].1.into())
|
||||||
}
|
}
|
||||||
fn slot(&self, index: usize) -> Slot {
|
fn slot(&self, index: usize) -> Slot {
|
||||||
// note that this could be different than 'target_slot()' PER account
|
// note that this could be different than 'target_slot()' PER account
|
||||||
|
|
|
@ -25,9 +25,13 @@ impl<'a> StorableAccounts<'a> for (Slot, &'a [StakeReward]) {
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
&self.1[index].stake_pubkey
|
&self.1[index].stake_pubkey
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
let entry = &self.1[index];
|
let entry = &self.1[index];
|
||||||
(&entry.stake_account).into()
|
callback((&entry.stake_account).into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
||||||
|
|
|
@ -84,11 +84,17 @@ pub trait StorableAccounts<'a>: Sync {
|
||||||
/// pubkey at 'index'
|
/// pubkey at 'index'
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey;
|
fn pubkey(&self, index: usize) -> &Pubkey;
|
||||||
/// account at 'index'
|
/// account at 'index'
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a>;
|
fn account<Ret>(&self, index: usize, callback: impl FnMut(AccountForStorage<'a>) -> Ret)
|
||||||
|
-> Ret;
|
||||||
/// None if account is zero lamports
|
/// None if account is zero lamports
|
||||||
fn account_default_if_zero_lamport(&self, index: usize) -> Option<AccountForStorage<'a>> {
|
fn account_default_if_zero_lamport<Ret>(
|
||||||
let account = self.account(index);
|
&self,
|
||||||
(account.lamports() != 0).then_some(account)
|
index: usize,
|
||||||
|
mut callback: impl FnMut(Option<AccountForStorage<'a>>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
self.account(index, |account| {
|
||||||
|
callback((!account.is_zero_lamport()).then_some(account))
|
||||||
|
})
|
||||||
}
|
}
|
||||||
// current slot for account at 'index'
|
// current slot for account at 'index'
|
||||||
fn slot(&self, index: usize) -> Slot;
|
fn slot(&self, index: usize) -> Slot;
|
||||||
|
@ -139,8 +145,12 @@ where
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
self.accounts[index].0
|
self.accounts[index].0
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
self.accounts[index].1.into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback(self.accounts[index].1.into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// per-index slot is not unique per slot, but it is different than 'target_slot'
|
// per-index slot is not unique per slot, but it is different than 'target_slot'
|
||||||
|
@ -162,8 +172,12 @@ where
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
self.1[index].0
|
self.1[index].0
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
self.1[index].1.into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback(self.1[index].1.into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
||||||
|
@ -183,8 +197,12 @@ where
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
&self.1[index].0
|
&self.1[index].0
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
(&self.1[index].1).into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback((&self.1[index].1).into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
||||||
|
@ -202,8 +220,12 @@ impl<'a> StorableAccounts<'a> for (Slot, &'a [&'a StoredAccountMeta<'a>]) {
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
self.1[index].pubkey()
|
self.1[index].pubkey()
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
self.1[index].into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback(self.1[index].into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
// per-index slot is not unique per slot when per-account slot is not included in the source data
|
||||||
|
@ -291,9 +313,13 @@ impl<'a> StorableAccounts<'a> for StorableAccountsBySlot<'a> {
|
||||||
let indexes = self.find_internal_index(index);
|
let indexes = self.find_internal_index(index);
|
||||||
self.slots_and_accounts[indexes.0].1[indexes.1].pubkey()
|
self.slots_and_accounts[indexes.0].1[indexes.1].pubkey()
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
let indexes = self.find_internal_index(index);
|
let indexes = self.find_internal_index(index);
|
||||||
self.slots_and_accounts[indexes.0].1[indexes.1].into()
|
callback(self.slots_and_accounts[indexes.0].1[indexes.1].into())
|
||||||
}
|
}
|
||||||
fn slot(&self, index: usize) -> Slot {
|
fn slot(&self, index: usize) -> Slot {
|
||||||
let indexes = self.find_internal_index(index);
|
let indexes = self.find_internal_index(index);
|
||||||
|
@ -323,8 +349,12 @@ impl<'a> StorableAccounts<'a> for (Slot, &'a [&'a StoredAccountMeta<'a>], Slot)
|
||||||
fn pubkey(&self, index: usize) -> &Pubkey {
|
fn pubkey(&self, index: usize) -> &Pubkey {
|
||||||
self.1[index].pubkey()
|
self.1[index].pubkey()
|
||||||
}
|
}
|
||||||
fn account(&self, index: usize) -> AccountForStorage<'a> {
|
fn account<Ret>(
|
||||||
self.1[index].into()
|
&self,
|
||||||
|
index: usize,
|
||||||
|
mut callback: impl FnMut(AccountForStorage<'a>) -> Ret,
|
||||||
|
) -> Ret {
|
||||||
|
callback(self.1[index].into())
|
||||||
}
|
}
|
||||||
fn slot(&self, _index: usize) -> Slot {
|
fn slot(&self, _index: usize) -> Slot {
|
||||||
// same other slot for all accounts
|
// same other slot for all accounts
|
||||||
|
@ -364,7 +394,11 @@ pub mod tests {
|
||||||
assert_eq!(a.is_empty(), b.is_empty());
|
assert_eq!(a.is_empty(), b.is_empty());
|
||||||
(0..a.len()).for_each(|i| {
|
(0..a.len()).for_each(|i| {
|
||||||
assert_eq!(a.pubkey(i), b.pubkey(i));
|
assert_eq!(a.pubkey(i), b.pubkey(i));
|
||||||
assert!(accounts_equal(&a.account(i), &b.account(i)));
|
b.account(i, |account| {
|
||||||
|
a.account(i, |account_a| {
|
||||||
|
assert!(accounts_equal(&account_a, &account));
|
||||||
|
});
|
||||||
|
});
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -486,7 +520,9 @@ pub mod tests {
|
||||||
compare(&test2, &test_moving_slots2);
|
compare(&test2, &test_moving_slots2);
|
||||||
for (i, raw) in raw.iter().enumerate() {
|
for (i, raw) in raw.iter().enumerate() {
|
||||||
assert_eq!(raw.0, *test3.pubkey(i));
|
assert_eq!(raw.0, *test3.pubkey(i));
|
||||||
assert!(accounts_equal(&raw.1, &test3.account(i)));
|
test3.account(i, |account| {
|
||||||
|
assert!(accounts_equal(&raw.1, &account));
|
||||||
|
});
|
||||||
assert_eq!(raw.2, test3.slot(i));
|
assert_eq!(raw.2, test3.slot(i));
|
||||||
assert_eq!(target_slot, test4.slot(i));
|
assert_eq!(target_slot, test4.slot(i));
|
||||||
assert_eq!(target_slot, test2.slot(i));
|
assert_eq!(target_slot, test2.slot(i));
|
||||||
|
@ -587,7 +623,9 @@ pub mod tests {
|
||||||
assert_eq!(entries0 != entries, storable.contains_multiple_slots());
|
assert_eq!(entries0 != entries, storable.contains_multiple_slots());
|
||||||
(0..entries).for_each(|index| {
|
(0..entries).for_each(|index| {
|
||||||
let index = index as usize;
|
let index = index as usize;
|
||||||
assert!(accounts_equal(&storable.account(index), &raw2[index]));
|
storable.account(index, |account| {
|
||||||
|
assert!(accounts_equal(&account, &raw2[index]));
|
||||||
|
});
|
||||||
assert_eq!(storable.pubkey(index), raw2[index].pubkey());
|
assert_eq!(storable.pubkey(index), raw2[index].pubkey());
|
||||||
assert_eq!(storable.hash(index), raw2[index].hash());
|
assert_eq!(storable.hash(index), raw2[index].hash());
|
||||||
assert_eq!(storable.slot(index), expected_slots[index]);
|
assert_eq!(storable.slot(index), expected_slots[index]);
|
||||||
|
|
|
@ -5045,11 +5045,13 @@ impl Bank {
|
||||||
let mut m = Measure::start("stakes_cache.check_and_store");
|
let mut m = Measure::start("stakes_cache.check_and_store");
|
||||||
let new_warmup_cooldown_rate_epoch = self.new_warmup_cooldown_rate_epoch();
|
let new_warmup_cooldown_rate_epoch = self.new_warmup_cooldown_rate_epoch();
|
||||||
(0..accounts.len()).for_each(|i| {
|
(0..accounts.len()).for_each(|i| {
|
||||||
self.stakes_cache.check_and_store(
|
accounts.account(i, |account| {
|
||||||
accounts.pubkey(i),
|
self.stakes_cache.check_and_store(
|
||||||
&accounts.account(i),
|
accounts.pubkey(i),
|
||||||
new_warmup_cooldown_rate_epoch,
|
&account,
|
||||||
)
|
new_warmup_cooldown_rate_epoch,
|
||||||
|
)
|
||||||
|
})
|
||||||
});
|
});
|
||||||
self.rc.accounts.store_accounts_cached(accounts);
|
self.rc.accounts.store_accounts_cached(accounts);
|
||||||
m.stop();
|
m.stop();
|
||||||
|
|
Loading…
Reference in New Issue