Compare commits

...

2 Commits

Author SHA1 Message Date
Paul 6a1c128e85
Anchor.toml: remove safety check feature (#24) 2022-02-20 19:22:30 -05:00
Paul 571f2c2781
add new errors and Result (#23) 2022-02-20 16:03:55 -05:00
4 changed files with 61 additions and 60 deletions

View File

@ -3,4 +3,4 @@ cluster = "localnet"
wallet = "~/.config/solana/id.json"
[features]
safety_checks = false

24
Cargo.lock generated
View File

@ -19,7 +19,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-access-control"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -31,7 +31,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-account"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -44,7 +44,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-constant"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"proc-macro2",
@ -53,7 +53,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-error"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"proc-macro2",
@ -63,7 +63,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-event"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -74,7 +74,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-interface"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -86,7 +86,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-program"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -97,7 +97,7 @@ dependencies = [
[[package]]
name = "anchor-attribute-state"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -108,7 +108,7 @@ dependencies = [
[[package]]
name = "anchor-derive-accounts"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-syn",
"anyhow",
@ -119,7 +119,7 @@ dependencies = [
[[package]]
name = "anchor-lang"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-attribute-access-control",
"anchor-attribute-account",
@ -141,7 +141,7 @@ dependencies = [
[[package]]
name = "anchor-spl"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anchor-lang",
"solana-program",
@ -151,7 +151,7 @@ dependencies = [
[[package]]
name = "anchor-syn"
version = "0.20.1"
version = "0.21.0"
dependencies = [
"anyhow",
"bs58 0.3.1",

View File

@ -42,10 +42,10 @@ pub mod lockup {
#[access_control(whitelist_auth(self, &ctx))]
pub fn whitelist_add(&mut self, ctx: Context<Auth>, entry: WhitelistEntry) -> Result<()> {
if self.whitelist.len() == Self::WHITELIST_SIZE {
return Err(ErrorCode::WhitelistFull.into());
return err!(ErrorCode::WhitelistFull);
}
if self.whitelist.contains(&entry) {
return Err(ErrorCode::WhitelistEntryAlreadyExists.into());
return err!(ErrorCode::WhitelistEntryAlreadyExists);
}
self.whitelist.push(entry);
Ok(())
@ -58,7 +58,7 @@ pub mod lockup {
entry: WhitelistEntry,
) -> Result<()> {
if !self.whitelist.contains(&entry) {
return Err(ErrorCode::WhitelistEntryNotFound.into());
return err!(ErrorCode::WhitelistEntryNotFound);
}
self.whitelist.retain(|e| e != &entry);
Ok(())
@ -83,10 +83,10 @@ pub mod lockup {
realizor: Option<Realizor>,
) -> Result<()> {
if deposit_amount == 0 {
return Err(ErrorCode::InvalidDepositAmount.into());
return err!(ErrorCode::InvalidDepositAmount);
}
if !is_valid_schedule(start_ts, end_ts, period_count) {
return Err(ErrorCode::InvalidSchedule.into());
return err!(ErrorCode::InvalidSchedule);
}
let vesting = &mut ctx.accounts.vesting;
vesting.beneficiary = beneficiary;
@ -117,7 +117,7 @@ pub mod lockup {
ctx.accounts.clock.unix_timestamp,
)
{
return Err(ErrorCode::InsufficientWithdrawalBalance.into());
return err!(ErrorCode::InsufficientWithdrawalBalance);
}
// Transfer funds out.
@ -154,7 +154,7 @@ pub mod lockup {
// CPI safety checks.
let withdraw_amount = before_amount - after_amount;
if withdraw_amount > amount {
return Err(ErrorCode::WhitelistWithdrawLimit)?;
return err!(ErrorCode::WhitelistWithdrawLimit);
}
// Bookeeping.
@ -180,10 +180,10 @@ pub mod lockup {
// CPI safety checks.
let deposit_amount = after_amount - before_amount;
if deposit_amount <= 0 {
return Err(ErrorCode::InsufficientWhitelistDepositAmount)?;
return err!(ErrorCode::InsufficientWhitelistDepositAmount);
}
if deposit_amount > ctx.accounts.transfer.vesting.whitelist_owned {
return Err(ErrorCode::WhitelistDepositOverflow)?;
return err!(ErrorCode::WhitelistDepositOverflow);
}
// Bookkeeping.
@ -238,9 +238,9 @@ impl<'info> CreateVesting<'info> {
],
ctx.program_id,
)
.map_err(|_| ErrorCode::InvalidProgramAddress)?;
.map_err(|_| error!(ErrorCode::InvalidProgramAddress))?;
if ctx.accounts.vault.owner != vault_authority {
return Err(ErrorCode::InvalidVaultOwner)?;
return err!(ErrorCode::InvalidVaultOwner);
}
Ok(())
@ -371,7 +371,7 @@ pub struct WhitelistEntry {
pub program_id: Pubkey,
}
#[error]
#[error_code]
pub enum ErrorCode {
#[msg("Vesting end must be greater than the current unix timestamp.")]
InvalidTimestamp,
@ -490,14 +490,14 @@ pub fn is_whitelisted<'info>(transfer: &WhitelistTransfer<'info>) -> Result<()>
if !transfer.lockup.whitelist.contains(&WhitelistEntry {
program_id: *transfer.whitelisted_program.key,
}) {
return Err(ErrorCode::WhitelistEntryNotFound.into());
return err!(ErrorCode::WhitelistEntryNotFound);
}
Ok(())
}
fn whitelist_auth(lockup: &Lockup, ctx: &Context<Auth>) -> Result<()> {
if &lockup.authority != ctx.accounts.authority.key {
return Err(ErrorCode::Unauthorized.into());
return err!(ErrorCode::Unauthorized);
}
Ok(())
}
@ -523,14 +523,15 @@ fn is_realized(ctx: &Context<Withdraw>) -> Result<()> {
let cpi_program = {
let p = ctx.remaining_accounts[0].clone();
if p.key != &realizor.program {
return Err(ErrorCode::InvalidLockRealizor.into());
return err!(ErrorCode::InvalidLockRealizor);
}
p
};
let cpi_accounts = ctx.remaining_accounts.to_vec()[1..].to_vec();
let cpi_ctx = CpiContext::new(cpi_program, cpi_accounts);
let vesting = (*ctx.accounts.vesting).clone();
realize_lock::is_realized(cpi_ctx, vesting).map_err(|_| ErrorCode::UnrealizedVesting)?;
realize_lock::is_realized(cpi_ctx, vesting)
.map_err(|_| error!(ErrorCode::UnrealizedVesting))?;
}
Ok(())
}
@ -543,5 +544,5 @@ fn is_realized(ctx: &Context<Withdraw>) -> Result<()> {
/// until one has completely unstaked.
#[interface]
pub trait RealizeLock<'info, T: Accounts<'info>> {
fn is_realized(ctx: Context<T>, v: Vesting) -> ProgramResult;
fn is_realized(ctx: Context<T>, v: Vesting) -> Result<()>;
}

View File

@ -43,7 +43,7 @@ mod registry {
.parse()
.unwrap();
if ctx.accounts.authority.key != &expected {
return Err(ErrorCode::InvalidProgramAuthority.into());
return err!(ErrorCode::InvalidProgramAuthority);
}
self.lockup_program = lockup_program;
@ -53,16 +53,16 @@ mod registry {
}
impl<'info> RealizeLock<'info, IsRealized<'info>> for Registry {
fn is_realized(ctx: Context<IsRealized>, v: Vesting) -> ProgramResult {
fn is_realized(ctx: Context<IsRealized>, v: Vesting) -> Result<()> {
if let Some(realizor) = &v.realizor {
if &realizor.metadata != ctx.accounts.member.to_account_info().key {
return Err(ErrorCode::InvalidRealizorMetadata.into());
return err!(ErrorCode::InvalidRealizorMetadata);
}
assert!(ctx.accounts.member.beneficiary == v.beneficiary);
let total_staked =
ctx.accounts.member_spt.amount + ctx.accounts.member_spt_locked.amount;
if total_staked != 0 {
return Err(ErrorCode::UnrealizedReward.into());
return err!(ErrorCode::UnrealizedReward);
}
}
Ok(())
@ -287,7 +287,7 @@ mod registry {
pub fn end_unstake(ctx: Context<EndUnstake>) -> Result<()> {
if ctx.accounts.pending_withdrawal.end_ts > ctx.accounts.clock.unix_timestamp {
return Err(ErrorCode::UnstakeTimelock.into());
return err!(ErrorCode::UnstakeTimelock);
}
// Select which balance set this affects.
@ -300,10 +300,10 @@ mod registry {
};
// Check the vaults given are corrrect.
if &balances.vault != ctx.accounts.vault.key {
return Err(ErrorCode::InvalidVault.into());
return err!(ErrorCode::InvalidVault);
}
if &balances.vault_pw != ctx.accounts.vault_pw.key {
return Err(ErrorCode::InvalidVault.into());
return err!(ErrorCode::InvalidVault);
}
// Transfer tokens between vaults.
@ -379,33 +379,33 @@ mod registry {
nonce: u8,
) -> Result<()> {
if total < ctx.accounts.pool_mint.supply {
return Err(ErrorCode::InsufficientReward.into());
return err!(ErrorCode::InsufficientReward);
}
if ctx.accounts.clock.unix_timestamp >= expiry_ts {
return Err(ErrorCode::InvalidExpiry.into());
return err!(ErrorCode::InvalidExpiry);
}
if ctx.accounts.registrar.to_account_info().key == &dxl_registrar::ID {
if ctx.accounts.vendor_vault.mint != dxl_mint::ID {
return Err(ErrorCode::InvalidMint.into());
return err!(ErrorCode::InvalidMint);
}
if total < DXL_MIN_REWARD {
return Err(ErrorCode::InsufficientReward.into());
return err!(ErrorCode::InsufficientReward);
}
} else if ctx.accounts.registrar.to_account_info().key == &fida_registrar::ID {
if ctx.accounts.vendor_vault.mint != fida_mint::ID {
return Err(ErrorCode::InvalidMint.into());
return err!(ErrorCode::InvalidMint);
}
if total < FIDA_MIN_REWARD {
return Err(ErrorCode::InsufficientReward.into());
return err!(ErrorCode::InsufficientReward);
}
} else if ctx.accounts.registrar.to_account_info().key == &srm_registrar::ID
|| ctx.accounts.registrar.to_account_info().key == &msrm_registrar::ID
{
if ctx.accounts.vendor_vault.mint != srm_mint::ID {
return Err(ErrorCode::InvalidMint.into());
return err!(ErrorCode::InvalidMint);
}
if total < SRM_MIN_REWARD {
return Err(ErrorCode::InsufficientReward.into());
return err!(ErrorCode::InsufficientReward);
}
} else {
// TODO: in a future major version upgrade. Add the amount + mint
@ -420,7 +420,7 @@ mod registry {
} = kind
{
if !lockup::is_valid_schedule(start_ts, end_ts, period_count) {
return Err(ErrorCode::InvalidVestingSchedule.into());
return err!(ErrorCode::InvalidVestingSchedule);
}
}
@ -457,7 +457,7 @@ mod registry {
#[access_control(reward_eligible(&ctx.accounts.cmn))]
pub fn claim_reward(ctx: Context<ClaimReward>) -> Result<()> {
if RewardVendorKind::Unlocked != ctx.accounts.cmn.vendor.kind {
return Err(ErrorCode::ExpectedUnlockedVendor.into());
return err!(ErrorCode::ExpectedUnlockedVendor);
}
// Reward distribution.
let spt_total =
@ -500,7 +500,7 @@ mod registry {
nonce: u8,
) -> Result<()> {
let (start_ts, end_ts, period_count) = match ctx.accounts.cmn.vendor.kind {
RewardVendorKind::Unlocked => return Err(ErrorCode::ExpectedLockedVendor.into()),
RewardVendorKind::Unlocked => return Err(error!(ErrorCode::ExpectedLockedVendor)),
RewardVendorKind::Locked {
start_ts,
end_ts,
@ -573,7 +573,7 @@ mod registry {
pub fn expire_reward(ctx: Context<ExpireReward>) -> Result<()> {
if ctx.accounts.clock.unix_timestamp < ctx.accounts.vendor.expiry_ts {
return Err(ErrorCode::VendorNotYetExpired.into());
return err!(ErrorCode::VendorNotYetExpired);
}
// Send all remaining funds to the expiry receiver's token.
@ -622,9 +622,9 @@ impl<'info> Initialize<'info> {
],
ctx.program_id,
)
.map_err(|_| ErrorCode::InvalidNonce)?;
.map_err(|_| error!(ErrorCode::InvalidNonce))?;
if ctx.accounts.pool_mint.mint_authority != COption::Some(registrar_signer) {
return Err(ErrorCode::InvalidPoolMintAuthority.into());
return err!(ErrorCode::InvalidPoolMintAuthority);
}
assert!(ctx.accounts.pool_mint.supply == 0);
Ok(())
@ -675,9 +675,9 @@ impl<'info> CreateMember<'info> {
&[nonce],
];
let member_signer = Pubkey::create_program_address(seeds, ctx.program_id)
.map_err(|_| ErrorCode::InvalidNonce)?;
.map_err(|_| error!(ErrorCode::InvalidNonce))?;
if &member_signer != ctx.accounts.member_signer.to_account_info().key {
return Err(ErrorCode::InvalidMemberSigner.into());
return err!(ErrorCode::InvalidMemberSigner);
}
Ok(())
@ -983,9 +983,9 @@ impl<'info> DropReward<'info> {
],
ctx.program_id,
)
.map_err(|_| ErrorCode::InvalidNonce)?;
.map_err(|_| error!(ErrorCode::InvalidNonce))?;
if vendor_signer != ctx.accounts.vendor_vault.owner {
return Err(ErrorCode::InvalidVaultOwner.into());
return err!(ErrorCode::InvalidVaultOwner);
}
Ok(())
@ -1227,7 +1227,7 @@ pub enum RewardVendorKind {
},
}
#[error]
#[error_code]
pub enum ErrorCode {
#[msg("The given reward queue has already been initialized.")]
RewardQAlreadyInitialized,
@ -1340,13 +1340,13 @@ fn reward_eligible(cmn: &ClaimRewardCommon) -> Result<()> {
let vendor = &cmn.vendor;
let member = &cmn.member;
if vendor.expired {
return Err(ErrorCode::VendorExpired.into());
return err!(ErrorCode::VendorExpired);
}
if member.rewards_cursor > vendor.reward_event_q_cursor {
return Err(ErrorCode::CursorAlreadyProcessed.into());
return err!(ErrorCode::CursorAlreadyProcessed);
}
if member.last_stake_ts > vendor.start_ts {
return Err(ErrorCode::NotStakedDuringDrop.into());
return err!(ErrorCode::NotStakedDuringDrop);
}
Ok(())
}
@ -1372,7 +1372,7 @@ pub fn no_available_rewards<'info>(
let r_event = reward_q.get(cursor);
if member.last_stake_ts < r_event.ts {
if balances.spt.amount > 0 || balances_locked.spt.amount > 0 {
return Err(ErrorCode::RewardsNeedsProcessing.into());
return err!(ErrorCode::RewardsNeedsProcessing);
}
}
cursor += 1;