spl_single_pool/
lib.rs

1#![deny(missing_docs)]
2
3//! A program for liquid staking with a single validator
4
5pub mod error;
6pub mod inline_mpl_token_metadata;
7pub mod instruction;
8pub mod processor;
9pub mod state;
10
11#[cfg(not(feature = "no-entrypoint"))]
12pub mod entrypoint;
13
14// export current sdk types for downstream users building with a different sdk
15// version
16pub use solana_program;
17use solana_program::{pubkey::Pubkey, stake};
18
19solana_program::declare_id!("SVSPxpvHdN29nkVg9rPapPNDddN5DipNLRUFhyjFThE");
20
21const POOL_PREFIX: &[u8] = b"pool";
22const POOL_STAKE_PREFIX: &[u8] = b"stake";
23const POOL_MINT_PREFIX: &[u8] = b"mint";
24const POOL_MINT_AUTHORITY_PREFIX: &[u8] = b"mint_authority";
25const POOL_STAKE_AUTHORITY_PREFIX: &[u8] = b"stake_authority";
26const POOL_MPL_AUTHORITY_PREFIX: &[u8] = b"mpl_authority";
27
28const MINT_DECIMALS: u8 = 9;
29
30const VOTE_STATE_DISCRIMINATOR_END: usize = 4;
31const VOTE_STATE_AUTHORIZED_WITHDRAWER_START: usize = 36;
32const VOTE_STATE_AUTHORIZED_WITHDRAWER_END: usize = 68;
33
34fn find_pool_address_and_bump(program_id: &Pubkey, vote_account_address: &Pubkey) -> (Pubkey, u8) {
35    Pubkey::find_program_address(&[POOL_PREFIX, vote_account_address.as_ref()], program_id)
36}
37
38fn find_pool_stake_address_and_bump(program_id: &Pubkey, pool_address: &Pubkey) -> (Pubkey, u8) {
39    Pubkey::find_program_address(&[POOL_STAKE_PREFIX, pool_address.as_ref()], program_id)
40}
41
42fn find_pool_mint_address_and_bump(program_id: &Pubkey, pool_address: &Pubkey) -> (Pubkey, u8) {
43    Pubkey::find_program_address(&[POOL_MINT_PREFIX, pool_address.as_ref()], program_id)
44}
45
46fn find_pool_stake_authority_address_and_bump(
47    program_id: &Pubkey,
48    pool_address: &Pubkey,
49) -> (Pubkey, u8) {
50    Pubkey::find_program_address(
51        &[POOL_STAKE_AUTHORITY_PREFIX, pool_address.as_ref()],
52        program_id,
53    )
54}
55
56fn find_pool_mint_authority_address_and_bump(
57    program_id: &Pubkey,
58    pool_address: &Pubkey,
59) -> (Pubkey, u8) {
60    Pubkey::find_program_address(
61        &[POOL_MINT_AUTHORITY_PREFIX, pool_address.as_ref()],
62        program_id,
63    )
64}
65
66fn find_pool_mpl_authority_address_and_bump(
67    program_id: &Pubkey,
68    pool_address: &Pubkey,
69) -> (Pubkey, u8) {
70    Pubkey::find_program_address(
71        &[POOL_MPL_AUTHORITY_PREFIX, pool_address.as_ref()],
72        program_id,
73    )
74}
75
76fn find_default_deposit_account_address_and_seed(
77    pool_address: &Pubkey,
78    user_wallet_address: &Pubkey,
79) -> (Pubkey, String) {
80    let pool_address_str = pool_address.to_string();
81    let seed = format!("svsp{}", &pool_address_str[0..28]);
82    let address =
83        Pubkey::create_with_seed(user_wallet_address, &seed, &stake::program::id()).unwrap();
84
85    (address, seed)
86}
87
88/// Find the canonical pool address for a given vote account.
89pub fn find_pool_address(program_id: &Pubkey, vote_account_address: &Pubkey) -> Pubkey {
90    find_pool_address_and_bump(program_id, vote_account_address).0
91}
92
93/// Find the canonical stake account address for a given pool account.
94pub fn find_pool_stake_address(program_id: &Pubkey, pool_address: &Pubkey) -> Pubkey {
95    find_pool_stake_address_and_bump(program_id, pool_address).0
96}
97
98/// Find the canonical token mint address for a given pool account.
99pub fn find_pool_mint_address(program_id: &Pubkey, pool_address: &Pubkey) -> Pubkey {
100    find_pool_mint_address_and_bump(program_id, pool_address).0
101}
102
103/// Find the canonical stake authority address for a given pool account.
104pub fn find_pool_stake_authority_address(program_id: &Pubkey, pool_address: &Pubkey) -> Pubkey {
105    find_pool_stake_authority_address_and_bump(program_id, pool_address).0
106}
107
108/// Find the canonical mint authority address for a given pool account.
109pub fn find_pool_mint_authority_address(program_id: &Pubkey, pool_address: &Pubkey) -> Pubkey {
110    find_pool_mint_authority_address_and_bump(program_id, pool_address).0
111}
112
113/// Find the canonical MPL authority address for a given pool account.
114pub fn find_pool_mpl_authority_address(program_id: &Pubkey, pool_address: &Pubkey) -> Pubkey {
115    find_pool_mpl_authority_address_and_bump(program_id, pool_address).0
116}
117
118/// Find the address of the default intermediate account that holds activating
119/// user stake before deposit.
120pub fn find_default_deposit_account_address(
121    pool_address: &Pubkey,
122    user_wallet_address: &Pubkey,
123) -> Pubkey {
124    find_default_deposit_account_address_and_seed(pool_address, user_wallet_address).0
125}