Smart Contracts
On-chain program instructions and accounts
Program ID#
7zKs14NrKub1ED6eCxdjC1K2yB1YTczcH8UTyCPuoQCE
Account Structures#
MixerState#
The pool state for SOL pools.
pub struct MixerState {
pub merkle_root: [u8; 32], // Current Merkle root
pub vault_bump: u8, // PDA bump for vault
pub total_shielded: u64, // Total deposits
pub bump: u8, // PDA bump
}
// Space: 50 bytes
PDA seed: ["mixer", denomination LE bytes]
Vault#
The pool's SOL vault. A system-owned account with zero-size data (only holds lamports).
PDA seed: ["vault", mixer_state.key()]
KeyRegistry#
Stores a user's protocol public keys.
pub struct KeyRegistry {
pub owner: Pubkey,
pub x25519_public_key: [u8; 32], // Viewing public key
pub user_commitment: [u8; 32], // Spending public key
pub bump: u8,
}
// Space: 105 bytes
PDA seed: ["key-registry", owner]
Multisig#
The 2-of-3 oracle multisig configuration.
pub struct Multisig {
pub oracles: [Pubkey; 3], // Three oracle pubkeys
pub threshold: u8, // Required signatures (2)
pub bump: u8,
}
// Space: 106 bytes
PDA seed: ["multisig"]
NullifierAccount#
Records a spent nullifier.
pub struct NullifierAccount {
pub hash: [u8; 32],
pub bump: u8,
}
// Space: 41 bytes
PDA seed: ["nullifier", nullifier_hash]
NullifierCompressed#
Records a spent nullifier with compressed variant.
PDA seed: ["nullifier_c", nullifier_hash]
MixerTokenState Coming Soon#
Pool state for SPL token pools.
pub struct MixerTokenState {
pub merkle_root: [u8; 32],
pub mint: Pubkey,
pub total_shielded: u64,
pub bump: u8,
}
// Space: 81 bytes
PDA seed: ["mixer_token", mint, denomination LE bytes]
Instructions#
| Instruction | Accounts | Description |
|---|---|---|
| register_keys | payer, key_registry, system_program | Register viewing and spending public keys |
| init_multisig | payer, multisig, system_program | Initialize 2-of-3 oracle multisig |
| init_mixer | payer, mixer_state, vault, system_program | Create pool for a denomination |
| shield | payer, mixer_state, vault, system_program | Deposit SOL into pool |
| unshield | payer, recipient, mixer_state, vault, nullifier_account, system_program | Withdraw with ZK proof |
| unshield_compressed | payer, recipient, mixer_state, vault, nullifier_account, system_program | Withdraw with compressed nullifier |
| update_root | payer, multisig, mixer_state, system_program + remaining_accounts (oracles) | Update Merkle root via multisig |
| admin_update_root | admin, mixer_state | Update root (temporary, pre-multisig) |
| announce_stealth | sender | Announce stealth payment |
| claim_stealth | stealth_address, recipient, system_program | Claim funds from stealth address |
| init_token_mixer | payer, mixer_token_state, vault_ata, mint, ... | Create SPL token pool |
| shield_token | payer, payer_ata, mixer_token_state, vault_ata, mint, token_program, ... | Deposit tokens |
| unshield_token | payer, recipient, recipient_ata, mixer_token_state, vault_ata, mint, nullifier_account, ... | Withdraw tokens with ZK proof |
Error Codes#
| Code | Name | Description | |---|---|---| | 0x1770 | InsufficientOracleSignatures | At least two registered oracle signatures are required | | 0x1771 | DuplicateOracle | Multisig oracles must be unique | | 0x1772 | InvalidDenomination | Invalid denomination | | 0x1773 | InvalidPublicInputs | Invalid public inputs length | | 0x1774 | InvalidMerkleRoot | Invalid merkle root | | 0x1775 | InvalidRecipient | Invalid recipient | | 0x1776 | InvalidNullifierAccount | Invalid nullifier account | | 0x1777 | InvalidMixerState | Invalid mixer state account | | 0x1778 | InvalidVaultAccount | Invalid vault account | | 0x1779 | NullifierAlreadySpent | Nullifier already spent | | 0x177A | InvalidEtaAuthority | Invalid ETA authority | | 0x177B | InvalidCompressedPda | Invalid compressed PDA |
Verifier Errors#
| Error | Description | |---|---| | InvalidPublicInputs | Wrong number of public inputs | | MultiexpFailed | G1 multiexponentiation failed | | AdditionFailed | G1 addition failed | | PairingFailed | Pairing check failed | | ProofVerificationFailed | Generic proof failure | | InvalidRecipient | Recipient address mismatch |