Skip to main content

shadow_drive_user_staking/instructions/
mutable_fees.rs

1use crate::{
2    errors::ErrorCodes,
3    instructions::{initialize_config::StorageConfig, update_config::is_admin},
4};
5use anchor_lang::prelude::*;
6use std::convert::TryInto;
7
8/// This is the function that handles the `mutable_fees` ix
9pub fn handler(
10    ctx: Context<MutableFees>,
11    shades_per_gib_per_epoch: Option<u64>,
12    crank_bps: Option<u32>,
13) -> Result<()> {
14    let storage_config = &mut ctx.accounts.storage_config;
15    // We should assume if some value is passed in for both shades_per_gib_per_epoch and
16    // crank_bps, then we can assume fees should be enabled or updated
17    if shades_per_gib_per_epoch.is_some() && crank_bps.is_some() {
18        // Mutable fees are off. Turn them on.
19        msg!(
20            "Turning on mutable account storage fees. Shades/GB = {}; Crank bps = {}",
21            shades_per_gib_per_epoch.unwrap(),
22            crank_bps.unwrap()
23        );
24
25        let clock = Clock::get()?;
26        storage_config.mutable_fee_start_epoch = Some(clock.epoch.try_into().unwrap());
27        storage_config.shades_per_gib_per_epoch = shades_per_gib_per_epoch.unwrap();
28        storage_config.crank_bps = crank_bps.unwrap().try_into().unwrap();
29    } else if !shades_per_gib_per_epoch.is_some() && !crank_bps.is_some() {
30        // Mutable fees are on. Turn them off.
31        msg!("Turning off mutable account storage fees");
32        storage_config.mutable_fee_start_epoch = None;
33        storage_config.shades_per_gib_per_epoch = 0;
34        storage_config.crank_bps = 0;
35    } else {
36        // Check for valid fee parameters and return the appropriate error
37        require!(shades_per_gib_per_epoch.is_some(), ErrorCodes::NeedSomeFees);
38        require!(crank_bps.is_some(), ErrorCodes::NeedSomeCrankBps);
39    }
40
41    Ok(())
42}
43
44#[derive(Accounts)]
45/// This `MutableFees` context is used to initialize the account which stores Shadow Drive
46/// configuration data including storage costs, admin pubkeys.
47pub struct MutableFees<'info> {
48    /// This account is a PDA that holds the SPL's staking and slashing policy.
49    /// This is the account that signs transactions on behalf of the program to
50    /// distribute staking rewards.
51    #[account(
52        mut,
53        seeds = [
54            "storage-config".as_bytes()
55        ],
56        bump,
57    )]
58    pub storage_config: Box<Account<'info, StorageConfig>>,
59
60    /// This account is the SPL's staking policy admin.
61    /// Must be either freeze or mint authority
62    #[account(mut, constraint = is_admin(&admin, &storage_config))]
63    pub admin: Signer<'info>,
64}