anchor_lang/
lib.rs

1#![cfg_attr(docsrs, feature(doc_cfg))]
2
3//! Anchor ⚓ is a framework for Solana's Sealevel runtime providing several
4//! convenient developer tools.
5//!
6//! - Rust eDSL for writing safe, secure, and high level Solana programs
7//! - [IDL](https://en.wikipedia.org/wiki/Interface_description_language) specification
8//! - TypeScript package for generating clients from IDL
9//! - CLI and workspace management for developing complete applications
10//!
11//! If you're familiar with developing in Ethereum's
12//! [Solidity](https://docs.soliditylang.org/en/v0.7.4/),
13//! [Truffle](https://www.trufflesuite.com/),
14//! [web3.js](https://github.com/ethereum/web3.js) or Parity's
15//! [Ink!](https://github.com/paritytech/ink), then the experience will be
16//! familiar. Although the syntax and semantics are targeted at Solana, the high
17//! level workflow of writing RPC request handlers, emitting an IDL, and
18//! generating clients from IDL is the same.
19//!
20//! For detailed tutorials and examples on how to use Anchor, see the guided
21//! [tutorials](https://anchor-lang.com) or examples in the GitHub
22//! [repository](https://github.com/coral-xyz/anchor).
23//!
24//! Presented here are the Rust primitives for building on Solana.
25
26extern crate self as anchor_lang;
27
28use crate::solana_program::account_info::AccountInfo;
29use crate::solana_program::instruction::AccountMeta;
30use crate::solana_program::program_error::ProgramError;
31use crate::solana_program::pubkey::Pubkey;
32use bytemuck::{Pod, Zeroable};
33use std::{collections::BTreeSet, fmt::Debug, io::Write};
34
35mod account_meta;
36pub mod accounts;
37mod bpf_upgradeable_state;
38mod bpf_writer;
39mod common;
40pub mod context;
41pub mod error;
42#[doc(hidden)]
43pub mod event;
44#[doc(hidden)]
45pub mod idl;
46pub mod signature_verification;
47pub mod system_program;
48mod vec;
49
50#[cfg(feature = "lazy-account")]
51mod lazy;
52
53pub use crate::bpf_upgradeable_state::*;
54pub use anchor_attribute_access_control::access_control;
55pub use anchor_attribute_account::{account, declare_id, pubkey, zero_copy};
56pub use anchor_attribute_constant::constant;
57pub use anchor_attribute_error::*;
58pub use anchor_attribute_event::{emit, event};
59pub use anchor_attribute_program::{declare_program, instruction, program};
60pub use anchor_derive_accounts::Accounts;
61pub use anchor_derive_serde::{AnchorDeserialize, AnchorSerialize};
62pub use anchor_derive_space::InitSpace;
63pub use const_crypto::ed25519::derive_program_address;
64
65/// Borsh is the default serialization format for instructions and accounts.
66pub use borsh::de::BorshDeserialize as AnchorDeserialize;
67pub use borsh::ser::BorshSerialize as AnchorSerialize;
68pub mod solana_program {
69    pub use solana_feature_gate_interface as feature;
70
71    pub use {
72        solana_account_info as account_info, solana_clock as clock, solana_msg::msg,
73        solana_program_entrypoint as entrypoint, solana_program_entrypoint::entrypoint,
74        solana_program_error as program_error, solana_program_memory as program_memory,
75        solana_program_option as program_option, solana_program_pack as program_pack,
76        solana_pubkey as pubkey, solana_sdk_ids::system_program,
77        solana_system_interface::instruction as system_instruction,
78    };
79    pub mod instruction {
80        pub use solana_instruction::*;
81        /// Get the current stack height, transaction-level instructions are height
82        /// TRANSACTION_LEVEL_STACK_HEIGHT, fist invoked inner instruction is height
83        /// TRANSACTION_LEVEL_STACK_HEIGHT + 1, etc...
84        pub fn get_stack_height() -> usize {
85            #[cfg(target_os = "solana")]
86            unsafe {
87                solana_instruction::syscalls::sol_get_stack_height() as usize
88            }
89
90            #[cfg(not(target_os = "solana"))]
91            {
92                solana_sysvar::program_stubs::sol_get_stack_height() as usize
93            }
94        }
95    }
96    pub mod rent {
97        pub use solana_sysvar::rent::*;
98    }
99    pub mod program {
100        pub use solana_cpi::*;
101        pub use solana_invoke::{invoke, invoke_signed, invoke_signed_unchecked, invoke_unchecked};
102    }
103
104    pub mod bpf_loader_upgradeable {
105        #[allow(deprecated)]
106        pub use solana_loader_v3_interface::{
107            get_program_data_address,
108            instruction::{
109                close, close_any, create_buffer, deploy_with_max_program_len, extend_program,
110                is_close_instruction, is_set_authority_checked_instruction,
111                is_set_authority_instruction, is_upgrade_instruction, set_buffer_authority,
112                set_buffer_authority_checked, set_upgrade_authority, set_upgrade_authority_checked,
113                upgrade, write,
114            },
115            state::UpgradeableLoaderState,
116        };
117        pub use solana_sdk_ids::bpf_loader_upgradeable::{check_id, id, ID};
118    }
119
120    pub mod log {
121        pub use solana_msg::{msg, sol_log};
122        /// Print some slices as base64.
123        pub fn sol_log_data(data: &[&[u8]]) {
124            #[cfg(target_os = "solana")]
125            unsafe {
126                solana_define_syscall::definitions::sol_log_data(
127                    data as *const _ as *const u8,
128                    data.len() as u64,
129                )
130            };
131
132            #[cfg(not(target_os = "solana"))]
133            core::hint::black_box(data);
134        }
135    }
136    pub mod sysvar {
137        pub use solana_sysvar_id::{declare_deprecated_sysvar_id, declare_sysvar_id, SysvarId};
138        pub mod instructions {
139            pub use solana_instruction::{BorrowedAccountMeta, BorrowedInstruction};
140            #[cfg(not(target_os = "solana"))]
141            pub use solana_instructions_sysvar::construct_instructions_data;
142        }
143    }
144}
145
146#[cfg(feature = "event-cpi")]
147pub use anchor_attribute_event::{emit_cpi, event_cpi};
148
149#[cfg(feature = "idl-build")]
150pub use idl::IdlBuild;
151
152#[cfg(feature = "interface-instructions")]
153pub use anchor_attribute_program::interface;
154
155pub type Result<T> = std::result::Result<T, error::Error>;
156
157// Deprecated message for AccountInfo usage in Accounts struct
158#[deprecated(
159    note = "Use `UncheckedAccount` instead of `AccountInfo` for safer unchecked accounts."
160)]
161pub fn deprecated_account_info_usage() {}
162
163/// A data structure of validated accounts that can be deserialized from the
164/// input to a Solana program. Implementations of this trait should perform any
165/// and all requisite constraint checks on accounts to ensure the accounts
166/// maintain any invariants required for the program to run securely. In most
167/// cases, it's recommended to use the [`Accounts`](./derive.Accounts.html)
168/// derive macro to implement this trait.
169///
170/// Generics:
171/// -   `B`: the type of the PDA bumps cache struct generated by the `Accounts` struct.
172///     For example,
173/// ```rust,ignore
174/// pub struct Example<'info> {
175///     #[account(
176///         init,
177///         seeds = [...],
178///         bump,
179///     )]
180///     pub pda_1: UncheckedAccount<'info>,
181///     pub not_pda: UncheckedAccount<'info>,
182/// }
183/// ```
184///
185///    generates:
186///
187/// ```rust,ignore
188/// pub struct ExampleBumps {
189///     pub pda_1: u8,
190/// }
191/// ```
192pub trait Accounts<'info, B>: ToAccountMetas + ToAccountInfos<'info> + Sized {
193    /// Returns the validated accounts struct. What constitutes "valid" is
194    /// program dependent. However, users of these types should never have to
195    /// worry about account substitution attacks. For example, if a program
196    /// expects a `Mint` account from the SPL token program  in a particular
197    /// field, then it should be impossible for this method to return `Ok` if
198    /// any other account type is given--from the SPL token program or elsewhere.
199    ///
200    /// `program_id` is the currently executing program. `accounts` is the
201    /// set of accounts to construct the type from. For every account used,
202    /// the implementation should mutate the slice, consuming the used entry
203    /// so that it cannot be used again.
204    fn try_accounts(
205        program_id: &Pubkey,
206        accounts: &mut &'info [AccountInfo<'info>],
207        ix_data: &[u8],
208        bumps: &mut B,
209        reallocs: &mut BTreeSet<Pubkey>,
210    ) -> Result<Self>;
211}
212
213/// Associated bump seeds for `Accounts`.
214pub trait Bumps {
215    /// Struct to hold account bump seeds.
216    type Bumps: Sized + Debug;
217}
218
219/// The exit procedure for an account. Any cleanup or persistence to storage
220/// should be done here.
221pub trait AccountsExit<'info>: ToAccountMetas + ToAccountInfos<'info> {
222    /// `program_id` is the currently executing program.
223    fn exit(&self, _program_id: &Pubkey) -> Result<()> {
224        // no-op
225        Ok(())
226    }
227}
228
229/// The close procedure to initiate garabage collection of an account, allowing
230/// one to retrieve the rent exemption.
231pub trait AccountsClose<'info>: ToAccountInfos<'info> {
232    fn close(&self, sol_destination: AccountInfo<'info>) -> Result<()>;
233}
234
235/// Transformation to
236/// [`AccountMeta`](../solana_program/instruction/struct.AccountMeta.html)
237/// structs.
238pub trait ToAccountMetas {
239    /// `is_signer` is given as an optional override for the signer meta field.
240    /// This covers the edge case when a program-derived-address needs to relay
241    /// a transaction from a client to another program but sign the transaction
242    /// before the relay. The client cannot mark the field as a signer, and so
243    /// we have to override the is_signer meta field given by the client.
244    fn to_account_metas(&self, is_signer: Option<bool>) -> Vec<AccountMeta>;
245}
246
247/// Transformation to
248/// [`AccountInfo`](../solana_program/account_info/struct.AccountInfo.html)
249/// structs.
250pub trait ToAccountInfos<'info> {
251    fn to_account_infos(&self) -> Vec<AccountInfo<'info>>;
252}
253
254/// Transformation to an `AccountInfo` struct.
255pub trait ToAccountInfo<'info> {
256    fn to_account_info(&self) -> AccountInfo<'info>;
257}
258
259impl<'info, T> ToAccountInfo<'info> for T
260where
261    T: AsRef<AccountInfo<'info>>,
262{
263    fn to_account_info(&self) -> AccountInfo<'info> {
264        self.as_ref().clone()
265    }
266}
267
268/// Lamports related utility methods for accounts.
269pub trait Lamports<'info>: AsRef<AccountInfo<'info>> {
270    /// Get the lamports of the account.
271    fn get_lamports(&self) -> u64 {
272        self.as_ref().lamports()
273    }
274
275    /// Add lamports to the account.
276    ///
277    /// This method is useful for transferring lamports from a PDA.
278    ///
279    /// # Requirements
280    ///
281    /// 1. The account must be marked `mut`.
282    /// 2. The total lamports **before** the transaction must equal to total lamports **after**
283    ///    the transaction.
284    /// 3. `lamports` field of the account info should not currently be borrowed.
285    ///
286    /// See [`Lamports::sub_lamports`] for subtracting lamports.
287    fn add_lamports(&self, amount: u64) -> Result<&Self> {
288        **self.as_ref().try_borrow_mut_lamports()? = self
289            .get_lamports()
290            .checked_add(amount)
291            .ok_or(ProgramError::ArithmeticOverflow)?;
292        Ok(self)
293    }
294
295    /// Subtract lamports from the account.
296    ///
297    /// This method is useful for transferring lamports from a PDA.
298    ///
299    /// # Requirements
300    ///
301    /// 1. The account must be owned by the executing program.
302    /// 2. The account must be marked `mut`.
303    /// 3. The total lamports **before** the transaction must equal to total lamports **after**
304    ///    the transaction.
305    /// 4. `lamports` field of the account info should not currently be borrowed.
306    ///
307    /// See [`Lamports::add_lamports`] for adding lamports.
308    fn sub_lamports(&self, amount: u64) -> Result<&Self> {
309        **self.as_ref().try_borrow_mut_lamports()? = self
310            .get_lamports()
311            .checked_sub(amount)
312            .ok_or(ProgramError::ArithmeticOverflow)?;
313        Ok(self)
314    }
315}
316
317impl<'info, T: AsRef<AccountInfo<'info>>> Lamports<'info> for T {}
318
319/// A data structure that can be serialized and stored into account storage,
320/// i.e. an
321/// [`AccountInfo`](../solana_program/account_info/struct.AccountInfo.html#structfield.data)'s
322/// mutable data slice.
323///
324/// Implementors of this trait should ensure that any subsequent usage of the
325/// `AccountDeserialize` trait succeeds if and only if the account is of the
326/// correct type.
327///
328/// In most cases, one can use the default implementation provided by the
329/// [`#[account]`](./attr.account.html) attribute.
330pub trait AccountSerialize {
331    /// Serializes the account data into `writer`.
332    fn try_serialize<W: Write>(&self, _writer: &mut W) -> Result<()> {
333        Ok(())
334    }
335}
336
337/// A data structure that can be deserialized and stored into account storage,
338/// i.e. an
339/// [`AccountInfo`](../solana_program/account_info/struct.AccountInfo.html#structfield.data)'s
340/// mutable data slice.
341pub trait AccountDeserialize: Sized {
342    /// Deserializes previously initialized account data. Should fail for all
343    /// uninitialized accounts, where the bytes are zeroed. Implementations
344    /// should be unique to a particular account type so that one can never
345    /// successfully deserialize the data of one account type into another.
346    /// For example, if the SPL token program were to implement this trait,
347    /// it should be impossible to deserialize a `Mint` account into a token
348    /// `Account`.
349    fn try_deserialize(buf: &mut &[u8]) -> Result<Self> {
350        Self::try_deserialize_unchecked(buf)
351    }
352
353    /// Deserializes account data without checking the account discriminator.
354    /// This should only be used on account initialization, when the bytes of
355    /// the account are zeroed.
356    fn try_deserialize_unchecked(buf: &mut &[u8]) -> Result<Self>;
357}
358
359/// An account data structure capable of zero copy deserialization.
360pub trait ZeroCopy: Discriminator + Copy + Clone + Zeroable + Pod {}
361
362/// Calculates the data for an instruction invocation, where the data is
363/// `Discriminator + BorshSerialize(args)`. `args` is a borsh serialized
364/// struct of named fields for each argument given to an instruction.
365pub trait InstructionData: Discriminator + AnchorSerialize {
366    fn data(&self) -> Vec<u8> {
367        let mut data = Vec::with_capacity(256);
368        data.extend_from_slice(Self::DISCRIMINATOR);
369        self.serialize(&mut data).unwrap();
370        data
371    }
372
373    /// Clears `data` and writes instruction data to it.
374    ///
375    /// We use a `Vec<u8>`` here because of the additional flexibility of re-allocation (only if
376    /// necessary), and because the data field in `Instruction` expects a `Vec<u8>`.
377    fn write_to(&self, mut data: &mut Vec<u8>) {
378        data.clear();
379        data.extend_from_slice(Self::DISCRIMINATOR);
380        self.serialize(&mut data).unwrap()
381    }
382}
383
384/// An event that can be emitted via a Solana log. See [`emit!`](crate::prelude::emit) for an example.
385pub trait Event: AnchorSerialize + AnchorDeserialize + Discriminator {
386    fn data(&self) -> Vec<u8>;
387}
388
389/// Unique identifier for a type.
390///
391/// This is not a trait you should derive manually, as various Anchor macros already derive it
392/// internally.
393///
394/// Prior to Anchor v0.31, discriminators were always 8 bytes in size. However, starting with Anchor
395/// v0.31, it is possible to override the default discriminators, and discriminator length is no
396/// longer fixed, which means this trait can also be implemented for non-Anchor programs.
397///
398/// It's important that the discriminator is always unique for the type you're implementing it
399/// for. While the discriminator can be at any length (including zero), the IDL generation does not
400/// currently allow empty discriminators for safety and convenience reasons. However, the trait
401/// definition still allows empty discriminators because some non-Anchor programs, e.g. the SPL
402/// Token program, don't have account discriminators. In that case, safety checks should never
403/// depend on the discriminator.
404pub trait Discriminator {
405    /// Discriminator slice.
406    ///
407    /// See [`Discriminator`] trait documentation for more information.
408    const DISCRIMINATOR: &'static [u8];
409}
410
411/// Defines the space of an account for initialization.
412pub trait Space {
413    const INIT_SPACE: usize;
414}
415
416/// Bump seed for program derived addresses.
417pub trait Bump {
418    fn seed(&self) -> u8;
419}
420
421/// Defines an address expected to own an account.
422pub trait Owner {
423    fn owner() -> Pubkey;
424}
425
426/// Defines a list of addresses expected to own an account.
427pub trait Owners {
428    fn owners() -> &'static [Pubkey];
429}
430
431/// Defines a trait for checking the owner of a program.
432pub trait CheckOwner {
433    fn check_owner(owner: &Pubkey) -> Result<()>;
434}
435
436impl<T: Owners> CheckOwner for T {
437    fn check_owner(owner: &Pubkey) -> Result<()> {
438        if !Self::owners().contains(owner) {
439            Err(
440                error::Error::from(error::ErrorCode::AccountOwnedByWrongProgram)
441                    .with_account_name(*owner),
442            )
443        } else {
444            Ok(())
445        }
446    }
447}
448
449/// Defines the id of a program.
450pub trait Id {
451    fn id() -> Pubkey;
452}
453
454/// Defines the possible ids of a program.
455pub trait Ids {
456    fn ids() -> &'static [Pubkey];
457}
458
459/// Defines a trait for checking the id of a program.
460pub trait CheckId {
461    fn check_id(id: &Pubkey) -> Result<()>;
462}
463
464impl<T: Ids> CheckId for T {
465    fn check_id(id: &Pubkey) -> Result<()> {
466        if !Self::ids().contains(id) {
467            Err(error::Error::from(error::ErrorCode::InvalidProgramId).with_account_name(*id))
468        } else {
469            Ok(())
470        }
471    }
472}
473
474/// Defines the Pubkey of an account.
475pub trait Key {
476    fn key(&self) -> Pubkey;
477}
478
479impl Key for Pubkey {
480    fn key(&self) -> Pubkey {
481        *self
482    }
483}
484
485/// The prelude contains all commonly used components of the crate.
486/// All programs should include it via `anchor_lang::prelude::*;`.
487pub mod prelude {
488    pub use super::{
489        access_control, account, accounts::account::Account,
490        accounts::account_loader::AccountLoader, accounts::interface::Interface,
491        accounts::interface_account::InterfaceAccount, accounts::program::Program,
492        accounts::signer::Signer, accounts::system_account::SystemAccount,
493        accounts::sysvar::Sysvar, accounts::unchecked_account::UncheckedAccount, constant,
494        context::Context, context::CpiContext, declare_id, declare_program, emit, err, error,
495        event, instruction, program, pubkey, require, require_eq, require_gt, require_gte,
496        require_keys_eq, require_keys_neq, require_neq,
497        solana_program::bpf_loader_upgradeable::UpgradeableLoaderState, source,
498        system_program::System, zero_copy, AccountDeserialize, AccountSerialize, Accounts,
499        AccountsClose, AccountsExit, AnchorDeserialize, AnchorSerialize, Discriminator, Id,
500        InitSpace, Key, Lamports, Owner, ProgramData, Result, Space, ToAccountInfo, ToAccountInfos,
501        ToAccountMetas,
502    };
503    pub use crate::solana_program::account_info::{next_account_info, AccountInfo};
504    pub use crate::solana_program::instruction::AccountMeta;
505    pub use crate::solana_program::program_error::ProgramError;
506    pub use crate::solana_program::pubkey::Pubkey;
507    pub use crate::solana_program::*;
508    pub use anchor_attribute_error::*;
509    pub use borsh;
510    pub use error::*;
511    pub use solana_clock::Clock;
512    pub use solana_instructions_sysvar::Instructions;
513    pub use solana_stake_interface::stake_history::StakeHistory;
514    pub use solana_sysvar::epoch_schedule::EpochSchedule;
515    pub use solana_sysvar::rent::Rent;
516    pub use solana_sysvar::rewards::Rewards;
517    pub use solana_sysvar::slot_hashes::SlotHashes;
518    pub use solana_sysvar::slot_history::SlotHistory;
519    pub use solana_sysvar::Sysvar as SolanaSysvar;
520    pub use thiserror;
521
522    #[cfg(feature = "event-cpi")]
523    pub use super::{emit_cpi, event_cpi};
524
525    #[cfg(feature = "idl-build")]
526    pub use super::idl::IdlBuild;
527
528    #[cfg(feature = "interface-instructions")]
529    pub use super::interface;
530
531    #[cfg(feature = "lazy-account")]
532    pub use super::accounts::lazy_account::LazyAccount;
533}
534
535/// Internal module used by macros and unstable apis.
536#[doc(hidden)]
537pub mod __private {
538    pub use anchor_attribute_account::ZeroCopyAccessor;
539    pub use base64;
540    pub use bytemuck;
541
542    pub use crate::{bpf_writer::BpfWriter, common::is_closed};
543
544    use crate::solana_program::pubkey::Pubkey;
545
546    // Used to calculate the maximum between two expressions.
547    // It is necessary for the calculation of the enum space.
548    #[doc(hidden)]
549    pub const fn max(a: usize, b: usize) -> usize {
550        [a, b][(a < b) as usize]
551    }
552
553    // Very experimental trait.
554    #[doc(hidden)]
555    pub trait ZeroCopyAccessor<Ty> {
556        fn get(&self) -> Ty;
557        fn set(input: &Ty) -> Self;
558    }
559
560    #[doc(hidden)]
561    impl ZeroCopyAccessor<Pubkey> for [u8; 32] {
562        fn get(&self) -> Pubkey {
563            Pubkey::from(*self)
564        }
565        fn set(input: &Pubkey) -> [u8; 32] {
566            input.to_bytes()
567        }
568    }
569
570    #[cfg(feature = "lazy-account")]
571    pub use crate::lazy::Lazy;
572    #[cfg(feature = "lazy-account")]
573    pub use anchor_derive_serde::Lazy;
574
575    /// Trait for compile-time type equality checking.
576    /// Used to enforce that instruction argument types match the `#[instruction(...)]` attribute types.
577    #[doc(hidden)]
578    #[diagnostic::on_unimplemented(
579        message = "instruction handler argument type `{Self}` does not match `#[instruction(...)]` attribute type `{T}`",
580        label = "expected `{T}` here based on `#[instruction(...)]` attribute, found `{Self}`",
581        note = "ensure `#[instruction(..)]` argument types match those of the instruction handler"
582    )]
583    pub trait IsSameType<T> {}
584
585    impl<T> IsSameType<T> for T {}
586}
587
588/// Ensures a condition is true, otherwise returns with the given error.
589/// Use this with or without a custom error type.
590///
591/// # Example
592/// ```ignore
593/// // Instruction function
594/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
595///     require!(ctx.accounts.data.mutation_allowed, MyError::MutationForbidden);
596///     ctx.accounts.data.data = data;
597///     Ok(())
598/// }
599///
600/// // An enum for custom error codes
601/// #[error_code]
602/// pub enum MyError {
603///     MutationForbidden
604/// }
605///
606/// // An account definition
607/// #[account]
608/// #[derive(Default)]
609/// pub struct MyData {
610///     mutation_allowed: bool,
611///     data: u64
612/// }
613///
614/// // An account validation struct
615/// #[derive(Accounts)]
616/// pub struct SetData<'info> {
617///     #[account(mut)]
618///     pub data: Account<'info, MyData>
619/// }
620/// ```
621#[macro_export]
622macro_rules! require {
623    ($invariant:expr, $error:tt $(,)?) => {
624        if !($invariant) {
625            return Err(anchor_lang::error!($crate::ErrorCode::$error));
626        }
627    };
628    ($invariant:expr, $error:expr $(,)?) => {
629        if !($invariant) {
630            return Err(anchor_lang::error!($error));
631        }
632    };
633}
634
635/// Ensures two NON-PUBKEY values are equal.
636///
637/// Use [require_keys_eq](crate::prelude::require_keys_eq)
638/// to compare two pubkeys.
639///
640/// Can be used with or without a custom error code.
641///
642/// # Example
643/// ```rust,ignore
644/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
645///     require_eq!(ctx.accounts.data.data, 0);
646///     ctx.accounts.data.data = data;
647///     Ok(())
648/// }
649/// ```
650#[macro_export]
651macro_rules! require_eq {
652    ($value1: expr, $value2: expr, $error_code:expr $(,)?) => {
653        if $value1 != $value2 {
654            return Err(error!($error_code).with_values(($value1, $value2)));
655        }
656    };
657    ($value1: expr, $value2: expr $(,)?) => {
658        if $value1 != $value2 {
659            return Err(error!(anchor_lang::error::ErrorCode::RequireEqViolated)
660                .with_values(($value1, $value2)));
661        }
662    };
663}
664
665/// Ensures two NON-PUBKEY values are not equal.
666///
667/// Use [require_keys_neq](crate::prelude::require_keys_neq)
668/// to compare two pubkeys.
669///
670/// Can be used with or without a custom error code.
671///
672/// # Example
673/// ```rust,ignore
674/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
675///     require_neq!(ctx.accounts.data.data, 0);
676///     ctx.accounts.data.data = data;
677///     Ok(());
678/// }
679/// ```
680#[macro_export]
681macro_rules! require_neq {
682    ($value1: expr, $value2: expr, $error_code: expr $(,)?) => {
683        if $value1 == $value2 {
684            return Err(error!($error_code).with_values(($value1, $value2)));
685        }
686    };
687    ($value1: expr, $value2: expr $(,)?) => {
688        if $value1 == $value2 {
689            return Err(error!(anchor_lang::error::ErrorCode::RequireNeqViolated)
690                .with_values(($value1, $value2)));
691        }
692    };
693}
694
695/// Ensures two pubkeys values are equal.
696///
697/// Use [require_eq](crate::prelude::require_eq)
698/// to compare two non-pubkey values.
699///
700/// Can be used with or without a custom error code.
701///
702/// # Example
703/// ```rust,ignore
704/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
705///     require_keys_eq!(ctx.accounts.data.authority.key(), ctx.accounts.authority.key());
706///     ctx.accounts.data.data = data;
707///     Ok(())
708/// }
709/// ```
710#[macro_export]
711macro_rules! require_keys_eq {
712    ($value1: expr, $value2: expr, $error_code:expr $(,)?) => {
713        if $value1 != $value2 {
714            return Err(error!($error_code).with_pubkeys(($value1, $value2)));
715        }
716    };
717    ($value1: expr, $value2: expr $(,)?) => {
718        if $value1 != $value2 {
719            return Err(error!(anchor_lang::error::ErrorCode::RequireKeysEqViolated)
720                .with_pubkeys(($value1, $value2)));
721        }
722    };
723}
724
725/// Ensures two pubkeys are not equal.
726///
727/// Use [require_neq](crate::prelude::require_neq)
728/// to compare two non-pubkey values.
729///
730/// Can be used with or without a custom error code.
731///
732/// # Example
733/// ```rust,ignore
734/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
735///     require_keys_neq!(ctx.accounts.data.authority.key(), ctx.accounts.other.key());
736///     ctx.accounts.data.data = data;
737///     Ok(())
738/// }
739/// ```
740#[macro_export]
741macro_rules! require_keys_neq {
742    ($value1: expr, $value2: expr, $error_code: expr $(,)?) => {
743        if $value1 == $value2 {
744            return Err(error!($error_code).with_pubkeys(($value1, $value2)));
745        }
746    };
747    ($value1: expr, $value2: expr $(,)?) => {
748        if $value1 == $value2 {
749            return Err(
750                error!(anchor_lang::error::ErrorCode::RequireKeysNeqViolated)
751                    .with_pubkeys(($value1, $value2)),
752            );
753        }
754    };
755}
756
757/// Ensures the first NON-PUBKEY value is greater than the second
758/// NON-PUBKEY value.
759///
760/// To include an equality check, use [require_gte](crate::require_gte).
761///
762/// Can be used with or without a custom error code.
763///
764/// # Example
765/// ```rust,ignore
766/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
767///     require_gt!(ctx.accounts.data.data, 0);
768///     ctx.accounts.data.data = data;
769///     Ok(());
770/// }
771/// ```
772#[macro_export]
773macro_rules! require_gt {
774    ($value1: expr, $value2: expr, $error_code: expr $(,)?) => {
775        if $value1 <= $value2 {
776            return Err(error!($error_code).with_values(($value1, $value2)));
777        }
778    };
779    ($value1: expr, $value2: expr $(,)?) => {
780        if $value1 <= $value2 {
781            return Err(error!(anchor_lang::error::ErrorCode::RequireGtViolated)
782                .with_values(($value1, $value2)));
783        }
784    };
785}
786
787/// Ensures the first NON-PUBKEY value is greater than or equal
788/// to the second NON-PUBKEY value.
789///
790/// Can be used with or without a custom error code.
791///
792/// # Example
793/// ```rust,ignore
794/// pub fn set_data(ctx: Context<SetData>, data: u64) -> Result<()> {
795///     require_gte!(ctx.accounts.data.data, 1);
796///     ctx.accounts.data.data = data;
797///     Ok(());
798/// }
799/// ```
800#[macro_export]
801macro_rules! require_gte {
802    ($value1: expr, $value2: expr, $error_code: expr $(,)?) => {
803        if $value1 < $value2 {
804            return Err(error!($error_code).with_values(($value1, $value2)));
805        }
806    };
807    ($value1: expr, $value2: expr $(,)?) => {
808        if $value1 < $value2 {
809            return Err(error!(anchor_lang::error::ErrorCode::RequireGteViolated)
810                .with_values(($value1, $value2)));
811        }
812    };
813}
814
815/// Returns with the given error.
816/// Use this with a custom error type.
817///
818/// # Example
819/// ```ignore
820/// // Instruction function
821/// pub fn example(ctx: Context<Example>) -> Result<()> {
822///     err!(MyError::SomeError)
823/// }
824///
825/// // An enum for custom error codes
826/// #[error_code]
827/// pub enum MyError {
828///     SomeError
829/// }
830/// ```
831#[macro_export]
832macro_rules! err {
833    ($error:tt $(,)?) => {
834        Err(anchor_lang::error!($crate::ErrorCode::$error))
835    };
836    ($error:expr $(,)?) => {
837        Err(anchor_lang::error!($error))
838    };
839}
840
841/// Creates a [`Source`](crate::error::Source)
842#[macro_export]
843macro_rules! source {
844    () => {
845        anchor_lang::error::Source {
846            filename: file!(),
847            line: line!(),
848        }
849    };
850}