instructions/account_manager/exec.rs, interface.rs.
Flow
Accounts
remaining_accounts, in order:
- The external instruction’s accounts (
call_account_countof them). None is a signer: Vanna signs as the margin. - The allowed-token groups, venue groups and debt groups (see Architecture).
- The oracle segment, including the price accounts of every holding and every token the call will receive.
- The validator segment, only when the validator needs accounts. For Phoenix it is
[vanna_validator, market_book, exchange].
The permit
review_call receives a CallContext { mode, target_program, data, call_account_count, margin, authority, venue } and returns:
The core then enforces the permit:
- Every token in
tokens_inandtokens_outmust be an allowed token. - Each spent vault may drop by at most its cap. A receiving vault must not shrink.
- The margin may appear only where the permit says. The core program, the authority’s wallet and the margin’s other token accounts may not appear anywhere in the call.
- A vault left with a delegate or close authority is refused.
- If the call opens a venue, the venue’s
collateral_enabledmust be on, and the margin must have room undermax_venues_per_margin.
Health
After the call, every holding is revalued. The account must be debt-free or above HF 1.10. A collateral whose price fails a check counts as zero. A debt that is fresh and within confidence but off its TWAP counts at the higher of price and TWAP rather than blocking. There is no minimum output check in the core. Slippage protection is the external program’s own bound (for example Jupiter’s or Titan’s minimum out).Client notes
- The receiving margin vault must exist before the call. The margin account can’t pay rent, so the client creates the ATA idempotently from the wallet in the same transaction.
- Large calls (Phoenix, the basis vaults) need a v0 transaction with an address lookup table and a raised compute-unit limit.
- The app’s builder is
marginExecuteIxinlib/solana/exec.ts.

