Crate: wormhole-staking-program
The wormhole-staking-program program is a Solana program built using the Anchor framework. It handles multiple aspects of protocol state including governance configuration, stake account creation and management, delegation and vote-casting, vesting operations, and cross-chain message execution (via Wormhole). The contract maintains various on-chain states:
Global Configuration: Stored in a configuration account, this includes:
bump
: Seed bump for proper PDA derivation.governance_authority
: The address authorized to make governance-level changes.voting_token_mint
: The mint address for the token used in voting.vesting_admin
: The administrator permitted to perform vesting operations.max_checkpoints_account_limit
: A bound on checkpoint entries to mitigate potential account bloat/DoS.
Stake Account State: For each user, stake account metadata and checkpoint data track:
Ownership, delegated addresses, and recorded balances.
Historical checkpoints for stake and delegation amounts, which are critical for calculating voting power over time.
Vesting State: Multiple vesting-related accounts and configuration parameters are maintained to control token vesting, claims, transfers, and cancellations.
Spoke Message Execution State: This includes executor, airlock, and metadata collector accounts used to securely process cross-chain messages.
Below is a function-by-function walkthrough with key safety and threat-mitigation considerations.
Function: init_config
Description:
Initializes the global configuration.
Stores the governance authority, voting token mint, vesting admin, and a checkpoint limit.
Enforces that the
max_checkpoints_account_limit
does not exceed 655,000 (to prevent account bloat and DoS).
Safety Considerations:
DoS Mitigation: Limiting checkpoint size prevents an attacker from filling the account.
Function: update_governance_authority
Description:
Updates the governance authority stored in the configuration.
Critical for transferring administrative control.
Safety Considerations:
Authorization: Must be callable only by the current governance authority.
Function: update_vesting_admin
Description:
Updates the vesting administrator.
Allows transfer of vesting operational control.
Safety Considerations:
Authorization: Access is restricted to authorized parties.
Function: create_stake_account
Description:
Creates a new stake account for a user.
Initializes stake account metadata and checkpoint data.
Safety Considerations:
State Initialization: Correctly sets up user stake and checkpoint state for later operations.
Function: create_checkpoints
Description:
Creates and appends a checkpoint entry reflecting the current stake balance.
Loads the existing checkpoint data and pushes a new checkpoint.
Safety Considerations:
Checkpoint Limits: Verifies that the number of checkpoints does not exceed the configured limit.
Account Safety: Uses safe account initialization via anchor's init annotation to avoid state corruption.
Function: delegate
Description:
Updates a staker’s delegation to a delegatee.
Adjusts checkpoint data for both the previous delegate and the new delegatee.
Emits events (
DelegateChanged
) to signal delegation updates.
Safety Considerations:
Checkpoint Boundaries: Enforces limits to prevent account bloat.
Balance Validation: Updates both stake and recorded vesting balances carefully to avoid miscounting.
Function: withdraw_tokens
Description:
Allows users to withdraw tokens from their stake custody.
Updates checkpoint data to reflect a changed balance.
Verifies that the withdrawal amount is non-zero and that the destination is controlled by the signer.
Safety Considerations:
SPL Token Transfer: Uses the SPL token program with
invoke_signed
and proper signer seeds.Account Ownership: Checks that the destination account is owned by the signer to prevent unauthorized transfers.
Function: cast_vote
Description:
Enables users to cast votes on proposals.
Determines voting weight by traversing historical checkpoints within a defined time window.
Validates that the vote does not exceed the available weight and updates proposal totals.
Safety Considerations:
Historical Integrity: Uses checkpoint history to secure against vote manipulation.
Bounds Checking: Thorough arithmetic and bounds checks prevent overflows and replay of stale checkpoints.
Data Consistency: Handles transitions between checkpoint accounts safely.
Function: initialize_vesting_config
Description:
Initializes vesting configuration (mint, vault, admin, etc.).
Safety Considerations:
Access Control: Only authorized (vesting-admin) accounts should perform this operation.
Function: create_vesting_balance
Description:
Creates a vesting balance account for a user.
Intended to be used when the vesting configuration is not yet finalized.
Safety Considerations:
Account Initialization: Ensures that vesting balance accounts are correctly associated and initialized.
Function: finalize_vesting_config
Description:
Finalizes the vesting configuration, preventing further vesting account creation or cancellation.
Restricted to the vesting admin.
Safety Considerations:
Locking Critical State: Once finalized, no further vesting changes are allowed. This is strictly enforced.
Privilege Control: Ensures only the vesting admin can finalize to prevent accidental or malicious configuration changes.
Function: create_vesting
Description:
Opens a new vesting account and deposits tokens into the vesting vault.
Accepts parameters for maturation time and vesting amount.
Safety Considerations:
Parameter Validation: Ensures maturation and amount parameters are valid and won’t cause overflow.
State Consistency: Must integrate correctly with vesting configuration state (especially in non-finalized mode).
Function: claim_vesting
Description:
Allows a user to claim tokens from a vesting account and close it.
Emits events to signal vesting balance and delegated vote adjustments.
Safety Considerations:
Atomic Claims: Updates vesting state and transfers tokens atomically to prevent double-claims.
State Cleanup: Correctly removes vesting accounts to free storage and avoid dangling state.
Function: transfer_vesting
Description:
Transfers vesting tokens from one account to another.
Updates the stake account metadata and emits events for vesting balance changes.
Safety Considerations:
State Synchronization: Both source and destination vesting accounts are updated to avoid fund loss.
Arithmetic Safety: Uses safe math and validated state updates.
Function: cancel_vesting
Description:
Cancels and closes a vesting account for configurations that are not finalized.
Restricted to the vesting admin.
Safety Considerations:
Conditional Access: Ensures vesting cancellation is only permitted when configuration is not finalized.
Fund Recovery: Must correctly refund any remaining tokens and update state.
Function: withdraw_surplus
Description:
Enables the vesting admin to withdraw surplus tokens beyond the total vested amount.
Intended to recover tokens that are not allocated to vesting obligations.
Safety Considerations:
Privilege Restriction: Only callable by the vesting admin.
Amount Validation: Must ensure that withdrawal amounts are correctly computed to avoid draining user funds.
Function: initialize_spoke_message_executor
Description:
Sets up the executor for processing cross-chain messages (using Wormhole).
Initializes key state variables such as the hub chain ID, spoke chain ID, and Wormhole core program ID.
Safety Considerations:
Proper Initialization: Uses bump seeds and strict account derivation to prevent misrouting of messages.
Access Control: Only authorized accounts should set up the executor.
Function: receive_message
Description:
Processes an incoming Wormhole message.
Validates that the message comes from the expected Wormhole (spoke) chain.
Iterates over embedded instructions and calls them via
invoke_signed
with the correct signer seeds.Ensures that lamport usage remains within the allowed maximum and that the payer’s ownership is unchanged after execution.
Safety Considerations:
Cost Limitation: Verifies lamport differences to prevent draining the payer’s account.
Payload Validation: Checks that the Wormhole chain ID and message payload are as expected to block spoofing.
Function: initialize_spoke_airlock
Description:
Initializes the airlock and its self-call counterpart used in cross-chain message execution.
Function: initialize_spoke_metadata_collector
Description:
Sets up a metadata collector to receive proposal metadata from the hub chain.
Stores details such as the hub chain ID, hub proposal metadata, and Wormhole core program ID.
Safety Considerations:
Data Authenticity: Ensures that only messages from legitimate hub sources are recorded.
Function: update_hub_proposal_metadata
Description:
Updates the hub proposal metadata stored in the metadata collector.
Enforces that either governance or an authorized airlock self-call account may perform the update, based on a configuration flag.
Safety Considerations:
Access Verification: Validates the caller’s authority (either governance or via a valid self-call).
Data Integrity: Prevents unauthorized modifications that could misdirect proposal data.
Function: relinquish_admin_control_over_hub_proposal_metadata
Description:
Permanently disables governance control over updating hub proposal metadata.
Shifts control solely to the airlock self-call mechanism.
Function: initialize_vote_weight_window_lengths
Description:
Initializes the vote weight window lengths, which are used to determine historical vote weight based on checkpoint data.
Sets an initial window length in a dedicated account.
Safety Considerations:
State Integrity: Correctly initializes historical data needed for secure vote weight calculations.
Boundary Enforcement: Uses safe initialization methods to avoid overflow or misconfiguration.
Function: update_vote_weight_window_lengths
Description:
Updates (by appending) the window lengths used in vote weight calculations.
Records the new window length along with a timestamp.
Safety Considerations:
Bounds Checking: Ensures that new window lengths do not cause account bloat or exceed limits.
Function: post_signatures
Description:
Appends guardian signatures to a
GuardianSignatures
account.Supports multiple invocations if the number of required signatures exceeds what can fit in a single transaction.
Safety Considerations:
Authorization: Verifies that the caller (the refund recipient) is authorized to append signatures.
Function: close_signatures
Description:
Allows the initial payer to close the
GuardianSignatures
account if the associated query was invalid.Returns the funds by refunding the payer.
Safety Considerations:
Access Restriction: Only callable by the initial payer.
Function: add_proposal
Description:
Adds a new proposal after verifying external proposal metadata obtained via a Wormhole query response.
Parses the query response, validates the Ethereum call data (including the expected function signature and proposal ID), and updates the proposal state.
Emits events (
ProposalCreated
) on successful addition.
Safety Considerations:
Strict Validation: Checks chain IDs, function signatures, and proposal IDs to prevent spoofing.