#solana #performance #replace #invoke-signed #heap #cpi

solana-invoke

A drop-in replacement for solana_program::program::invoke* with better compute and heap efficiency

5 releases (breaking)

0.5.0 Nov 26, 2025
0.4.0 Aug 28, 2025
0.3.0 Aug 23, 2025
0.2.0 Oct 7, 2024
0.1.0 May 9, 2024

#2 in #invoke-signed

Download history 9380/week @ 2025-10-13 16054/week @ 2025-10-20 11083/week @ 2025-10-27 7938/week @ 2025-11-03 8589/week @ 2025-11-10 15399/week @ 2025-11-17 15328/week @ 2025-11-24 17633/week @ 2025-12-01 16487/week @ 2025-12-08 15477/week @ 2025-12-15 8729/week @ 2025-12-22 9419/week @ 2025-12-29 16170/week @ 2026-01-05 20367/week @ 2026-01-12 17309/week @ 2026-01-19 17018/week @ 2026-01-26

71,960 downloads per month
Used in 184 crates (4 directly)

MIT/Apache

11KB
126 lines

solana-invoke

A drop-in replacement for solana_program::program::invoke* with better compute and heap efficiency

Summary

The current CPI functions solana_program::program::invoke* perform unnecessary copies and allocations. This crate removes these inefficiencies in a manner that is 100% backwards compatible.

The compute and heap savings scale with the amount of accounts and data passed in on CPI. Even in the test program featured in test-program/, which passes in only two accounts and O(16 bytes) of data, a significant saving is observed (overhead reduced from 536 cus -> 197 cus).

use solana_account_info::AccountInfo;
use solana_cpi::invoke;
use solana_program_entrypoint::{entrypoint, ProgramResult};
use solana_pubkey::Pubkey;

// A simple solana program that transfers 1 lamport thrice
fn process_instruction(
    _program_id: &Pubkey,
    accounts: &[AccountInfo],
    _data: &[u8],
) -> ProgramResult {
    // Send from account zero to account one, thrice.
    // 1) First with standard invoke.
    // 2) Then with our invoke
    // 3) Then with our invoke_unchecked
    let transfer =
        solana_system_interface::instruction::transfer(accounts[0].key, accounts[1].key, 1);

    // 1) First with standard invoke_signed.
    solana_cpi::invoke(&transfer, &accounts[..2])?;

    // 2) Then with our invoke_signed
    solana_invoke::invoke(&transfer, &accounts[..2])?;

    // 3) Then with our invoke_unchecked
    solana_invoke::invoke_unchecked(&transfer, &accounts[..2])?;

    Ok(())
}

Output:

Program 1111111QLbz7JHiBTspS962RLKV8GndWFwiEaqKM invoke [1]
Program log: invoking system program via solana_program::program::invoke
Program 11111111111111111111111111111111 invoke [2]
Program 11111111111111111111111111111111 success
Program log: invoked system program via solana_program::program::invoke successfully: 536 cus
Program log: invoking system program via our invoke
Program 11111111111111111111111111111111 invoke [2]
Program 11111111111111111111111111111111 success
Program log: invoked system program via our invoke successfully: 392 cus
Program log: invoking system program via our invoke
Program 11111111111111111111111111111111 invoke [2]
Program 11111111111111111111111111111111 success
Program log: invoked system program via our invoke successfully: 197 cus
Program 1111111QLbz7JHiBTspS962RLKV8GndWFwiEaqKM consumed 7864 of 200000 compute units
Program 1111111QLbz7JHiBTspS962RLKV8GndWFwiEaqKM success

Dependencies

~3–4MB
~92K SLoC