Forráskód Böngészése

p-token: Add `unsafe` qualifier to validate owner (#66)

* Add unsafe qualifier

* Update validate_owner callsite
Fernando Otero 3 hónapja
szülő
commit
d05d10807f

+ 2 - 1
p-token/src/processor/close_account.rs

@@ -37,7 +37,8 @@ pub fn process_close_account(accounts: &[AccountInfo]) -> ProgramResult {
             .unwrap_or(&source_account.owner);
 
         if !source_account.is_owned_by_system_program_or_incinerator() {
-            validate_owner(authority, authority_info, remaining)?;
+            // SAFETY: `authority_info` is not currently borrowed.
+            unsafe { validate_owner(authority, authority_info, remaining)? };
         } else if destination_account_info.key() != &INCINERATOR_ID {
             return Err(ProgramError::InvalidAccountData);
         }

+ 5 - 2
p-token/src/processor/mod.rs

@@ -86,12 +86,15 @@ fn check_account_owner(account_info: &AccountInfo) -> ProgramResult {
 
 /// Validates owner(s) are present.
 ///
-/// Note that `owner_account_info` will be immutable borrowed when it represents
+///
+/// # Safety
+///
+/// The `owner_account_info` will be immutable borrowed when it represents
 /// a multisig account, therefore it should not have any mutable borrows when
 /// calling this function.
 #[inline(always)]
 #[allow(clippy::arithmetic_side_effects)]
-fn validate_owner(
+unsafe fn validate_owner(
     expected_owner: &Pubkey,
     owner_account_info: &AccountInfo,
     signers: &[AccountInfo],

+ 2 - 1
p-token/src/processor/revoke.rs

@@ -28,7 +28,8 @@ pub fn process_revoke(accounts: &[AccountInfo]) -> ProgramResult {
         return Err(TokenError::AccountFrozen.into());
     }
 
-    validate_owner(&source_account.owner, owner_info, remaining)?;
+    // SAFETY: `owner_info` is not currently borrowed.
+    unsafe { validate_owner(&source_account.owner, owner_info, remaining)? }
 
     source_account.clear_delegate();
     source_account.set_delegated_amount(0);

+ 8 - 4
p-token/src/processor/set_authority.rs

@@ -50,7 +50,8 @@ pub fn process_set_authority(accounts: &[AccountInfo], instruction_data: &[u8])
 
         match authority_type {
             AuthorityType::AccountOwner => {
-                validate_owner(&account.owner, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(&account.owner, authority_info, remaining)? };
 
                 if let Some(authority) = new_authority {
                     account.owner = *authority;
@@ -67,7 +68,8 @@ pub fn process_set_authority(accounts: &[AccountInfo], instruction_data: &[u8])
             }
             AuthorityType::CloseAccount => {
                 let authority = account.close_authority().unwrap_or(&account.owner);
-                validate_owner(authority, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(authority, authority_info, remaining)? };
 
                 if let Some(authority) = new_authority {
                     account.set_close_authority(authority);
@@ -90,7 +92,8 @@ pub fn process_set_authority(accounts: &[AccountInfo], instruction_data: &[u8])
                 // mint_authority.
                 let mint_authority = mint.mint_authority().ok_or(TokenError::FixedSupply)?;
 
-                validate_owner(mint_authority, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(mint_authority, authority_info, remaining)? };
 
                 if let Some(authority) = new_authority {
                     mint.set_mint_authority(authority);
@@ -105,7 +108,8 @@ pub fn process_set_authority(accounts: &[AccountInfo], instruction_data: &[u8])
                     .freeze_authority()
                     .ok_or(TokenError::MintCannotFreeze)?;
 
-                validate_owner(freeze_authority, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(freeze_authority, authority_info, remaining)? };
 
                 if let Some(authority) = new_authority {
                     mint.set_freeze_authority(authority);

+ 2 - 1
p-token/src/processor/shared/approve.rs

@@ -69,7 +69,8 @@ pub fn process_approve(
         }
     }
 
-    validate_owner(&source_account.owner, owner_info, remaining)?;
+    // SAFETY: `owner_info` is not currently borrowed.
+    unsafe { validate_owner(&source_account.owner, owner_info, remaining)? };
 
     // Sets the delegate and delegated amount.
 

+ 4 - 2
p-token/src/processor/shared/burn.rs

@@ -54,7 +54,8 @@ pub fn process_burn(
     if !source_account.is_owned_by_system_program_or_incinerator() {
         match source_account.delegate() {
             Some(delegate) if authority_info.key() == delegate => {
-                validate_owner(delegate, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(delegate, authority_info, remaining)? };
 
                 let delegated_amount = source_account
                     .delegated_amount()
@@ -67,7 +68,8 @@ pub fn process_burn(
                 }
             }
             _ => {
-                validate_owner(&source_account.owner, authority_info, remaining)?;
+                // SAFETY: `authority_info` is not currently borrowed.
+                unsafe { validate_owner(&source_account.owner, authority_info, remaining)? };
             }
         }
     }

+ 2 - 1
p-token/src/processor/shared/mint_to.rs

@@ -48,7 +48,8 @@ pub fn process_mint_to(
     }
 
     match mint.mint_authority() {
-        Some(mint_authority) => validate_owner(mint_authority, owner_info, remaining)?,
+        // SAFETY: `owner_info` is not currently borrowed.
+        Some(mint_authority) => unsafe { validate_owner(mint_authority, owner_info, remaining)? },
         None => return Err(TokenError::FixedSupply.into()),
     }
 

+ 2 - 1
p-token/src/processor/shared/toggle_account_state.rs

@@ -35,7 +35,8 @@ pub fn process_toggle_account_state(accounts: &[AccountInfo], freeze: bool) -> P
     let mint = unsafe { load::<Mint>(mint_info.borrow_data_unchecked())? };
 
     match mint.freeze_authority() {
-        Some(authority) => validate_owner(authority, authority_info, remaining),
+        // SAFETY: `authority_info` is not currently borrowed.
+        Some(authority) => unsafe { validate_owner(authority, authority_info, remaining) },
         None => Err(TokenError::MintCannotFreeze.into()),
     }?;
 

+ 4 - 2
p-token/src/processor/shared/transfer.rs

@@ -127,7 +127,8 @@ pub fn process_transfer(
     // Validates the authority (delegate or owner).
 
     if source_account.delegate() == Some(authority_info.key()) {
-        validate_owner(authority_info.key(), authority_info, remaining)?;
+        // SAFETY: `authority_info` is not currently borrowed.
+        unsafe { validate_owner(authority_info.key(), authority_info, remaining)? };
 
         let delegated_amount = source_account
             .delegated_amount()
@@ -142,7 +143,8 @@ pub fn process_transfer(
             }
         }
     } else {
-        validate_owner(&source_account.owner, authority_info, remaining)?;
+        // SAFETY: `authority_info` is not currently borrowed.
+        unsafe { validate_owner(&source_account.owner, authority_info, remaining)? };
     }
 
     if self_transfer || amount == 0 {

+ 6 - 3
p-token/src/processor/withdraw_excess_lamports.rs

@@ -30,7 +30,8 @@ pub fn process_withdraw_excess_lamports(accounts: &[AccountInfo]) -> ProgramResu
                 return Err(TokenError::NativeNotSupported.into());
             }
 
-            validate_owner(&account.owner, authority_info, remaining)?;
+            // SAFETY: `authority_info` is not currently borrowed.
+            unsafe { validate_owner(&account.owner, authority_info, remaining)? };
         }
         Mint::LEN => {
             // SAFETY: `source_data` has the same length as `Mint`.
@@ -38,7 +39,8 @@ pub fn process_withdraw_excess_lamports(accounts: &[AccountInfo]) -> ProgramResu
 
             match mint.mint_authority() {
                 Some(mint_authority) => {
-                    validate_owner(mint_authority, authority_info, remaining)?;
+                    // SAFETY: `authority_info` is not currently borrowed.
+                    unsafe { validate_owner(mint_authority, authority_info, remaining)? };
                 }
                 None if source_account_info == authority_info => {
                     // Comparing whether the AccountInfo's "point" to the same account or
@@ -58,7 +60,8 @@ pub fn process_withdraw_excess_lamports(accounts: &[AccountInfo]) -> ProgramResu
             }
         }
         Multisig::LEN => {
-            validate_owner(source_account_info.key(), authority_info, remaining)?;
+            // SAFETY: `authority_info` is not currently mutably borrowed.
+            unsafe { validate_owner(source_account_info.key(), authority_info, remaining)? };
         }
         _ => return Err(TokenError::InvalidState.into()),
     }