Skip to content

Commit

Permalink
Fix signature count (backport #24471) (#24477)
Browse files Browse the repository at this point in the history
* Fix signature count (#24471)

* Fix signature count

* protect the signature count futher

(cherry picked from commit 5d1adf1)

* fix conflict

Co-authored-by: Jack May <[email protected]>
Co-authored-by: Justin Starry <[email protected]>
  • Loading branch information
3 people authored Apr 19, 2022
1 parent d356837 commit 995f109
Showing 1 changed file with 80 additions and 5 deletions.
85 changes: 80 additions & 5 deletions runtime/src/bank.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4096,8 +4096,6 @@ impl Bank {
feature_set_clone_time.as_us()
);

signature_count += u64::from(tx.message().header().num_required_signatures);

let tx_wide_compute_cap = feature_set.is_active(&tx_wide_compute_cap::id());
let mut compute_budget = self
.compute_budget
Expand All @@ -4121,13 +4119,11 @@ impl Bank {
}
}

let durable_nonce_fee = nonce.as_ref().map(DurableNonceFee::from);

self.execute_loaded_transaction(
tx,
loaded_transaction,
compute_budget,
durable_nonce_fee,
nonce.as_ref().map(DurableNonceFee::from),
enable_cpi_recording,
enable_log_recording,
timings,
Expand Down Expand Up @@ -4226,6 +4222,10 @@ impl Bank {
}

if execution_result.was_executed() {
// Signature count must be accumulated only if the transaction
// is executed, otherwise a mismatched count between banking and
// replay could occur
signature_count += u64::from(tx.message().header().num_required_signatures);
executed_transactions_count += 1;
}

Expand Down Expand Up @@ -16136,6 +16136,81 @@ pub(crate) mod tests {
bank.process_transaction(&tx).unwrap();
}

#[test]
fn test_failed_compute_request_instruction() {
solana_logger::setup();
let GenesisConfigInfo {
genesis_config,
mint_keypair,
..
} = create_genesis_config_with_leader(
1_000_000_000_000_000,
&Pubkey::new_unique(),
bootstrap_validator_stake_lamports(),
);
let mut bank = Bank::new_for_tests(&genesis_config);

let payer0_keypair = Keypair::new();
let payer1_keypair = Keypair::new();
bank.transfer(10, &mint_keypair, &payer0_keypair.pubkey())
.unwrap();
bank.transfer(10, &mint_keypair, &payer1_keypair.pubkey())
.unwrap();

fn mock_ix_processor(
_first_instruction_account: usize,
_data: &[u8],
invoke_context: &mut InvokeContext,
) -> std::result::Result<(), InstructionError> {
let compute_budget = invoke_context.get_compute_budget();
assert_eq!(
*compute_budget,
ComputeBudget {
max_units: 1,
heap_size: Some(48 * 1024),
..ComputeBudget::default()
}
);
Ok(())
}
let program_id = solana_sdk::pubkey::new_rand();
bank.add_builtin("mock_program", &program_id, mock_ix_processor);

// This message will not be executed because the compute budget request is invalid
let message0 = Message::new(
&[
ComputeBudgetInstruction::request_heap_frame(1),
Instruction::new_with_bincode(program_id, &0, vec![]),
],
Some(&payer0_keypair.pubkey()),
);
// This message will be processed successfully
let message1 = Message::new(
&[
ComputeBudgetInstruction::request_units(1, 0),
ComputeBudgetInstruction::request_heap_frame(48 * 1024),
Instruction::new_with_bincode(program_id, &0, vec![]),
],
Some(&payer1_keypair.pubkey()),
);
let txs = vec![
Transaction::new(&[&payer0_keypair], message0, bank.last_blockhash()),
Transaction::new(&[&payer1_keypair], message1, bank.last_blockhash()),
];
let results = bank.process_transactions(txs.iter());

assert_eq!(
results[0],
Err(TransactionError::InstructionError(
0,
InstructionError::InvalidInstructionData
))
);
assert_eq!(results[1], Ok(()));
// two transfers and the mock program
assert_eq!(bank.signature_count(), 3);
}

#[test]
fn test_verify_and_hash_transaction_sig_len() {
let GenesisConfigInfo {
Expand Down

0 comments on commit 995f109

Please sign in to comment.