Adds feature reject_empty_instruction_without_program. (#21591)
This commit is contained in:
committed by
GitHub
parent
015250f96c
commit
1a4a039913
@ -9,7 +9,8 @@ use solana_sdk::{
|
|||||||
compute_budget::ComputeBudget,
|
compute_budget::ComputeBudget,
|
||||||
feature_set::{
|
feature_set::{
|
||||||
demote_program_write_locks, do_support_realloc, neon_evm_compute_budget,
|
demote_program_write_locks, do_support_realloc, neon_evm_compute_budget,
|
||||||
remove_native_loader, requestable_heap_size, tx_wide_compute_cap, FeatureSet,
|
reject_empty_instruction_without_program, remove_native_loader, requestable_heap_size,
|
||||||
|
tx_wide_compute_cap, FeatureSet,
|
||||||
},
|
},
|
||||||
hash::Hash,
|
hash::Hash,
|
||||||
instruction::{AccountMeta, CompiledInstruction, Instruction, InstructionError},
|
instruction::{AccountMeta, CompiledInstruction, Instruction, InstructionError},
|
||||||
@ -218,6 +219,13 @@ impl<'a> InvokeContext<'a> {
|
|||||||
let program_id = program_indices
|
let program_id = program_indices
|
||||||
.last()
|
.last()
|
||||||
.map(|index_of_program_id| &self.accounts[*index_of_program_id].0);
|
.map(|index_of_program_id| &self.accounts[*index_of_program_id].0);
|
||||||
|
if program_id.is_none()
|
||||||
|
&& self
|
||||||
|
.feature_set
|
||||||
|
.is_active(&reject_empty_instruction_without_program::id())
|
||||||
|
{
|
||||||
|
return Err(InstructionError::UnsupportedProgramId);
|
||||||
|
}
|
||||||
if self.invoke_stack.is_empty() {
|
if self.invoke_stack.is_empty() {
|
||||||
let mut compute_budget = self.compute_budget;
|
let mut compute_budget = self.compute_budget;
|
||||||
if !self.feature_set.is_active(&tx_wide_compute_cap::id())
|
if !self.feature_set.is_active(&tx_wide_compute_cap::id())
|
||||||
|
@ -6506,6 +6506,7 @@ pub(crate) mod tests {
|
|||||||
compute_budget::ComputeBudgetInstruction,
|
compute_budget::ComputeBudgetInstruction,
|
||||||
epoch_schedule::MINIMUM_SLOTS_PER_EPOCH,
|
epoch_schedule::MINIMUM_SLOTS_PER_EPOCH,
|
||||||
feature::Feature,
|
feature::Feature,
|
||||||
|
feature_set::reject_empty_instruction_without_program,
|
||||||
genesis_config::create_genesis_config,
|
genesis_config::create_genesis_config,
|
||||||
hash,
|
hash,
|
||||||
instruction::{AccountMeta, CompiledInstruction, Instruction, InstructionError},
|
instruction::{AccountMeta, CompiledInstruction, Instruction, InstructionError},
|
||||||
@ -15445,17 +15446,23 @@ pub(crate) mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_an_empty_transaction_without_program() {
|
fn test_an_empty_instruction_without_program() {
|
||||||
let (genesis_config, mint_keypair) = create_genesis_config(1);
|
let (genesis_config, mint_keypair) = create_genesis_config(1);
|
||||||
let bank = Bank::new_for_tests(&genesis_config);
|
|
||||||
|
|
||||||
let destination = solana_sdk::pubkey::new_rand();
|
let destination = solana_sdk::pubkey::new_rand();
|
||||||
let mut ix = system_instruction::transfer(&mint_keypair.pubkey(), &destination, 0);
|
let mut ix = system_instruction::transfer(&mint_keypair.pubkey(), &destination, 0);
|
||||||
ix.program_id = native_loader::id(); // Empty executable account chain
|
ix.program_id = native_loader::id(); // Empty executable account chain
|
||||||
|
|
||||||
let message = Message::new(&[ix], Some(&mint_keypair.pubkey()));
|
let message = Message::new(&[ix], Some(&mint_keypair.pubkey()));
|
||||||
let tx = Transaction::new(&[&mint_keypair], message, genesis_config.hash());
|
let tx = Transaction::new(&[&mint_keypair], message, genesis_config.hash());
|
||||||
|
|
||||||
|
let bank = Bank::new_for_tests(&genesis_config);
|
||||||
bank.process_transaction(&tx).unwrap();
|
bank.process_transaction(&tx).unwrap();
|
||||||
|
|
||||||
|
let mut bank = Bank::new_for_tests(&genesis_config);
|
||||||
|
bank.activate_feature(&reject_empty_instruction_without_program::id());
|
||||||
|
assert_eq!(
|
||||||
|
bank.process_transaction(&tx).unwrap_err(),
|
||||||
|
TransactionError::InstructionError(0, InstructionError::UnsupportedProgramId),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
@ -257,6 +257,10 @@ pub mod leave_nonce_on_success {
|
|||||||
solana_sdk::declare_id!("E8MkiWZNNPGU6n55jkGzyj8ghUmjCHRmDFdYYFYHxWhQ");
|
solana_sdk::declare_id!("E8MkiWZNNPGU6n55jkGzyj8ghUmjCHRmDFdYYFYHxWhQ");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub mod reject_empty_instruction_without_program {
|
||||||
|
solana_sdk::declare_id!("9kdtFSrXHQg3hKkbXkQ6trJ3Ja1xpJ22CTFSNAciEwmL");
|
||||||
|
}
|
||||||
|
|
||||||
lazy_static! {
|
lazy_static! {
|
||||||
/// Map of feature identifiers to user-visible description
|
/// Map of feature identifiers to user-visible description
|
||||||
pub static ref FEATURE_NAMES: HashMap<Pubkey, &'static str> = [
|
pub static ref FEATURE_NAMES: HashMap<Pubkey, &'static str> = [
|
||||||
@ -316,6 +320,7 @@ lazy_static! {
|
|||||||
(nonce_must_be_writable::id(), "nonce must be writable"),
|
(nonce_must_be_writable::id(), "nonce must be writable"),
|
||||||
(spl_token_v3_3_0_release::id(), "spl-token v3.3.0 release"),
|
(spl_token_v3_3_0_release::id(), "spl-token v3.3.0 release"),
|
||||||
(leave_nonce_on_success::id(), "leave nonce as is on success"),
|
(leave_nonce_on_success::id(), "leave nonce as is on success"),
|
||||||
|
(reject_empty_instruction_without_program::id(), "fail instructions which have native_loader as program_id directly"),
|
||||||
/*************** ADD NEW FEATURES HERE ***************/
|
/*************** ADD NEW FEATURES HERE ***************/
|
||||||
]
|
]
|
||||||
.iter()
|
.iter()
|
||||||
|
Reference in New Issue
Block a user