Accounts index updates, remove pubkey when dead account (#7408)
This commit is contained in:
parent
f526c424c5
commit
0aa4dc904e
|
@ -603,8 +603,13 @@ impl AccountsDB {
|
||||||
|
|
||||||
// Recalculate reclaims with new purge set
|
// Recalculate reclaims with new purge set
|
||||||
let mut reclaims = Vec::new();
|
let mut reclaims = Vec::new();
|
||||||
|
let mut dead_keys = Vec::new();
|
||||||
for pubkey in purges.keys() {
|
for pubkey in purges.keys() {
|
||||||
reclaims.extend(accounts_index.purge(&pubkey));
|
let (new_reclaims, is_empty) = accounts_index.purge(&pubkey);
|
||||||
|
if is_empty {
|
||||||
|
dead_keys.push(*pubkey);
|
||||||
|
}
|
||||||
|
reclaims.extend(new_reclaims);
|
||||||
}
|
}
|
||||||
|
|
||||||
let last_root = accounts_index.last_root;
|
let last_root = accounts_index.last_root;
|
||||||
|
@ -612,6 +617,13 @@ impl AccountsDB {
|
||||||
drop(accounts_index);
|
drop(accounts_index);
|
||||||
drop(storage);
|
drop(storage);
|
||||||
|
|
||||||
|
if !dead_keys.is_empty() {
|
||||||
|
let mut accounts_index = self.accounts_index.write().unwrap();
|
||||||
|
for key in &dead_keys {
|
||||||
|
accounts_index.account_maps.remove(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
self.handle_reclaims(&reclaims, last_root);
|
self.handle_reclaims(&reclaims, last_root);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1916,19 +1928,13 @@ pub mod tests {
|
||||||
print_accounts("post_purge", &accounts);
|
print_accounts("post_purge", &accounts);
|
||||||
|
|
||||||
// Make sure the index is for pubkey cleared
|
// Make sure the index is for pubkey cleared
|
||||||
assert_eq!(
|
assert!(accounts
|
||||||
accounts
|
.accounts_index
|
||||||
.accounts_index
|
.read()
|
||||||
.read()
|
.unwrap()
|
||||||
.unwrap()
|
.account_maps
|
||||||
.account_maps
|
.get(&pubkey)
|
||||||
.get(&pubkey)
|
.is_none());
|
||||||
.unwrap()
|
|
||||||
.read()
|
|
||||||
.unwrap()
|
|
||||||
.len(),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
// slot 1 & 2 should not have any stores
|
// slot 1 & 2 should not have any stores
|
||||||
assert_no_stores(&accounts, 1);
|
assert_no_stores(&accounts, 1);
|
||||||
|
|
|
@ -41,11 +41,13 @@ impl<T: Clone> AccountsIndex<T> {
|
||||||
self.get_rooted_entries(&list)
|
self.get_rooted_entries(&list)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn purge(&self, pubkey: &Pubkey) -> Vec<(Slot, T)> {
|
// filter any rooted entries and return them along with a bool that indicates
|
||||||
|
// if this account has no more entries.
|
||||||
|
pub fn purge(&self, pubkey: &Pubkey) -> (Vec<(Slot, T)>, bool) {
|
||||||
let mut list = self.account_maps.get(&pubkey).unwrap().write().unwrap();
|
let mut list = self.account_maps.get(&pubkey).unwrap().write().unwrap();
|
||||||
let reclaims = self.get_rooted_entries(&list);
|
let reclaims = self.get_rooted_entries(&list);
|
||||||
list.retain(|(slot, _)| !self.is_root(*slot));
|
list.retain(|(slot, _)| !self.is_root(*slot));
|
||||||
reclaims
|
(reclaims, list.is_empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
// find the latest slot and T in a list for a given ancestor
|
// find the latest slot and T in a list for a given ancestor
|
||||||
|
@ -133,7 +135,6 @@ impl<T: Clone> AccountsIndex<T> {
|
||||||
.cloned(),
|
.cloned(),
|
||||||
);
|
);
|
||||||
slot_vec.retain(|(slot, _)| !Self::can_purge(max_root, *slot));
|
slot_vec.retain(|(slot, _)| !Self::can_purge(max_root, *slot));
|
||||||
|
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
Some(account_info)
|
Some(account_info)
|
||||||
|
@ -382,4 +383,25 @@ mod tests {
|
||||||
assert_eq!(num, 1);
|
assert_eq!(num, 1);
|
||||||
assert!(found_key);
|
assert!(found_key);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_purge() {
|
||||||
|
let key = Keypair::new();
|
||||||
|
let mut index = AccountsIndex::<u64>::default();
|
||||||
|
let mut gc = Vec::new();
|
||||||
|
assert_eq!(Some(12), index.update(1, &key.pubkey(), 12, &mut gc));
|
||||||
|
|
||||||
|
index.insert(1, &key.pubkey(), 12, &mut gc);
|
||||||
|
|
||||||
|
assert_eq!(None, index.update(1, &key.pubkey(), 10, &mut gc));
|
||||||
|
|
||||||
|
let purges = index.purge(&key.pubkey());
|
||||||
|
assert_eq!(purges, (vec![], false));
|
||||||
|
index.add_root(1);
|
||||||
|
|
||||||
|
let purges = index.purge(&key.pubkey());
|
||||||
|
assert_eq!(purges, (vec![(1, 10)], true));
|
||||||
|
|
||||||
|
assert_eq!(None, index.update(1, &key.pubkey(), 9, &mut gc));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue