Skip to content

Commit 7dab5d1

Browse files
authoredMar 19, 2024··
Fix money returns caused by an account shrinking (#1173)
* added the possibility to return lamports back after an account has been shrunk * fixed behaviour * Fix wrong key to compare with
1 parent 7c601f7 commit 7dab5d1

File tree

1 file changed

+30
-11
lines changed

1 file changed

+30
-11
lines changed
 

‎core/rust/utils/src/account.rs

+30-11
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ use solana_program::{
33
entrypoint::ProgramResult,
44
msg,
55
program::{invoke, invoke_signed},
6+
program_error::ProgramError,
67
pubkey::Pubkey,
78
rent::Rent,
89
system_instruction,
@@ -65,20 +66,38 @@ pub fn resize_or_reallocate_account_raw<'a>(
6566
) -> ProgramResult {
6667
let rent = Rent::get()?;
6768
let new_minimum_balance = rent.minimum_balance(new_size);
69+
let lamports_diff =
70+
new_minimum_balance.abs_diff(target_account.lamports());
71+
if new_size == target_account.data_len() {
72+
return Ok(());
73+
}
6874

69-
let lamports_diff = new_minimum_balance.saturating_sub(target_account.lamports());
70-
invoke(
71-
&system_instruction::transfer(funding_account.key, target_account.key, lamports_diff),
72-
&[
73-
funding_account.clone(),
74-
target_account.clone(),
75-
system_program.clone(),
76-
],
77-
)?;
75+
let account_infos = &[
76+
funding_account.clone(),
77+
target_account.clone(),
78+
system_program.clone(),
79+
];
7880

79-
target_account.realloc(new_size, false)?;
81+
if new_size > target_account.data_len() {
82+
invoke(
83+
&system_instruction::transfer(funding_account.key, target_account.key, lamports_diff),
84+
account_infos,
85+
)?;
86+
} else if target_account.owner == system_program.key {
87+
invoke(
88+
&system_instruction::transfer(target_account.key, funding_account.key, lamports_diff),
89+
account_infos,
90+
)?;
91+
} else {
92+
(**target_account.try_borrow_mut_lamports()?)
93+
.checked_sub(lamports_diff)
94+
.ok_or(ProgramError::InvalidRealloc)?;
95+
(**funding_account.try_borrow_mut_lamports()?)
96+
.checked_add(lamports_diff)
97+
.ok_or(ProgramError::InvalidRealloc)?;
98+
}
8099

81-
Ok(())
100+
target_account.realloc(new_size, false)
82101
}
83102

84103
/// Close src_account and transfer lamports to dst_account, lifted from Solana Cookbook

0 commit comments

Comments
 (0)
Please sign in to comment.