use {
num_derive::FromPrimitive,
solana_program_error::{ProgramError, ToStr},
thiserror::Error,
};
#[derive(Clone, Debug, Eq, Error, FromPrimitive, PartialEq)]
pub enum StakePoolError {
#[error("AlreadyInUse")]
AlreadyInUse,
#[error("InvalidProgramAddress")]
InvalidProgramAddress,
#[error("InvalidState")]
InvalidState,
#[error("CalculationFailure")]
CalculationFailure,
#[error("FeeTooHigh")]
FeeTooHigh,
#[error("WrongAccountMint")]
WrongAccountMint,
#[error("WrongManager")]
WrongManager,
#[error("SignatureMissing")]
SignatureMissing,
#[error("InvalidValidatorStakeList")]
InvalidValidatorStakeList,
#[error("InvalidFeeAccount")]
InvalidFeeAccount,
#[error("WrongPoolMint")]
WrongPoolMint,
#[error("WrongStakeStake")]
WrongStakeStake,
#[error("UserStakeNotActive")]
UserStakeNotActive,
#[error("ValidatorAlreadyAdded")]
ValidatorAlreadyAdded,
#[error("ValidatorNotFound")]
ValidatorNotFound,
#[error("InvalidStakeAccountAddress")]
InvalidStakeAccountAddress,
#[error("StakeListOutOfDate")]
StakeListOutOfDate,
#[error("StakeListAndPoolOutOfDate")]
StakeListAndPoolOutOfDate,
#[error("UnknownValidatorStakeAccount")]
UnknownValidatorStakeAccount,
#[error("WrongMintingAuthority")]
WrongMintingAuthority,
#[error("UnexpectedValidatorListAccountSize")]
UnexpectedValidatorListAccountSize,
#[error("WrongStaker")]
WrongStaker,
#[error("NonZeroPoolTokenSupply")]
NonZeroPoolTokenSupply,
#[error("StakeLamportsNotEqualToMinimum")]
StakeLamportsNotEqualToMinimum,
#[error("IncorrectDepositVoteAddress")]
IncorrectDepositVoteAddress,
#[error("IncorrectWithdrawVoteAddress")]
IncorrectWithdrawVoteAddress,
#[error("InvalidMintFreezeAuthority")]
InvalidMintFreezeAuthority,
#[error("FeeIncreaseTooHigh")]
FeeIncreaseTooHigh,
#[error("WithdrawalTooSmall")]
WithdrawalTooSmall,
#[error("DepositTooSmall")]
DepositTooSmall,
#[error("InvalidStakeDepositAuthority")]
InvalidStakeDepositAuthority,
#[error("InvalidSolDepositAuthority")]
InvalidSolDepositAuthority,
#[error("InvalidPreferredValidator")]
InvalidPreferredValidator,
#[error("TransientAccountInUse")]
TransientAccountInUse,
#[error("InvalidSolWithdrawAuthority")]
InvalidSolWithdrawAuthority,
#[error("SolWithdrawalTooLarge")]
SolWithdrawalTooLarge,
#[error("InvalidMetadataAccount")]
InvalidMetadataAccount,
#[error("UnsupportedMintExtension")]
UnsupportedMintExtension,
#[error("UnsupportedFeeAccountExtension")]
UnsupportedFeeAccountExtension,
#[error("Instruction exceeds desired slippage limit")]
ExceededSlippage,
#[error("IncorrectMintDecimals")]
IncorrectMintDecimals,
#[error("ReserveDepleted")]
ReserveDepleted,
#[error("Missing required sysvar account")]
MissingRequiredSysvar,
#[error("Epoch reward distribution is currently in progress, stakes are still being updated")]
EpochRewardDistributionInProgress,
#[error("The stake pool has too many validators in the pool")]
TooManyValidatorsInPool,
}
impl From<StakePoolError> for ProgramError {
fn from(e: StakePoolError) -> Self {
ProgramError::Custom(e as u32)
}
}
impl TryFrom<u32> for StakePoolError {
type Error = ProgramError;
fn try_from(code: u32) -> Result<Self, Self::Error> {
num_traits::FromPrimitive::from_u32(code).ok_or(ProgramError::InvalidArgument)
}
}
impl ToStr for StakePoolError {
fn to_str(&self) -> &'static str {
match self {
Self::AlreadyInUse => "Error: The account cannot be initialized because it is already being used.",
Self::InvalidProgramAddress => "Error: The program address provided doesn't match the value generated by the program.",
Self::InvalidState => "Error: The stake pool state is invalid.",
Self::CalculationFailure => "Error: The calculation failed.",
Self::FeeTooHigh => "Error: Stake pool fee greater than 1.",
Self::WrongAccountMint => "Error: Token account is associated with the wrong mint.",
Self::WrongManager => "Error: Wrong pool manager account.",
Self::SignatureMissing => "Error: Required signature is missing.",
Self::InvalidValidatorStakeList => "Error: Invalid validator stake list account.",
Self::InvalidFeeAccount => "Error: Invalid manager fee account.",
Self::WrongPoolMint => "Error: Specified pool mint account is wrong.",
Self::WrongStakeStake => "Error: Stake account is not in the state expected by the program.",
Self::UserStakeNotActive => "Error: User stake is not active",
Self::ValidatorAlreadyAdded => "Error: Stake account voting for this validator already exists in the pool.",
Self::ValidatorNotFound => "Error: Stake account for this validator not found in the pool.",
Self::InvalidStakeAccountAddress => "Error: Stake account address not properly derived from the validator address.",
Self::StakeListOutOfDate => "Error: Identify validator stake accounts with old balances and update them.",
Self::StakeListAndPoolOutOfDate => "Error: First update old validator stake account balances and then pool stake balance.",
Self::UnknownValidatorStakeAccount => "Error: Validator stake account is not found in the list storage.",
Self::WrongMintingAuthority => "Error: Wrong minting authority set for mint pool account",
Self::UnexpectedValidatorListAccountSize => "Error: The size of the given validator stake list does match the expected amount",
Self::WrongStaker => "Error: Wrong pool staker account.",
Self::NonZeroPoolTokenSupply => "Error: Pool token supply is not zero on initialization",
Self::StakeLamportsNotEqualToMinimum => "Error: The lamports in the validator stake account is not equal to the minimum",
Self::IncorrectDepositVoteAddress => "Error: The provided deposit stake account is not delegated to the preferred deposit vote account",
Self::IncorrectWithdrawVoteAddress => "Error: The provided withdraw stake account is not the preferred deposit vote account",
Self::InvalidMintFreezeAuthority => "Error: The mint has an invalid freeze authority",
Self::FeeIncreaseTooHigh => "Error: Proposed fee increase exceeds stipulated ratio",
Self::WithdrawalTooSmall => "Error: Not enough pool tokens provided to withdraw stake with one lamport",
Self::DepositTooSmall => "Error: Not enough lamports provided for deposit to result in one pool token",
Self::InvalidStakeDepositAuthority => "Error: Provided stake deposit authority does not match the program's",
Self::InvalidSolDepositAuthority => "Error: Provided sol deposit authority does not match the program's",
Self::InvalidPreferredValidator => "Error: Provided preferred validator is invalid",
Self::TransientAccountInUse => "Error: Provided validator stake account already has a transient stake account in use",
Self::InvalidSolWithdrawAuthority => "Error: Provided sol withdraw authority does not match the program's",
Self::SolWithdrawalTooLarge => "Error: Too much SOL withdrawn from the stake pool's reserve account",
Self::InvalidMetadataAccount => "Error: Provided metadata account does not match metadata account derived for pool mint",
Self::UnsupportedMintExtension => "Error: The mint has an unsupported extension",
Self::UnsupportedFeeAccountExtension => "Error: The fee account has an unsupported extension",
Self::ExceededSlippage => "Error: Instruction exceeds desired slippage limit",
Self::IncorrectMintDecimals => "Error: Provided mint does not have 9 decimals to match SOL",
Self::ReserveDepleted => "Error: Pool reserve does not have enough lamports to fund rent-exempt reserve in split destination. Deposit more SOL in reserve, or pre-fund split destination with the rent-exempt reserve for a stake account.",
Self::MissingRequiredSysvar => "Error: Missing required sysvar account",
Self::EpochRewardDistributionInProgress => "Error: Epoch reward distribution is currently in progress, stakes are still being updated",
Self::TooManyValidatorsInPool => "Error: The stake pool has too many validators in the pool",
}
}
}