Skip to content

solana-client-tools: helper for ATA address plus create-instruction CU cost #3768

@karl-dz

Description

@karl-dz

Background

Across the doublezerofoundation/doublezero-offchain workspace, CLI commands that push create_associated_token_account_idempotent build their compute-unit budget from Wallet::compute_units_for_bump_seed(bump) plus a base. The base is currently const CREATE_ATA_CU_BASE: u32 = 25_000; and is defined in two places:

A sibling site in the same shred-subscription CLI directory uses the bump-based pattern correctly (for the seat and escrow PDAs):

But crates/solana-cli/src/command/shreds/publisher_rewards/configure.rs (introduced by doublezerofoundation/doublezero-offchain#360 and refined in doublezerofoundation/doublezero-offchain#373) hardcodes a 250k figure at line 246 and uses get_associated_token_address(...) at line 164, which does not return the bump. The discrepancy was surfaced during the review of doublezerofoundation/doublezero-offchain#373.

Proposal

Add a helper that returns both the ATA pubkey and the compute-unit cost of creating it, so callers do not have to:

  1. Reach for get_associated_token_address (which drops the bump),
  2. Then separately remember to call Wallet::compute_units_for_bump_seed(bump) with the right bump value,
  3. Then add the right CREATE_ATA_CU_BASE constant.

The helper should delegate address derivation to spl_associated_token_account_interface::address::get_associated_token_address_and_bump_seed rather than hand-roll a Pubkey::find_program_address call. That crate is already a workspace dependency.

A possible shape:

use spl_associated_token_account_interface::address::get_associated_token_address_and_bump_seed;

const CREATE_ATA_CU_BASE: u32 = 25_000;

/// Derive the associated token account address for `(owner, mint)` and return
/// the address alongside the compute-unit cost of issuing a
/// `create_associated_token_account_idempotent` instruction for it.
pub fn find_associated_token_account_with_create_cu(owner: &Pubkey, mint: &Pubkey) -> (Pubkey, u32) {
    let (address, bump) = get_associated_token_address_and_bump_seed(
        owner,
        mint,
        &spl_associated_token_account_interface::program::ID,
    );
    let cu = CREATE_ATA_CU_BASE + Wallet::compute_units_for_bump_seed(bump);
    (address, cu)
}

CREATE_ATA_CU_BASE would be private to the helper module, since the helper itself encapsulates the budget math.

Open question: is there a caller that wants the base constant without going through the helper? If so, we could expose it as pub const CREATE_ATA_CU_BASE: u32. Leaning toward keeping it private until a concrete need arises.

Audit existing call sites and migrate the ones that hardcode the budget today.

Cross-references

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions