From 21eec8cb25ff6226a63afb7eb06e40983581d4f8 Mon Sep 17 00:00:00 2001 From: albert Date: Mon, 30 Sep 2024 15:10:52 +0200 Subject: [PATCH 01/21] chore: adding api call --- .../download-sol-program-idls.sh | 1 + .../v1.0.0/swap_endpoint.json | 655 ++++++++++++++++++ state-chain/chains/src/sol.rs | 2 + state-chain/chains/src/sol/api.rs | 36 + .../sol/sol_tx_core/program_instructions.rs | 18 + .../chains/src/sol/transaction_builder.rs | 45 +- 6 files changed, 754 insertions(+), 3 deletions(-) create mode 100644 contract-interfaces/sol-program-idls/v1.0.0/swap_endpoint.json diff --git a/contract-interfaces/sol-program-idls/download-sol-program-idls.sh b/contract-interfaces/sol-program-idls/download-sol-program-idls.sh index 15f85cd8af..a6f892928e 100755 --- a/contract-interfaces/sol-program-idls/download-sol-program-idls.sh +++ b/contract-interfaces/sol-program-idls/download-sol-program-idls.sh @@ -31,6 +31,7 @@ gh release download \ unzip -u ${ZIP_FILE} \ 'vault.json' \ 'cf_tester.json' \ + 'swap_endpoint.json' \ -d $TARGET_DIR rm ${ZIP_FILE} \ No newline at end of file diff --git a/contract-interfaces/sol-program-idls/v1.0.0/swap_endpoint.json b/contract-interfaces/sol-program-idls/v1.0.0/swap_endpoint.json new file mode 100644 index 0000000000..19f570dfd6 --- /dev/null +++ b/contract-interfaces/sol-program-idls/v1.0.0/swap_endpoint.json @@ -0,0 +1,655 @@ +{ + "address": "35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT", + "metadata": { + "name": "swap_endpoint", + "version": "0.1.0", + "spec": "0.1.0", + "description": "Created with Anchor" + }, + "instructions": [ + { + "name": "close_event_accounts", + "discriminator": [ + 165, + 102, + 61, + 1, + 185, + 77, + 189, + 121 + ], + "accounts": [ + { + "name": "data_account" + }, + { + "name": "agg_key", + "writable": true, + "signer": true + }, + { + "name": "swap_endpoint_data_account", + "writable": true + } + ], + "args": [] + }, + { + "name": "initialize", + "discriminator": [ + 175, + 175, + 109, + 31, + 13, + 152, + 155, + 237 + ], + "accounts": [ + { + "name": "swap_endpoint_data_account", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 100, + 97, + 116, + 97 + ] + } + ] + } + }, + { + "name": "signer", + "writable": true, + "signer": true + }, + { + "name": "system_program", + "address": "11111111111111111111111111111111" + } + ], + "args": [] + }, + { + "name": "x_swap_native", + "discriminator": [ + 163, + 38, + 92, + 226, + 243, + 105, + 141, + 196 + ], + "accounts": [ + { + "name": "data_account" + }, + { + "name": "agg_key", + "writable": true + }, + { + "name": "from", + "writable": true, + "signer": true + }, + { + "name": "event_data_account", + "writable": true, + "signer": true + }, + { + "name": "swap_endpoint_data_account", + "writable": true + }, + { + "name": "system_program", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "swap_native_params", + "type": { + "defined": { + "name": "SwapNativeParams" + } + } + } + ] + }, + { + "name": "x_swap_token", + "discriminator": [ + 69, + 50, + 252, + 99, + 229, + 83, + 119, + 235 + ], + "accounts": [ + { + "name": "data_account" + }, + { + "name": "token_vault_associated_token_account", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "data_account.token_vault_pda", + "account": "DataAccount" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "from", + "writable": true, + "signer": true + }, + { + "name": "from_token_account", + "writable": true + }, + { + "name": "event_data_account", + "writable": true, + "signer": true + }, + { + "name": "swap_endpoint_data_account", + "writable": true + }, + { + "name": "token_supported_account" + }, + { + "name": "token_program", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + }, + { + "name": "mint" + }, + { + "name": "system_program", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "swap_token_params", + "type": { + "defined": { + "name": "SwapTokenParams" + } + } + } + ] + } + ], + "accounts": [ + { + "name": "DataAccount", + "discriminator": [ + 85, + 240, + 182, + 158, + 76, + 7, + 18, + 233 + ] + }, + { + "name": "SupportedToken", + "discriminator": [ + 56, + 162, + 96, + 99, + 193, + 245, + 204, + 108 + ] + }, + { + "name": "SwapEndpointDataAccount", + "discriminator": [ + 79, + 152, + 191, + 225, + 128, + 108, + 11, + 139 + ] + }, + { + "name": "SwapEvent", + "discriminator": [ + 150, + 251, + 114, + 94, + 200, + 113, + 248, + 70 + ] + } + ], + "events": [ + { + "name": "CantDeserializeEventAccount", + "discriminator": [ + 248, + 26, + 198, + 175, + 8, + 58, + 229, + 137 + ] + }, + { + "name": "EventAccountNotTracked", + "discriminator": [ + 202, + 29, + 253, + 107, + 20, + 196, + 36, + 210 + ] + } + ], + "errors": [ + { + "code": 6000, + "name": "MathOverflow", + "msg": "Overflow in arithmetic operation" + }, + { + "code": 6001, + "name": "MathUnderflow", + "msg": "Underflow in arithmetic operation" + } + ], + "types": [ + { + "name": "CantDeserializeEventAccount", + "type": { + "kind": "struct", + "fields": [ + { + "name": "event_account", + "type": "pubkey" + }, + { + "name": "payee", + "type": "pubkey" + } + ] + } + }, + { + "name": "CcmParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "message", + "type": "bytes" + }, + { + "name": "gas_amount", + "type": "u64" + } + ] + } + }, + { + "name": "DataAccount", + "docs": [ + "* ****************************************************************************\n * *************************** IMPORTANT NOTE *********************************\n * ****************************************************************************\n * If the vault is upgraded and the DataAccount struct is modified we need to\n * check the compatibility and ensure there is a proper migration process, given\n * that the Vault bytecode is the only thing being upgraded, not the data account.\n *\n * The easiest approach on upgrade is keeping the DataAccount unchanged and use\n * a new account struct for any new data that is required.\n *\n * DO NOT MODIFY THIS WITHOUT UNDERSTANDING THE CONSEQUENCES!\n * ****************************************************************************\n * ****************************************************************************" + ], + "type": { + "kind": "struct", + "fields": [ + { + "name": "agg_key", + "type": "pubkey" + }, + { + "name": "gov_key", + "type": "pubkey" + }, + { + "name": "token_vault_pda", + "type": "pubkey" + }, + { + "name": "token_vault_bump", + "type": "u8" + }, + { + "name": "upgrade_signer_pda", + "type": "pubkey" + }, + { + "name": "upgrade_signer_pda_bump", + "type": "u8" + }, + { + "name": "suspended", + "type": "bool" + }, + { + "name": "suspended_legacy_swaps", + "type": "bool" + }, + { + "name": "suspended_event_swaps", + "type": "bool" + }, + { + "name": "min_native_swap_amount", + "type": "u64" + }, + { + "name": "max_dst_address_len", + "type": "u16" + }, + { + "name": "max_ccm_message_len", + "type": "u32" + }, + { + "name": "max_cf_parameters_len", + "type": "u32" + }, + { + "name": "max_event_accounts", + "type": "u32" + } + ] + } + }, + { + "name": "EventAccountNotTracked", + "type": { + "kind": "struct", + "fields": [ + { + "name": "event_account", + "type": "pubkey" + }, + { + "name": "payee", + "type": "pubkey" + } + ] + } + }, + { + "name": "SupportedToken", + "type": { + "kind": "struct", + "fields": [ + { + "name": "token_mint_pubkey", + "type": "pubkey" + }, + { + "name": "min_swap_amount", + "type": "u64" + } + ] + } + }, + { + "name": "SwapEndpointDataAccount", + "type": { + "kind": "struct", + "fields": [ + { + "name": "historical_number_event_accounts", + "type": "u128" + }, + { + "name": "open_event_accounts", + "type": { + "vec": "pubkey" + } + } + ] + } + }, + { + "name": "SwapEvent", + "type": { + "kind": "struct", + "fields": [ + { + "name": "sender", + "type": "pubkey" + }, + { + "name": "dst_chain", + "type": "u32" + }, + { + "name": "dst_address", + "type": "bytes" + }, + { + "name": "dst_token", + "type": "u32" + }, + { + "name": "amount", + "type": "u64" + }, + { + "name": "src_token", + "type": { + "option": "pubkey" + } + }, + { + "name": "ccm_parameters", + "type": { + "option": { + "defined": { + "name": "CcmParams" + } + } + } + }, + { + "name": "cf_parameters", + "type": "bytes" + } + ] + } + }, + { + "name": "SwapNativeParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dst_chain", + "type": "u32" + }, + { + "name": "dst_address", + "type": "bytes" + }, + { + "name": "dst_token", + "type": "u32" + }, + { + "name": "ccm_parameters", + "type": { + "option": { + "defined": { + "name": "CcmParams" + } + } + } + }, + { + "name": "cf_parameters", + "type": "bytes" + } + ] + } + }, + { + "name": "SwapTokenParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dst_chain", + "type": "u32" + }, + { + "name": "dst_address", + "type": "bytes" + }, + { + "name": "dst_token", + "type": "u32" + }, + { + "name": "ccm_parameters", + "type": { + "option": { + "defined": { + "name": "CcmParams" + } + } + } + }, + { + "name": "cf_parameters", + "type": "bytes" + }, + { + "name": "decimals", + "type": "u8" + } + ] + } + } + ] +} \ No newline at end of file diff --git a/state-chain/chains/src/sol.rs b/state-chain/chains/src/sol.rs index 04877d7de6..290c0e84d8 100644 --- a/state-chain/chains/src/sol.rs +++ b/state-chain/chains/src/sol.rs @@ -146,6 +146,8 @@ pub mod compute_units_costs { pub const COMPUTE_UNITS_PER_ROTATION: SolComputeLimit = 8_000u32; pub const COMPUTE_UNITS_PER_SET_GOV_KEY: SolComputeLimit = 15_000u32; pub const COMPUTE_UNITS_PER_BUMP_DERIVATION: SolComputeLimit = 2_000u32; + pub const COMPUTE_UNITS_PER_CLOSE_EVENT_ACCOUNTS: SolComputeLimit = 10_000u32; // TODO: To estimate this + pub const COMPUTE_UNITS_PER_CLOSE_ACCOUNT: SolComputeLimit = 10_000u32; // TODO: To estimate this pub const MIN_COMPUTE_PRICE: SolAmount = 10u64; diff --git a/state-chain/chains/src/sol/api.rs b/state-chain/chains/src/sol/api.rs index 4072c268d1..30b061102c 100644 --- a/state-chain/chains/src/sol/api.rs +++ b/state-chain/chains/src/sol/api.rs @@ -23,6 +23,7 @@ use crate::{ }; use cf_primitives::{EgressId, ForeignChain}; +use cf_utilities::bs58_array; #[derive(Clone, Encode, Decode, PartialEq, Debug, TypeInfo)] pub struct ComputePrice; @@ -36,6 +37,7 @@ pub struct ApiEnvironment; pub struct CurrentAggKey; pub type DurableNonceAndAccount = (SolAddress, SolHash); +pub type EventAccountAndSender = (SolAddress, SolAddress); /// Super trait combining all Environment lookups required for the Solana chain. /// Also contains some calls for easy data retrieval. @@ -114,6 +116,7 @@ pub enum SolanaTransactionType { RotateAggKey, CcmTransfer, SetGovKeyWithAggKey, + CloseEventAccounts, } /// The Solana Api call. Contains a call_type and the actual Transaction itself. @@ -370,6 +373,39 @@ impl SolanaApi { _phantom: Default::default(), }) } + + pub fn batch_close_event_accounts( + event_accounts: Vec, + ) -> Result { + // Lookup environment variables, such as aggkey and durable nonce. + let agg_key = Environment::current_agg_key()?; + let sol_api_environment = Environment::api_environment()?; + let compute_price = Environment::compute_price()?; + // TODO: As we do for other fetches we should have checked before that we still + // leave 1 nonce account available for a potential rotation (and potentially more). + let durable_nonce = Environment::nonce_account()?; + // TODO: To implement swap endpoint environment PRO-1521 + // TODO: We should set a limit on the number of event accounts that can be closed at once. + // We might have that limit outside of this function. + + // Build the transaction + let transaction = SolanaTransactionBuilder::close_event_accounts( + event_accounts, + sol_api_environment.vault_program_data_account, + SolAddress(bs58_array("35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT")), /* TODO: Implement PRO-1521 */ + SolAddress(bs58_array("2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9")), /* TODO: Implement PRO-1521 */ + agg_key, + durable_nonce, + compute_price, + )?; + + Ok(Self { + call_type: SolanaTransactionType::CloseEventAccounts, + transaction, + signer: None, + _phantom: Default::default(), + }) + } } impl ApiCall for SolanaApi { diff --git a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs index 54bcd4327c..c06fe9895f 100644 --- a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs +++ b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs @@ -629,6 +629,24 @@ solana_program!( } ); +solana_program!( + idl_path: concat!( + env!("CF_SOL_PROGRAM_IDL_ROOT"), "/", + env!("CF_SOL_PROGRAM_IDL_TAG"), "/" , + "swap_endpoint.json" + ), + SwapEndpointProgram { + close_event_accounts => CloseEventAccounts { + args: [], + account_metas: [ + data_account: { signer: false, writable: false }, + agg_key: { signer: true, writable: true }, + swap_endpoint_data_account: { signer: false, writable: false }, + ] + }, + } +); + #[cfg(test)] mod idl { use serde::{Deserialize, Serialize}; diff --git a/state-chain/chains/src/sol/transaction_builder.rs b/state-chain/chains/src/sol/transaction_builder.rs index 9d281e7995..59af47557e 100644 --- a/state-chain/chains/src/sol/transaction_builder.rs +++ b/state-chain/chains/src/sol/transaction_builder.rs @@ -11,10 +11,11 @@ use sol_prim::consts::{ use crate::{ sol::{ - api::{DurableNonceAndAccount, SolanaTransactionBuildingError}, + api::{DurableNonceAndAccount, EventAccountAndSender, SolanaTransactionBuildingError}, compute_units_costs::{ compute_limit_with_buffer, BASE_COMPUTE_UNITS_PER_TX, - COMPUTE_UNITS_PER_BUMP_DERIVATION, COMPUTE_UNITS_PER_FETCH_NATIVE, + COMPUTE_UNITS_PER_BUMP_DERIVATION, COMPUTE_UNITS_PER_CLOSE_ACCOUNT, + COMPUTE_UNITS_PER_CLOSE_EVENT_ACCOUNTS, COMPUTE_UNITS_PER_FETCH_NATIVE, COMPUTE_UNITS_PER_FETCH_TOKEN, COMPUTE_UNITS_PER_ROTATION, COMPUTE_UNITS_PER_SET_GOV_KEY, COMPUTE_UNITS_PER_TRANSFER_NATIVE, COMPUTE_UNITS_PER_TRANSFER_TOKEN, @@ -22,8 +23,11 @@ use crate::{ sol_tx_core::{ address_derivation::{derive_associated_token_account, derive_fetch_account}, compute_budget::ComputeBudgetInstruction, - program_instructions::{InstructionExt, SystemProgramInstruction, VaultProgram}, + program_instructions::{ + InstructionExt, SwapEndpointProgram, SystemProgramInstruction, VaultProgram, + }, token_instructions::AssociatedTokenAccountInstruction, + AccountMeta, }, AccountBump, SolAddress, SolAmount, SolApiEnvironment, SolAsset, SolCcmAccounts, SolComputeLimit, SolInstruction, SolMessage, SolPubkey, SolTransaction, Solana, @@ -437,6 +441,41 @@ impl SolanaTransactionBuilder { compute_limit_with_buffer(COMPUTE_UNITS_PER_SET_GOV_KEY), ) } + + /// Creates an instruction to close a number of open event swap accounts created via program + /// swap. + pub fn close_event_accounts( + event_accounts: Vec, + vault_program_data_account: SolAddress, + swap_endpoint_program: SolAddress, + swap_endpoint_data_account: SolAddress, + agg_key: SolAddress, + durable_nonce: DurableNonceAndAccount, + compute_price: SolAmount, + ) -> Result { + let number_of_accounts = event_accounts.len(); + let event_and_sender_vec: Vec = event_accounts + .into_iter() + .flat_map(|(event_account, payee)| vec![event_account, payee]) + // Both event account and payee should be writable and non-signers + .map(|address| AccountMeta::new(address.into(), false)) + .collect(); + + let instructions = vec![SwapEndpointProgram::with_id(swap_endpoint_program) + .close_event_accounts(vault_program_data_account, agg_key, swap_endpoint_data_account) + .with_remaining_accounts(event_and_sender_vec)]; + + Self::build( + instructions, + durable_nonce, + agg_key.into(), + compute_price, + compute_limit_with_buffer( + COMPUTE_UNITS_PER_CLOSE_EVENT_ACCOUNTS + + COMPUTE_UNITS_PER_CLOSE_ACCOUNT * number_of_accounts as u32, + ), + ) + } } #[cfg(test)] From 532416f3555e5b22735c42acb37adfc2de069a02 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 14:06:04 +0200 Subject: [PATCH 02/21] chore: add swap endpoint accounts to solEnvApi --- state-chain/chains/src/sol.rs | 4 ++++ state-chain/chains/src/sol/api.rs | 9 +++----- state-chain/chains/src/sol/sol_tx_core.rs | 4 ++++ .../chains/src/sol/transaction_builder.rs | 23 +++++++++++++++++++ 4 files changed, 34 insertions(+), 6 deletions(-) diff --git a/state-chain/chains/src/sol.rs b/state-chain/chains/src/sol.rs index 290c0e84d8..0d35adacba 100644 --- a/state-chain/chains/src/sol.rs +++ b/state-chain/chains/src/sol.rs @@ -369,4 +369,8 @@ pub struct SolApiEnvironment { // For Usdc token pub usdc_token_mint_pubkey: SolAddress, pub usdc_token_vault_ata: SolAddress, + + // For program swaps API calls. + pub swap_endpoint_program: SolAddress, + pub swap_endpoint_program_data_account: SolAddress, } diff --git a/state-chain/chains/src/sol/api.rs b/state-chain/chains/src/sol/api.rs index 30b061102c..e960fd0a44 100644 --- a/state-chain/chains/src/sol/api.rs +++ b/state-chain/chains/src/sol/api.rs @@ -23,7 +23,6 @@ use crate::{ }; use cf_primitives::{EgressId, ForeignChain}; -use cf_utilities::bs58_array; #[derive(Clone, Encode, Decode, PartialEq, Debug, TypeInfo)] pub struct ComputePrice; @@ -383,17 +382,15 @@ impl SolanaApi { let compute_price = Environment::compute_price()?; // TODO: As we do for other fetches we should have checked before that we still // leave 1 nonce account available for a potential rotation (and potentially more). + // That should be done as part of PRO-1520. let durable_nonce = Environment::nonce_account()?; - // TODO: To implement swap endpoint environment PRO-1521 - // TODO: We should set a limit on the number of event accounts that can be closed at once. - // We might have that limit outside of this function. // Build the transaction let transaction = SolanaTransactionBuilder::close_event_accounts( event_accounts, sol_api_environment.vault_program_data_account, - SolAddress(bs58_array("35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT")), /* TODO: Implement PRO-1521 */ - SolAddress(bs58_array("2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9")), /* TODO: Implement PRO-1521 */ + sol_api_environment.swap_endpoint_program, + sol_api_environment.swap_endpoint_program_data_account, agg_key, durable_nonce, compute_price, diff --git a/state-chain/chains/src/sol/sol_tx_core.rs b/state-chain/chains/src/sol/sol_tx_core.rs index 87c249fa18..4f69612bc5 100644 --- a/state-chain/chains/src/sol/sol_tx_core.rs +++ b/state-chain/chains/src/sol/sol_tx_core.rs @@ -906,6 +906,10 @@ pub mod sol_test_values { const_address("GUMpVpQFNYJvSbyTtUarZVL7UDUgErKzDTSVJhekUX55"), const_address("AUiHYbzH7qLZSkb3u7nAqtvqC7e41sEzgWjBEvXrpfGv"), ]; + pub const SWAP_ENDPOINT_PROGRAM: SolAddress = + const_address("35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT"); + pub const SWAP_ENDPOINT_PROGRAM_DATA_ACCOUNT: SolAddress = + const_address("2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9"); pub const RAW_KEYPAIR: [u8; 32] = [ 6, 151, 150, 20, 145, 210, 176, 113, 98, 200, 192, 80, 73, 63, 133, 232, 208, 124, 81, 213, 117, 199, 196, 243, 219, 33, 79, 217, 157, 69, 205, 140, diff --git a/state-chain/chains/src/sol/transaction_builder.rs b/state-chain/chains/src/sol/transaction_builder.rs index 59af47557e..d71f74eaba 100644 --- a/state-chain/chains/src/sol/transaction_builder.rs +++ b/state-chain/chains/src/sol/transaction_builder.rs @@ -526,6 +526,8 @@ mod test { token_vault_pda_account: TOKEN_VAULT_PDA_ACCOUNT, usdc_token_mint_pubkey: USDC_TOKEN_MINT_PUB_KEY, usdc_token_vault_ata: USDC_TOKEN_VAULT_ASSOCIATED_TOKEN_ACCOUNT, + swap_endpoint_program: SWAP_ENDPOINT_PROGRAM, + swap_endpoint_program_data_account: SWAP_ENDPOINT_PROGRAM_DATA_ACCOUNT, } } @@ -717,6 +719,27 @@ mod test { test_constructed_transaction(transaction, expected_serialized_tx); } + #[test] + fn can_close_event_accounts() { + let env = api_env(); + let event_accounts = vec![(FETCH_FROM_ACCOUNT, TRANSFER_TO_ACCOUNT)]; + let transaction = SolanaTransactionBuilder::close_event_accounts( + event_accounts, + env.vault_program_data_account, + env.swap_endpoint_program, + env.swap_endpoint_program_data_account, + agg_key(), + durable_nonce(), + compute_price(), + ) + .unwrap(); + + // Serialized tx built in `create_full_rotation` test + let expected_serialized_tx = hex_literal::hex!("").to_vec(); + + test_constructed_transaction(transaction, expected_serialized_tx); + } + #[test] fn can_calculate_gas_limit() { const TEST_EGRESS_BUDGET: SolAmount = 500_000; From 38b9307a6ff67c97454231e18f758eea1a9b6db3 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 16:01:51 +0200 Subject: [PATCH 03/21] chore: add swap endpoint contract --- bouncer/shared/utils.ts | 2 + .../cf-integration-tests/src/solana.rs | 2 + state-chain/chains/src/sol/sol_tx_core.rs | 46 +++++++++++++++++++ .../sol/sol_tx_core/program_instructions.rs | 43 ++++++++++------- .../chains/src/sol/transaction_builder.rs | 32 +++++++++++-- state-chain/node/src/chain_spec.rs | 19 ++++++++ state-chain/node/src/chain_spec/berghain.rs | 6 +++ .../node/src/chain_spec/perseverance.rs | 6 +++ state-chain/node/src/chain_spec/sisyphos.rs | 6 +++ state-chain/node/src/chain_spec/testnet.rs | 6 +++ 10 files changed, 146 insertions(+), 22 deletions(-) diff --git a/bouncer/shared/utils.ts b/bouncer/shared/utils.ts index f3d0e2c3c8..c6f839cc1c 100644 --- a/bouncer/shared/utils.ts +++ b/bouncer/shared/utils.ts @@ -104,6 +104,8 @@ export function getContractAddress(chain: Chain, contract: string): string { return '8pBPaVfTAcjLeNfC187Fkvi9b1XEFhRNJ95BQXXVksmH'; case 'SWAP_ENDPOINT': return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; + case 'SWAP_ENDPOINT_DATA_ACCOUNT': + return '2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9'; default: throw new Error(`Unsupported contract: ${contract}`); } diff --git a/state-chain/cf-integration-tests/src/solana.rs b/state-chain/cf-integration-tests/src/solana.rs index c01f7c70ad..1c3e4558b1 100644 --- a/state-chain/cf-integration-tests/src/solana.rs +++ b/state-chain/cf-integration-tests/src/solana.rs @@ -57,6 +57,8 @@ fn setup_sol_environments() { token_vault_pda_account: sol_test_values::TOKEN_VAULT_PDA_ACCOUNT, usdc_token_mint_pubkey: sol_test_values::USDC_TOKEN_MINT_PUB_KEY, usdc_token_vault_ata: sol_test_values::USDC_TOKEN_VAULT_ASSOCIATED_TOKEN_ACCOUNT, + swap_endpoint_program: sol_test_values::SWAP_ENDPOINT_PROGRAM, + swap_endpoint_program_data_account: sol_test_values::SWAP_ENDPOINT_PROGRAM_DATA_ACCOUNT, }); // Environment::AvailableDurableNonces diff --git a/state-chain/chains/src/sol/sol_tx_core.rs b/state-chain/chains/src/sol/sol_tx_core.rs index 4f69612bc5..01682b20a4 100644 --- a/state-chain/chains/src/sol/sol_tx_core.rs +++ b/state-chain/chains/src/sol/sol_tx_core.rs @@ -910,6 +910,52 @@ pub mod sol_test_values { const_address("35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT"); pub const SWAP_ENDPOINT_PROGRAM_DATA_ACCOUNT: SolAddress = const_address("2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9"); + pub const EVENT_AND_SENDER_ACCOUNTS: [(SolAddress, SolAddress); 11] = [ + ( + const_address("2cHcSNtikMpjxJfwwoYL3udpy7hedRExyhakk2eZ6cYA"), + const_address("7tVhSXxGfZyHQem8MdZVB6SoRsrvV4H8h1rX6hwBuvEA"), + ), + ( + const_address("6uuU1NFyThN3KJpU9mYXkGSmd8Qgncmd9aYAWYN71VkC"), + const_address("P3GYr1Z67jdBVimzFjMXQpeuew5TY5txoZ9CvqASpaP"), + ), + ( + const_address("DmAom3kp2ZKk9cnbWEsnbkLHkp3sx9ef1EX6GWj1JRUB"), + const_address("CS7yX5TKX36ugF4bycmVQ5vqB2ZbNVC5tvtrtLP92GDW"), + ), + ( + const_address("CJSdHgxwHLEbTsxKsJk9UyJxUEgku2UC9GXRTzR2ieSh"), + const_address("2taCR53epDtdrFZBxzKcbmv3cb5Umc5x9k2YCjmTDAnH"), + ), + ( + const_address("7DGwjsQEFA7XzZS9z5YbMhYGzWJSh5T78hRrU47RDTd2"), + const_address("FDPzoZj951Hq92jhoFdyzAVyUjyXhL8VEnqBhyjsDhow"), + ), + ( + const_address("A6yYXUmZHa32mcFRnwwq8ZQKCEYUn9ewF1vWn2wsXN5a"), + const_address("9bNNNU9B52VPVGm6zRccwPEexDHD1ntndD2aNu2un3ca"), + ), + ( + const_address("2F3365PULNzt7moa9GgHARy7Lumj5ptDQF7wDt6xeuHK"), + const_address("4m5t38fJsvULKaPyWZKWjzfbvnzBGL86BTRNk5vLLUrh"), + ), + ( + const_address("8sCBWv9tzdf2iC4GNj61UBN6TZpzsLP5Ppv9x1ENX4HT"), + const_address("A3P5kfRU1vgZn7GjNMomS8ye6GHsoHC4JoVNUotMbDPE"), + ), + ( + const_address("3b1FkNvnvKJ4TzKeft7wA47VfYpjkoHPE4ER13ZTNecX"), + const_address("ERwuPnX66dCZqj85kH9QQJmwcVrzcczBnu8onJY2R7tG"), + ), + ( + const_address("Bnrp9X562krXVfaY8FnwJa3Mxp1gbDCrvGNW1qc99rKe"), + const_address("2aoZg41FFnTBnuHpkfHdFsCuPz8DhN4dsUW5386XwE8g"), + ), + ( + const_address("EuLceVgXMaJNPT7C88pnL7DRWcf1poy9BCeWY1GL8Agd"), + const_address("G1iXMtwUU76JGau9cJm6N8wBTmcsvyXuJcC7PtfU1TXZ"), + ), + ]; pub const RAW_KEYPAIR: [u8; 32] = [ 6, 151, 150, 20, 145, 210, 176, 113, 98, 200, 192, 80, 73, 63, 133, 232, 208, 124, 81, 213, 117, 199, 196, 243, 219, 33, 79, 217, 157, 69, 205, 140, diff --git a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs index c06fe9895f..2ce10f49a7 100644 --- a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs +++ b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs @@ -629,23 +629,32 @@ solana_program!( } ); -solana_program!( - idl_path: concat!( - env!("CF_SOL_PROGRAM_IDL_ROOT"), "/", - env!("CF_SOL_PROGRAM_IDL_TAG"), "/" , - "swap_endpoint.json" - ), - SwapEndpointProgram { - close_event_accounts => CloseEventAccounts { - args: [], - account_metas: [ - data_account: { signer: false, writable: false }, - agg_key: { signer: true, writable: true }, - swap_endpoint_data_account: { signer: false, writable: false }, - ] - }, - } -); +pub mod swap_endpoints { + // use super::{AccountMeta, Instruction, Pubkey}; + + // use crate::sol::sol_tx_core::program_instructions::ProgramInstruction; + // use borsh::BorshSerialize; + // use sp_std::vec; + use super::*; + + solana_program!( + idl_path: concat!( + env!("CF_SOL_PROGRAM_IDL_ROOT"), "/", + env!("CF_SOL_PROGRAM_IDL_TAG"), "/" , + "swap_endpoint.json" + ), + SwapEndpointProgram { + close_event_accounts => CloseEventAccounts { + args: [], + account_metas: [ + data_account: { signer: false, writable: false }, + agg_key: { signer: true, writable: true }, + swap_endpoint_data_account: { signer: false, writable: true }, + ] + }, + } + ); +} #[cfg(test)] mod idl { diff --git a/state-chain/chains/src/sol/transaction_builder.rs b/state-chain/chains/src/sol/transaction_builder.rs index d71f74eaba..d1b94395ee 100644 --- a/state-chain/chains/src/sol/transaction_builder.rs +++ b/state-chain/chains/src/sol/transaction_builder.rs @@ -24,7 +24,8 @@ use crate::{ address_derivation::{derive_associated_token_account, derive_fetch_account}, compute_budget::ComputeBudgetInstruction, program_instructions::{ - InstructionExt, SwapEndpointProgram, SystemProgramInstruction, VaultProgram, + swap_endpoints::SwapEndpointProgram, InstructionExt, SystemProgramInstruction, + VaultProgram, }, token_instructions::AssociatedTokenAccountInstruction, AccountMeta, @@ -713,7 +714,7 @@ mod test { ) .unwrap(); - // Serialized tx built in `create_full_rotation` test + // Serialized tx built in `rotate_agg_key` test let expected_serialized_tx = hex_literal::hex!("0180d9ae78d86dbf0895772b959d27110d09d8cb0f9bb388cbc84a53372b568ea56cb9f235f05bf59446a18b9e9babdf61e7194cd6f838d6fd6a741e6f60cc300d01000411f79d5e026f12edc6443a534b2cdd5072233989b415d7596573e743f3e5b386fb0e14940a2247d0a8a33650d7dfe12d269ecabce61c1219b5a6dcdb6961026e0917eb2b10d3377bda2bc7bea65bec6b8372f4fc3463ec2cd6f9fde4b2c633d1926744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900448541f57201f277c5f3ffb631d0212e26e7f47749c26c4808718174a0ab2a09a18cd28baa84f2067bbdf24513c2d44e44bf408f2e6da6e60762e3faa4a62a0adbcd644e45426a41a7cb8369b8a0c1c89bb3f86cf278fdd9cc38b0f69784ad5667e392cd98d3284fd551604be95c14cc8e20123e2940ef9fb784e6b591c7442864e5e1869817a4fd88ddf7ab7a5f7252d7c345b39721769888608592912e8ca9acf0f13460b3fd04b7d53d7421fc874ec00eec769cf36480895e1a407bf1249475f2b2e24122be016983be9369965246cc45e1f621d40fba300c56c7ac50c3874df4f83bd213a59c9785110cf83c718f9486c3484f918593bce20c61dc6a96036afecc89e3b031824af6363174d19bbec12d3a13c4a173e5aeb349b63042bc138f00000000000000000000000000000000000000000000000000000000000000000306466fe5211732ffecadba72c39be7bc8ce5bbc5f7126b2c439b3a4000000006a7d517192c568ee08a845f73d29788cf035c3145b21ab344d8062ea940000072b5d2051d300b10b74314b7e25ace9998ca66eb2c7fbc10ef130dd67028293cc27e9074fac5e8d36cf04f94a0606fdd8ddbb420e99a489c7915ce5699e489000e0d03020f0004040000000e00090340420f00000000000e000502e02e000010040100030d094e518fabdda5d68b000d02020024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d020b0024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02090024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d020a0024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02070024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02060024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02040024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d020c0024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02080024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be5439900440d02050024070000006744e9d9790761c45a800a074687b5ff47b449a90c722a3852543be543990044").to_vec(); test_constructed_transaction(transaction, expected_serialized_tx); @@ -722,7 +723,7 @@ mod test { #[test] fn can_close_event_accounts() { let env = api_env(); - let event_accounts = vec![(FETCH_FROM_ACCOUNT, TRANSFER_TO_ACCOUNT)]; + let event_accounts = vec![EVENT_AND_SENDER_ACCOUNTS[0]]; let transaction = SolanaTransactionBuilder::close_event_accounts( event_accounts, env.vault_program_data_account, @@ -734,8 +735,29 @@ mod test { ) .unwrap(); - // Serialized tx built in `create_full_rotation` test - let expected_serialized_tx = hex_literal::hex!("").to_vec(); + // Serialized tx built in `close_event_accounts` test + let expected_serialized_tx = hex_literal::hex!("01026e2d4bdca9e638b59507a70ea62ad88f098ffb25df028a19288702698fdf6d1cf77618b2123c0205a8e8d272ba8ea645b7e75c606ca3aa4356b65fa52ca20b0100050af79d5e026f12edc6443a534b2cdd5072233989b415d7596573e743f3e5b386fb17e5cc1f4d51a40626e11c783b75a45a4922615ecd7f5320b9d4d46481a196a317eb2b10d3377bda2bc7bea65bec6b8372f4fc3463ec2cd6f9fde4b2c633d1921c1f0efc91eeb48bb80c90cf97775cd5d843a96f16500266cee2c20d053152d2665730decf59d4cd6db8437dab77302287431eb7562b5997601851a0eab6946f00000000000000000000000000000000000000000000000000000000000000000306466fe5211732ffecadba72c39be7bc8ce5bbc5f7126b2c439b3a4000000006a7d517192c568ee08a845f73d29788cf035c3145b21ab344d8062ea94000000e14940a2247d0a8a33650d7dfe12d269ecabce61c1219b5a6dcdb6961026e091ef91c791d2aa8492c90f12540abd10056ce5dd8d9ab08461476c1dcc1622938c27e9074fac5e8d36cf04f94a0606fdd8ddbb420e99a489c7915ce5699e4890004050302070004040000000600090340420f000000000006000502307500000905080003010408a5663d01b94dbd79").to_vec(); + + test_constructed_transaction(transaction, expected_serialized_tx); + } + + #[test] + fn can_close_max_event_accounts() { + let env = api_env(); + + // We can close 11 accounts without reaching the transaction length limit. + let transaction = SolanaTransactionBuilder::close_event_accounts( + EVENT_AND_SENDER_ACCOUNTS.to_vec(), + env.vault_program_data_account, + env.swap_endpoint_program, + env.swap_endpoint_program_data_account, + agg_key(), + durable_nonce(), + compute_price(), + ) + .unwrap(); + + let expected_serialized_tx = hex_literal::hex!("01361c7baab92d2d4599136442ad7d4c1d51fedc6749d44f3a8e8405cc19983862c885526b293ed79d0253d44e174705db9050638d1ffc31b6f7b586b269fea4030100051ef79d5e026f12edc6443a534b2cdd5072233989b415d7596573e743f3e5b386fb05a557a331e51b8bf444d3bacdf6f48d8fd583aa79f9b956dd68f13a67ad096412741ecfad8423dea0c173b354b32309c3e97bb1dc68e0d858c3caebc1a1701a178480c19a99c9f2b95d40ebcb55057a49f0df00e123da6ae5e85a77c282f7c117e5cc1f4d51a40626e11c783b75a45a4922615ecd7f5320b9d4d46481a196a317eb2b10d3377bda2bc7bea65bec6b8372f4fc3463ec2cd6f9fde4b2c633d1921c11d80c98e8c11e79fd97b6c10ad733782bdbe25a710b807bbf14dedaa314861c1f0efc91eeb48bb80c90cf97775cd5d843a96f16500266cee2c20d053152d2266d68abb283ba2f4cecb092e3cfed2cb1774468ebbc264426c268ff405aa5a837de225793278f0575804f7d969e1980caaa5c5ddb2aebfd8496b14e71c9fad657d7f5b3e6c340824caca3b6c34c03e2fe0e636430b2b729ddfe32146ba4b3795c4b1e73c84b8d3f9e006c22fe8b865b9900e296345d88cdaaa7077ef17d9a31665730decf59d4cd6db8437dab77302287431eb7562b5997601851a0eab6946f74dd7ddee33a59ae7431bb31fbeb738cbfd097a66fd6706cffe7fc7efb239ec67fab67806fbb92ffd9504f4411b7f4561a0efb16685e4a22c41373fedc50b4bf86554fe5208d48fc8198310804e59837443fdaab12ea97be0fa38049910da82987410536ffebba5f49e67bafd3aa4b6cc860a594641e801500e058f74bac504da054544b2425f722e18c810bbc6cb6b9045d0db0a62d529af30efde8c37255bda7e867ab720f01897e5ede67fc232e41729d0be2a530391619743822ff6d95bea9dff663e1d13345d96daede8066cd30a1474635f2d64052d1a50ac04aed3f99bd9ce2f9674b65bfaefb62c9b8252fd0080357b1cbff44d0dad8568535dbc230c78bf2e7aee8e16631746542ef634cee3ac9bdc044c491f06862590ff1029865ce904f76d0a0ffedad66f8e2c94bccc731cac372fef8bb12cd2c473d95acf366d33096c9d0fa193639345c07abfe81175fc4d153cf0ab7b5668006538f195382df0e412e53b45bf52f91fa8e70ea872687428e4cb372306b9e6073f8d3c270c400000000000000000000000000000000000000000000000000000000000000000306466fe5211732ffecadba72c39be7bc8ce5bbc5f7126b2c439b3a4000000006a7d517192c568ee08a845f73d29788cf035c3145b21ab344d8062ea94000000e14940a2247d0a8a33650d7dfe12d269ecabce61c1219b5a6dcdb6961026e091ef91c791d2aa8492c90f12540abd10056ce5dd8d9ab08461476c1dcc1622938c27e9074fac5e8d36cf04f94a0606fdd8ddbb420e99a489c7915ce5699e48900041903051b0004040000001a00090340420f00000000001a00050220bf02001d191c0007040c0a01141312060b17100e02090d0f08151103161808a5663d01b94dbd79").to_vec(); test_constructed_transaction(transaction, expected_serialized_tx); } diff --git a/state-chain/node/src/chain_spec.rs b/state-chain/node/src/chain_spec.rs index 29f971fcb2..f6ce8fdbdc 100644 --- a/state-chain/node/src/chain_spec.rs +++ b/state-chain/node/src/chain_spec.rs @@ -111,6 +111,8 @@ pub struct StateChainEnvironment { sol_durable_nonces_and_accounts: [DurableNonceAndAccount; 10], /* we inject 10 nonce * accounts * at genesis */ + sol_swap_endpoint_program: SolAddress, + sol_swap_endpoint_program_data_account: SolAddress, } /// Get the values from the State Chain's environment variables. Else set them via the defaults @@ -156,6 +158,12 @@ pub fn get_environment_or_defaults(defaults: StateChainEnvironment) -> StateChai from_env_var!(FromStr::from_str, SOL_TOKEN_VAULT_PDA_ACCOUNT, sol_token_vault_pda_account); from_env_var!(FromStr::from_str, SOL_USDC_TOKEN_MINT_PUBKEY, sol_usdc_token_mint_pubkey); from_env_var!(FromStr::from_str, SOL_USDC_TOKEN_VAULT_ATA, sol_usdc_token_vault_ata); + from_env_var!(FromStr::from_str, SOL_SWAP_ENDPOINT_PROGRAM, sol_swap_endpoint_program); + from_env_var!( + FromStr::from_str, + SOL_SWAP_ENDPOINT_PROGRAM_DATA_ACCOUNT, + sol_swap_endpoint_program_data_account + ); let dot_genesis_hash = match env::var("DOT_GENESIS_HASH") { Ok(s) => hex_decode::<32>(&s).unwrap().into(), @@ -216,6 +224,8 @@ pub fn get_environment_or_defaults(defaults: StateChainEnvironment) -> StateChai sol_token_vault_pda_account, sol_usdc_token_vault_ata, sol_durable_nonces_and_accounts, + sol_swap_endpoint_program, + sol_swap_endpoint_program_data_account, } } @@ -283,6 +293,8 @@ pub fn inner_cf_development_config( sol_token_vault_pda_account, sol_usdc_token_vault_ata, sol_durable_nonces_and_accounts, + sol_swap_endpoint_program, + sol_swap_endpoint_program_data_account, } = get_environment_or_defaults(testnet::ENV); Ok(ChainSpec::builder(wasm_binary, None) .with_name("CF Develop") @@ -320,6 +332,8 @@ pub fn inner_cf_development_config( usdc_token_mint_pubkey: sol_usdc_token_mint_pubkey, token_vault_pda_account: sol_token_vault_pda_account, usdc_token_vault_ata: sol_usdc_token_vault_ata, + swap_endpoint_program: sol_swap_endpoint_program, + swap_endpoint_program_data_account: sol_swap_endpoint_program_data_account, }, sol_durable_nonces_and_accounts: sol_durable_nonces_and_accounts.to_vec(), network_environment: NetworkEnvironment::Development, @@ -409,6 +423,8 @@ macro_rules! network_spec { sol_token_vault_pda_account, sol_usdc_token_vault_ata, sol_durable_nonces_and_accounts, + sol_swap_endpoint_program, + sol_swap_endpoint_program_data_account, } = env_override.unwrap_or(ENV); let protocol_id = format!( "{}-{}", @@ -478,6 +494,9 @@ macro_rules! network_spec { usdc_token_mint_pubkey: sol_usdc_token_mint_pubkey, token_vault_pda_account: sol_token_vault_pda_account, usdc_token_vault_ata: sol_usdc_token_vault_ata, + swap_endpoint_program: sol_swap_endpoint_program, + swap_endpoint_program_data_account: + sol_swap_endpoint_program_data_account, }, network_environment: NETWORK_ENVIRONMENT, ..Default::default() diff --git a/state-chain/node/src/chain_spec/berghain.rs b/state-chain/node/src/chain_spec/berghain.rs index 4c952773aa..dbde497410 100644 --- a/state-chain/node/src/chain_spec/berghain.rs +++ b/state-chain/node/src/chain_spec/berghain.rs @@ -106,6 +106,12 @@ pub const ENV: StateChainEnvironment = StateChainEnvironment { const_hash("AEzmj9wq8jp7wF46Lrr3Jc2K7xRP58V5Y3cYRVEqtE5J"), ), ], + sol_swap_endpoint_program: SolAddress(bs58_array( + "BnECXbsDFYPmhxcV57dodaWtJJjtGPE8Le3LAR7qieYb", + )), + sol_swap_endpoint_program_data_account: SolAddress(bs58_array( + "5mFsKrqCH5v9Q9uF5o6qrsUi1GV2myuhc23NAi5YFs4M", + )), }; pub const EPOCH_DURATION_BLOCKS: BlockNumber = 24 * HOURS; diff --git a/state-chain/node/src/chain_spec/perseverance.rs b/state-chain/node/src/chain_spec/perseverance.rs index bf5feafb01..04456f7c4c 100644 --- a/state-chain/node/src/chain_spec/perseverance.rs +++ b/state-chain/node/src/chain_spec/perseverance.rs @@ -106,6 +106,12 @@ pub const ENV: StateChainEnvironment = StateChainEnvironment { const_hash("FS1PdTqsDSEa9xUrLAS5k471MQsT28H2FW5CpUHiTmGF"), ), ], + sol_swap_endpoint_program: SolAddress(bs58_array( + "FXN1iLmQ47c962nackmzBWZxXE8BR9AXy8mu34oFdKiy", + )), + sol_swap_endpoint_program_data_account: SolAddress(bs58_array( + "4hD7UM6rQtcqQWtzELvrafpmBYReVXvCpssB6qjY1Sg5", + )), }; pub const EPOCH_DURATION_BLOCKS: BlockNumber = 24 * HOURS; diff --git a/state-chain/node/src/chain_spec/sisyphos.rs b/state-chain/node/src/chain_spec/sisyphos.rs index 6f61b90257..9090650de6 100644 --- a/state-chain/node/src/chain_spec/sisyphos.rs +++ b/state-chain/node/src/chain_spec/sisyphos.rs @@ -107,6 +107,12 @@ pub const ENV: StateChainEnvironment = StateChainEnvironment { const_hash("3iiniRfNTFmBn6Y9ZhovefUDaGaJ7buB2vYemnbFoHN3"), ), ], + sol_swap_endpoint_program: SolAddress(bs58_array( + "7G6TxoGDsgaZX3HaKkrKyy28tsdr7ZGmeeMbXpm8R5HZ", + )), + sol_swap_endpoint_program_data_account: SolAddress(bs58_array( + "mYabVW1uMXpGqwgHUBQu4Fg6GT9EMYUzYaGYbi3zgT7", + )), }; pub const BASHFUL_ACCOUNT_ID: &str = "cFLbasoV5juCGacy9LvvwSgkupFiFmwt8RmAuA3xcaY5YmkBe"; diff --git a/state-chain/node/src/chain_spec/testnet.rs b/state-chain/node/src/chain_spec/testnet.rs index f98a35eb99..b7760125d0 100644 --- a/state-chain/node/src/chain_spec/testnet.rs +++ b/state-chain/node/src/chain_spec/testnet.rs @@ -102,6 +102,12 @@ pub const ENV: StateChainEnvironment = StateChainEnvironment { const_hash("Hgr7AdqH4nQiau7raNF2ShTZqUfnE3D5AMX2nwYzHuJT"), ), ], + sol_swap_endpoint_program: SolAddress(bs58_array( + "35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT", + )), + sol_swap_endpoint_program_data_account: SolAddress(bs58_array( + "2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9", + )), }; pub const EPOCH_DURATION_BLOCKS: BlockNumber = 3 * HOURS; From f21e3790032acc79dc854520b66e765c579ce8b1 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 16:18:20 +0200 Subject: [PATCH 04/21] chore: add swap endpoint initialization --- .github/workflows/ci-development.yml | 9 +-------- bouncer/commands/setup_vaults.ts | 2 +- bouncer/shared/contract_interfaces.ts | 3 +++ bouncer/shared/initialize_new_chains.ts | 24 +++++++++++++++++++++++- bouncer/shared/utils.ts | 2 +- 5 files changed, 29 insertions(+), 11 deletions(-) diff --git a/.github/workflows/ci-development.yml b/.github/workflows/ci-development.yml index d5356303aa..c7e7e7734a 100644 --- a/.github/workflows/ci-development.yml +++ b/.github/workflows/ci-development.yml @@ -1,13 +1,6 @@ # This CI runs a lot of the jobs in parallel to speed up development time. We also run a simpler suite of bouncer tests. name: Release Chainflip Development -on: - pull_request: - branches: - - main - - "release/*" -concurrency: - group: ${{ github.ref }}-release-development - cancel-in-progress: true +on: push jobs: pre-check: diff --git a/bouncer/commands/setup_vaults.ts b/bouncer/commands/setup_vaults.ts index a0f2d61829..e91b0130c4 100755 --- a/bouncer/commands/setup_vaults.ts +++ b/bouncer/commands/setup_vaults.ts @@ -163,7 +163,7 @@ async function main(): Promise { // Confirmation console.log('Waiting for new epoch...'); - await observeEvent('validator:NewEpoch'); + await observeEvent('validator:NewEpoch').event; console.log('=== New Epoch ==='); console.log('=== Vault Setup completed ==='); diff --git a/bouncer/shared/contract_interfaces.ts b/bouncer/shared/contract_interfaces.ts index 4a32e53262..c9be8ad379 100644 --- a/bouncer/shared/contract_interfaces.ts +++ b/bouncer/shared/contract_interfaces.ts @@ -32,3 +32,6 @@ export const getSolanaVaultIdl = loadContractCached( export const getCfTesterIdl = loadContractCached( `../contract-interfaces/sol-program-idls/${CF_SOL_PROGRAM_IDL_TAG}/cf_tester.json`, ); +export const getSolanaSwapEndpointIdl = loadContractCached( + `../contract-interfaces/sol-program-idls/${CF_SOL_PROGRAM_IDL_TAG}/swap_endpoint.json`, +); \ No newline at end of file diff --git a/bouncer/shared/initialize_new_chains.ts b/bouncer/shared/initialize_new_chains.ts index 344d9acf26..5fcedfa902 100644 --- a/bouncer/shared/initialize_new_chains.ts +++ b/bouncer/shared/initialize_new_chains.ts @@ -14,7 +14,7 @@ import { solanaNumberOfNonces, } from '../shared/utils'; import { sendSol, signAndSendTxSol } from '../shared/send_sol'; -import { getSolanaVaultIdl, getKeyManagerAbi } from '../shared/contract_interfaces'; +import { getSolanaVaultIdl, getKeyManagerAbi, getSolanaSwapEndpointIdl } from '../shared/contract_interfaces'; import { signAndSendTxEvm } from '../shared/send_evm'; import { submitGovernanceExtrinsic } from './cf_governance'; import { observeEvent } from './utils/substrate'; @@ -232,4 +232,26 @@ export async function initializeSolanaPrograms(solClient: Connection, solKey: st }), ); await signAndSendTxSol(tx); + + // Initialize the Swap Endpoint Data Account + const swapEndpointDataAccount = new PublicKey(getContractAddress('Solana', 'SWAP_ENDPOINT_DATA_ACCOUNT')); + const swapEndpointIdl: any = await getSolanaSwapEndpointIdl(); + + const swapEndpointInitializeDiscriminatorString = swapEndpointIdl.instructions.find( + (instruction: { name: string }) => instruction.name === 'initialize', + ).discriminator; + const swapEndpointInitializeDiscriminator = new Uint8Array(swapEndpointInitializeDiscriminatorString.map(Number)); + + tx = new Transaction().add( + new TransactionInstruction({ + data: Buffer.from(swapEndpointInitializeDiscriminator.buffer), + keys: [ + { pubkey: swapEndpointDataAccount, isSigner: false, isWritable: true }, + { pubkey: whaleKeypair.publicKey, isSigner: true, isWritable: false }, + { pubkey: SystemProgram.programId, isSigner: false, isWritable: false }, + ], + programId: swapEndpointIdl, + }), + ); + await signAndSendTxSol(tx); } diff --git a/bouncer/shared/utils.ts b/bouncer/shared/utils.ts index c6f839cc1c..631400e4d7 100644 --- a/bouncer/shared/utils.ts +++ b/bouncer/shared/utils.ts @@ -105,7 +105,7 @@ export function getContractAddress(chain: Chain, contract: string): string { case 'SWAP_ENDPOINT': return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; case 'SWAP_ENDPOINT_DATA_ACCOUNT': - return '2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9'; + return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; default: throw new Error(`Unsupported contract: ${contract}`); } From 9e0de52be27054db7ad3e3dab9dae1cddb94da5b Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 16:40:08 +0200 Subject: [PATCH 05/21] chore: fix lint and initialization --- bouncer/shared/contract_interfaces.ts | 2 +- bouncer/shared/initialize_new_chains.ts | 19 +++++++++++++++---- bouncer/shared/utils.ts | 2 +- 3 files changed, 17 insertions(+), 6 deletions(-) diff --git a/bouncer/shared/contract_interfaces.ts b/bouncer/shared/contract_interfaces.ts index c9be8ad379..b909d41364 100644 --- a/bouncer/shared/contract_interfaces.ts +++ b/bouncer/shared/contract_interfaces.ts @@ -34,4 +34,4 @@ export const getCfTesterIdl = loadContractCached( ); export const getSolanaSwapEndpointIdl = loadContractCached( `../contract-interfaces/sol-program-idls/${CF_SOL_PROGRAM_IDL_TAG}/swap_endpoint.json`, -); \ No newline at end of file +); diff --git a/bouncer/shared/initialize_new_chains.ts b/bouncer/shared/initialize_new_chains.ts index 5fcedfa902..d089f20c0a 100644 --- a/bouncer/shared/initialize_new_chains.ts +++ b/bouncer/shared/initialize_new_chains.ts @@ -14,7 +14,11 @@ import { solanaNumberOfNonces, } from '../shared/utils'; import { sendSol, signAndSendTxSol } from '../shared/send_sol'; -import { getSolanaVaultIdl, getKeyManagerAbi, getSolanaSwapEndpointIdl } from '../shared/contract_interfaces'; +import { + getSolanaVaultIdl, + getKeyManagerAbi, + getSolanaSwapEndpointIdl, +} from '../shared/contract_interfaces'; import { signAndSendTxEvm } from '../shared/send_evm'; import { submitGovernanceExtrinsic } from './cf_governance'; import { observeEvent } from './utils/substrate'; @@ -234,13 +238,20 @@ export async function initializeSolanaPrograms(solClient: Connection, solKey: st await signAndSendTxSol(tx); // Initialize the Swap Endpoint Data Account - const swapEndpointDataAccount = new PublicKey(getContractAddress('Solana', 'SWAP_ENDPOINT_DATA_ACCOUNT')); + const swapEndpointProgramId = new PublicKey(getContractAddress('Solana', 'SWAP_ENDPOINT')); + const swapEndpointDataAccount = new PublicKey( + getContractAddress('Solana', 'SWAP_ENDPOINT_DATA_ACCOUNT'), + ); + + // eslint-disable-next-line @typescript-eslint/no-explicit-any const swapEndpointIdl: any = await getSolanaSwapEndpointIdl(); const swapEndpointInitializeDiscriminatorString = swapEndpointIdl.instructions.find( (instruction: { name: string }) => instruction.name === 'initialize', ).discriminator; - const swapEndpointInitializeDiscriminator = new Uint8Array(swapEndpointInitializeDiscriminatorString.map(Number)); + const swapEndpointInitializeDiscriminator = new Uint8Array( + swapEndpointInitializeDiscriminatorString.map(Number), + ); tx = new Transaction().add( new TransactionInstruction({ @@ -250,7 +261,7 @@ export async function initializeSolanaPrograms(solClient: Connection, solKey: st { pubkey: whaleKeypair.publicKey, isSigner: true, isWritable: false }, { pubkey: SystemProgram.programId, isSigner: false, isWritable: false }, ], - programId: swapEndpointIdl, + programId: swapEndpointProgramId, }), ); await signAndSendTxSol(tx); diff --git a/bouncer/shared/utils.ts b/bouncer/shared/utils.ts index 631400e4d7..655ad1cbdd 100644 --- a/bouncer/shared/utils.ts +++ b/bouncer/shared/utils.ts @@ -105,7 +105,7 @@ export function getContractAddress(chain: Chain, contract: string): string { case 'SWAP_ENDPOINT': return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; case 'SWAP_ENDPOINT_DATA_ACCOUNT': - return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; + return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; default: throw new Error(`Unsupported contract: ${contract}`); } From 8910e63515409f8233d20fcc688aadfab46aadd1 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 17:06:14 +0200 Subject: [PATCH 06/21] chore: update swap endpoint data account --- bouncer/shared/utils.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bouncer/shared/utils.ts b/bouncer/shared/utils.ts index 655ad1cbdd..dfe68a4eb8 100644 --- a/bouncer/shared/utils.ts +++ b/bouncer/shared/utils.ts @@ -105,7 +105,7 @@ export function getContractAddress(chain: Chain, contract: string): string { case 'SWAP_ENDPOINT': return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; case 'SWAP_ENDPOINT_DATA_ACCOUNT': - return '35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT'; + return '2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9'; default: throw new Error(`Unsupported contract: ${contract}`); } From be4303320e8f011047c06528f6211c0b349caa47 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 17:27:58 +0200 Subject: [PATCH 07/21] chore: remove initialization as its already done in image --- bouncer/shared/initialize_new_chains.ts | 35 +------------------------ 1 file changed, 1 insertion(+), 34 deletions(-) diff --git a/bouncer/shared/initialize_new_chains.ts b/bouncer/shared/initialize_new_chains.ts index d089f20c0a..344d9acf26 100644 --- a/bouncer/shared/initialize_new_chains.ts +++ b/bouncer/shared/initialize_new_chains.ts @@ -14,11 +14,7 @@ import { solanaNumberOfNonces, } from '../shared/utils'; import { sendSol, signAndSendTxSol } from '../shared/send_sol'; -import { - getSolanaVaultIdl, - getKeyManagerAbi, - getSolanaSwapEndpointIdl, -} from '../shared/contract_interfaces'; +import { getSolanaVaultIdl, getKeyManagerAbi } from '../shared/contract_interfaces'; import { signAndSendTxEvm } from '../shared/send_evm'; import { submitGovernanceExtrinsic } from './cf_governance'; import { observeEvent } from './utils/substrate'; @@ -236,33 +232,4 @@ export async function initializeSolanaPrograms(solClient: Connection, solKey: st }), ); await signAndSendTxSol(tx); - - // Initialize the Swap Endpoint Data Account - const swapEndpointProgramId = new PublicKey(getContractAddress('Solana', 'SWAP_ENDPOINT')); - const swapEndpointDataAccount = new PublicKey( - getContractAddress('Solana', 'SWAP_ENDPOINT_DATA_ACCOUNT'), - ); - - // eslint-disable-next-line @typescript-eslint/no-explicit-any - const swapEndpointIdl: any = await getSolanaSwapEndpointIdl(); - - const swapEndpointInitializeDiscriminatorString = swapEndpointIdl.instructions.find( - (instruction: { name: string }) => instruction.name === 'initialize', - ).discriminator; - const swapEndpointInitializeDiscriminator = new Uint8Array( - swapEndpointInitializeDiscriminatorString.map(Number), - ); - - tx = new Transaction().add( - new TransactionInstruction({ - data: Buffer.from(swapEndpointInitializeDiscriminator.buffer), - keys: [ - { pubkey: swapEndpointDataAccount, isSigner: false, isWritable: true }, - { pubkey: whaleKeypair.publicKey, isSigner: true, isWritable: false }, - { pubkey: SystemProgram.programId, isSigner: false, isWritable: false }, - ], - programId: swapEndpointProgramId, - }), - ); - await signAndSendTxSol(tx); } From 05bf121d7afce0679707ea2095426bd98d57aeb3 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 1 Oct 2024 17:29:46 +0200 Subject: [PATCH 08/21] chore: cleanup --- .../chains/src/sol/sol_tx_core/program_instructions.rs | 5 ----- 1 file changed, 5 deletions(-) diff --git a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs index 2ce10f49a7..dccf261237 100644 --- a/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs +++ b/state-chain/chains/src/sol/sol_tx_core/program_instructions.rs @@ -630,11 +630,6 @@ solana_program!( ); pub mod swap_endpoints { - // use super::{AccountMeta, Instruction, Pubkey}; - - // use crate::sol::sol_tx_core::program_instructions::ProgramInstruction; - // use borsh::BorshSerialize; - // use sp_std::vec; use super::*; solana_program!( From 903db1b02be2c1bb87ae503b97c7a735e18d57ed Mon Sep 17 00:00:00 2001 From: albert Date: Wed, 2 Oct 2024 11:25:27 +0200 Subject: [PATCH 09/21] chore: restore ci --- .github/workflows/ci-development.yml | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/.github/workflows/ci-development.yml b/.github/workflows/ci-development.yml index c7e7e7734a..d5356303aa 100644 --- a/.github/workflows/ci-development.yml +++ b/.github/workflows/ci-development.yml @@ -1,6 +1,13 @@ # This CI runs a lot of the jobs in parallel to speed up development time. We also run a simpler suite of bouncer tests. name: Release Chainflip Development -on: push +on: + pull_request: + branches: + - main + - "release/*" +concurrency: + group: ${{ github.ref }}-release-development + cancel-in-progress: true jobs: pre-check: From f4b573c99ecc3cce494cae6c464c10e850e68653 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 8 Oct 2024 10:25:35 +0200 Subject: [PATCH 10/21] chore: remove unnecessary TODOs --- state-chain/chains/src/sol.rs | 4 ++-- state-chain/chains/src/sol/api.rs | 3 --- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/state-chain/chains/src/sol.rs b/state-chain/chains/src/sol.rs index 0d35adacba..37503876ac 100644 --- a/state-chain/chains/src/sol.rs +++ b/state-chain/chains/src/sol.rs @@ -146,8 +146,8 @@ pub mod compute_units_costs { pub const COMPUTE_UNITS_PER_ROTATION: SolComputeLimit = 8_000u32; pub const COMPUTE_UNITS_PER_SET_GOV_KEY: SolComputeLimit = 15_000u32; pub const COMPUTE_UNITS_PER_BUMP_DERIVATION: SolComputeLimit = 2_000u32; - pub const COMPUTE_UNITS_PER_CLOSE_EVENT_ACCOUNTS: SolComputeLimit = 10_000u32; // TODO: To estimate this - pub const COMPUTE_UNITS_PER_CLOSE_ACCOUNT: SolComputeLimit = 10_000u32; // TODO: To estimate this + pub const COMPUTE_UNITS_PER_CLOSE_EVENT_ACCOUNTS: SolComputeLimit = 10_000u32; + pub const COMPUTE_UNITS_PER_CLOSE_ACCOUNT: SolComputeLimit = 10_000u32; pub const MIN_COMPUTE_PRICE: SolAmount = 10u64; diff --git a/state-chain/chains/src/sol/api.rs b/state-chain/chains/src/sol/api.rs index e960fd0a44..2d882d3ecd 100644 --- a/state-chain/chains/src/sol/api.rs +++ b/state-chain/chains/src/sol/api.rs @@ -380,9 +380,6 @@ impl SolanaApi { let agg_key = Environment::current_agg_key()?; let sol_api_environment = Environment::api_environment()?; let compute_price = Environment::compute_price()?; - // TODO: As we do for other fetches we should have checked before that we still - // leave 1 nonce account available for a potential rotation (and potentially more). - // That should be done as part of PRO-1520. let durable_nonce = Environment::nonce_account()?; // Build the transaction From 833de6435707923e43ad8fdd65eeb1f343ea6905 Mon Sep 17 00:00:00 2001 From: Roy Yang Date: Fri, 11 Oct 2024 17:39:17 +1300 Subject: [PATCH 11/21] Added storage migration for Environment pallet. --- .../pallets/cf-broadcast/src/migrations.rs | 2 +- state-chain/pallets/cf-environment/src/lib.rs | 2 +- .../pallets/cf-environment/src/migrations.rs | 2 +- state-chain/runtime/src/lib.rs | 7 +- state-chain/runtime/src/migrations.rs | 1 + .../src/migrations/sol_api_environment.rs | 96 +++++++++++++++++++ 6 files changed, 106 insertions(+), 4 deletions(-) create mode 100644 state-chain/runtime/src/migrations/sol_api_environment.rs diff --git a/state-chain/pallets/cf-broadcast/src/migrations.rs b/state-chain/pallets/cf-broadcast/src/migrations.rs index 3cb192c8a8..6942d64c78 100644 --- a/state-chain/pallets/cf-broadcast/src/migrations.rs +++ b/state-chain/pallets/cf-broadcast/src/migrations.rs @@ -7,5 +7,5 @@ mod migrate_timeouts; pub type PalletMigration = ( VersionedMigration, initialize_broadcast_timeout_storage::Migration, 6, 7>, VersionedMigration, migrate_timeouts::Migration, 7, 8>, - PlaceholderMigration, 8>, + PlaceholderMigration, 9>, ); diff --git a/state-chain/pallets/cf-environment/src/lib.rs b/state-chain/pallets/cf-environment/src/lib.rs index 4b62f53cb7..08cf3a06a1 100644 --- a/state-chain/pallets/cf-environment/src/lib.rs +++ b/state-chain/pallets/cf-environment/src/lib.rs @@ -37,7 +37,7 @@ pub mod weights; pub use weights::WeightInfo; pub mod migrations; -pub const PALLET_VERSION: StorageVersion = StorageVersion::new(12); +pub const PALLET_VERSION: StorageVersion = StorageVersion::new(13); const INITIAL_CONSOLIDATION_PARAMETERS: utxo_selection::ConsolidationParameters = utxo_selection::ConsolidationParameters { diff --git a/state-chain/pallets/cf-environment/src/migrations.rs b/state-chain/pallets/cf-environment/src/migrations.rs index daf793873b..15e032cf04 100644 --- a/state-chain/pallets/cf-environment/src/migrations.rs +++ b/state-chain/pallets/cf-environment/src/migrations.rs @@ -32,7 +32,7 @@ impl OnRuntimeUpgrade for VersionUpdate { } } -pub type PalletMigration = PlaceholderMigration, 12>; +pub type PalletMigration = PlaceholderMigration, 13>; #[cfg(test)] mod tests { diff --git a/state-chain/runtime/src/lib.rs b/state-chain/runtime/src/lib.rs index 02a2d5e93d..3ab8ebbf9e 100644 --- a/state-chain/runtime/src/lib.rs +++ b/state-chain/runtime/src/lib.rs @@ -19,7 +19,10 @@ use crate::{ }, Offence, }, - migrations::serialize_solana_broadcast::{NoopUpgrade, SerializeSolanaBroadcastMigration}, + migrations::{ + serialize_solana_broadcast::{NoopUpgrade, SerializeSolanaBroadcastMigration}, + sol_api_environment::SolApiEnvironmentMigration, + }, monitoring_apis::{ AuthoritiesInfo, BtcUtxos, EpochState, ExternalChainsBlockHeight, FeeImbalance, FlipSupply, LastRuntimeUpgradeInfo, MonitoringData, OpenDepositChannels, PendingBroadcasts, @@ -1264,6 +1267,8 @@ type MigrationsForV1_7 = ( VersionedMigration, NoopUpgrade, 8, 9>, VersionedMigration, NoopUpgrade, 8, 9>, VersionedMigration, NoopUpgrade, 8, 9>, + // Migration for Updating Solana's Api Environments. + VersionedMigration, SolApiEnvironmentMigration, 12, 13>, ); #[cfg(feature = "runtime-benchmarks")] diff --git a/state-chain/runtime/src/migrations.rs b/state-chain/runtime/src/migrations.rs index 03fc5f0beb..09de81f1fa 100644 --- a/state-chain/runtime/src/migrations.rs +++ b/state-chain/runtime/src/migrations.rs @@ -3,3 +3,4 @@ pub mod housekeeping; pub mod reap_old_accounts; pub mod serialize_solana_broadcast; +pub mod sol_api_environment; diff --git a/state-chain/runtime/src/migrations/sol_api_environment.rs b/state-chain/runtime/src/migrations/sol_api_environment.rs new file mode 100644 index 0000000000..649b54682e --- /dev/null +++ b/state-chain/runtime/src/migrations/sol_api_environment.rs @@ -0,0 +1,96 @@ +use frame_support::traits::OnRuntimeUpgrade; + +use crate::*; +use frame_support::pallet_prelude::Weight; + +use cf_chains::sol::SolAddress; +use cf_utilities::bs58_array; +use codec::{Decode, Encode}; +use scale_info::TypeInfo; + +pub mod old { + use super::*; + use cf_chains::sol::SolAddress; + + #[derive(Encode, Decode, TypeInfo)] + pub struct SolApiEnvironment { + pub vault_program: SolAddress, + pub vault_program_data_account: SolAddress, + pub token_vault_pda_account: SolAddress, + pub usdc_token_mint_pubkey: SolAddress, + pub usdc_token_vault_ata: SolAddress, + } +} + +pub struct SolApiEnvironmentMigration; + +impl OnRuntimeUpgrade for SolApiEnvironmentMigration { + fn on_runtime_upgrade() -> Weight { + log::info!("🌮 Running migration for Environment pallet: Updating SolApiEnvironment."); + let _ = pallet_cf_environment::SolanaApiEnvironment::::translate::< + old::SolApiEnvironment, + _, + >(|old_env| { + old_env.map( + |old::SolApiEnvironment { + vault_program, + vault_program_data_account, + token_vault_pda_account, + usdc_token_mint_pubkey, + usdc_token_vault_ata, + }| { + let (swap_endpoint_program, swap_endpoint_program_data_account) = + match cf_runtime_upgrade_utilities::genesis_hashes::genesis_hash::( + ) { + cf_runtime_upgrade_utilities::genesis_hashes::BERGHAIN => ( + SolAddress(bs58_array( + "BnECXbsDFYPmhxcV57dodaWtJJjtGPE8Le3LAR7qieYb", + )), + SolAddress(bs58_array( + "5mFsKrqCH5v9Q9uF5o6qrsUi1GV2myuhc23NAi5YFs4M", + )), + ), + cf_runtime_upgrade_utilities::genesis_hashes::PERSEVERANCE => ( + SolAddress(bs58_array( + "FXN1iLmQ47c962nackmzBWZxXE8BR9AXy8mu34oFdKiy", + )), + SolAddress(bs58_array( + "4hD7UM6rQtcqQWtzELvrafpmBYReVXvCpssB6qjY1Sg5", + )), + ), + cf_runtime_upgrade_utilities::genesis_hashes::SISYPHOS => ( + SolAddress(bs58_array( + "7G6TxoGDsgaZX3HaKkrKyy28tsdr7ZGmeeMbXpm8R5HZ", + )), + SolAddress(bs58_array( + "mYabVW1uMXpGqwgHUBQu4Fg6GT9EMYUzYaGYbi3zgT7", + )), + ), + _ => ( + SolAddress(bs58_array( + "35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT", + )), + SolAddress(bs58_array( + "2tmtGLQcBd11BMiE9B1tAkQXwmPNgR79Meki2Eme4Ec9", + )), + ), + }; + + cf_chains::sol::SolApiEnvironment { + vault_program, + vault_program_data_account, + token_vault_pda_account, + usdc_token_mint_pubkey, + usdc_token_vault_ata, + + // Newly inserted values + swap_endpoint_program, + swap_endpoint_program_data_account, + } + }, + ) + }); + + Weight::zero() + } +} From 81558b08607dcf7f27083d683911c939130d76fa Mon Sep 17 00:00:00 2001 From: albert Date: Wed, 16 Oct 2024 14:35:49 +0200 Subject: [PATCH 12/21] chore: address comment --- state-chain/chains/src/sol/transaction_builder.rs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/state-chain/chains/src/sol/transaction_builder.rs b/state-chain/chains/src/sol/transaction_builder.rs index d1b94395ee..9bc4b4cfcb 100644 --- a/state-chain/chains/src/sol/transaction_builder.rs +++ b/state-chain/chains/src/sol/transaction_builder.rs @@ -457,9 +457,13 @@ impl SolanaTransactionBuilder { let number_of_accounts = event_accounts.len(); let event_and_sender_vec: Vec = event_accounts .into_iter() - .flat_map(|(event_account, payee)| vec![event_account, payee]) // Both event account and payee should be writable and non-signers - .map(|address| AccountMeta::new(address.into(), false)) + .flat_map(|(event_account, payee)| { + vec![ + AccountMeta::new(event_account.into(), false), + AccountMeta::new(payee.into(), false), + ] + }) .collect(); let instructions = vec![SwapEndpointProgram::with_id(swap_endpoint_program) From 7b945788e0938abf1a8b6af32a3f7bf2ccb254b6 Mon Sep 17 00:00:00 2001 From: Albert Llimos <53186777+albert-llimos@users.noreply.github.com> Date: Wed, 16 Oct 2024 14:38:18 +0200 Subject: [PATCH 13/21] chore: bouncer solana program swaps (#5318) * chore: first iteration adding anchor * chore: small cleanup * chore: syntax improvement * chore: add comment * chore: update compute units --- bouncer/shared/contract_swap.ts | 226 +- bouncer/shared/initialize_new_chains.ts | 5 +- bouncer/shared/solana_keypair.json | 6 + bouncer/shared/utils.ts | 11 + .../v1.0.0/types/swap_endpoint.ts | 661 ++++++ .../sol-program-idls/v1.0.0/types/vault.ts | 2012 +++++++++++++++++ 6 files changed, 2876 insertions(+), 45 deletions(-) create mode 100644 bouncer/shared/solana_keypair.json create mode 100644 contract-interfaces/sol-program-idls/v1.0.0/types/swap_endpoint.ts create mode 100644 contract-interfaces/sol-program-idls/v1.0.0/types/vault.ts diff --git a/bouncer/shared/contract_swap.ts b/bouncer/shared/contract_swap.ts index fa3f70c94c..9cf80a9ad4 100644 --- a/bouncer/shared/contract_swap.ts +++ b/bouncer/shared/contract_swap.ts @@ -1,3 +1,6 @@ +import * as anchor from '@coral-xyz/anchor'; +// import NodeWallet from '@coral-xyz/anchor/dist/cjs/nodewallet'; + import { InternalAsset as Asset, executeSwap, @@ -9,6 +12,8 @@ import { Chain, } from '@chainflip/cli'; import { HDNodeWallet, Wallet, getDefaultProvider } from 'ethers'; +import { PublicKey, sendAndConfirmTransaction, Keypair } from '@solana/web3.js'; +import { getAssociatedTokenAddressSync, TOKEN_PROGRAM_ID } from '@solana/spl-token'; import { observeBalanceIncrease, getContractAddress, @@ -20,12 +25,23 @@ import { assetDecimals, stateChainAssetFromAsset, chainGasAsset, + evmChains, + getSolWhaleKeyPair, + getSolConnection, } from './utils'; import { getBalance } from './get_balance'; import { CcmDepositMetadata } from '../shared/new_swap'; import { send } from './send'; import { SwapContext, SwapStatus } from './swap_context'; +import VaultIdl from '../../contract-interfaces/sol-program-idls/v1.0.0/vault.json'; +import SwapEndpointIdl from '../../contract-interfaces/sol-program-idls/v1.0.0/swap_endpoint.json'; +import { SwapEndpoint } from '../../contract-interfaces/sol-program-idls/v1.0.0/types/swap_endpoint'; +import { Vault } from '../../contract-interfaces/sol-program-idls/v1.0.0/types/vault'; + +// Workaround because of anchor issue +const { BN } = anchor.default; + const erc20Assets: Asset[] = ['Flip', 'Usdc', 'Usdt', 'ArbUsdc']; export async function executeContractSwap( @@ -71,6 +87,118 @@ export async function executeContractSwap( return receipt; } + +// Temporary before the SDK implements this. +export async function executeSolContractSwap( + srcAsset: Asset, + destAsset: Asset, + destAddress: string, + messageMetadata?: CcmDepositMetadata, +) { + const destChain = chainFromAsset(destAsset); + + // const solanaSwapEndpointId = new PublicKey(getContractAddress('Solana', 'SWAP_ENDPOINT')); + const solanaVaultDataAccount = new PublicKey(getContractAddress('Solana', 'DATA_ACCOUNT')); + const swapEndpointDataAccount = new PublicKey( + getContractAddress('Solana', 'SWAP_ENDPOINT_DATA_ACCOUNT'), + ); + const whaleKeypair = getSolWhaleKeyPair(); + + // We should just be able to do this instead but it's not working... + // const wallet = new NodeWallet(whaleKeypair); + // const provider = new anchor.AnchorProvider(connection, wallet, { + // commitment: 'processed', + // }); + // const cfSwapEndpointProgram = new anchor.Program(SwapEndpointIdl, provider); + // const vaultProgram = new anchor.Program(VaultIdl, provider); + + // The current workaround requires having the wallet in a id.json and then set the ANCHOR_WALLET env. + // TODO: Depending on how the SDK is implemented we can remove this. + process.env.ANCHOR_WALLET = 'shared/solana_keypair.json'; + + const connection = getSolConnection(); + const cfSwapEndpointProgram = new anchor.Program(SwapEndpointIdl as SwapEndpoint); + const vaultProgram = new anchor.Program(VaultIdl as Vault); + + const newEventAccountKeypair = Keypair.generate(); + const fetchedDataAccount = await vaultProgram.account.dataAccount.fetch(solanaVaultDataAccount); + const aggKey = fetchedDataAccount.aggKey; + + const tx = + srcAsset === 'Sol' + ? await cfSwapEndpointProgram.methods + .xSwapNative({ + amount: new BN( + amountToFineAmount(defaultAssetAmounts(srcAsset), assetDecimals(srcAsset)), + ), + dstChain: Number(destChain), + dstAddress: Buffer.from(destAddress), + dstToken: Number(stateChainAssetFromAsset(destAsset)), + ccmParameters: messageMetadata + ? { + message: Buffer.from(messageMetadata.message.slice(2), 'hex'), + gasAmount: new BN(messageMetadata.gasBudget), + } + : null, + cfParameters: Buffer.from(messageMetadata?.cfParameters?.slice(2) ?? '', 'hex'), + }) + .accountsPartial({ + dataAccount: solanaVaultDataAccount, + aggKey, + from: whaleKeypair.publicKey, + eventDataAccount: newEventAccountKeypair.publicKey, + swapEndpointDataAccount, + systemProgram: anchor.web3.SystemProgram.programId, + }) + .signers([whaleKeypair, newEventAccountKeypair]) + .transaction() + : await cfSwapEndpointProgram.methods + .xSwapToken({ + amount: new BN( + amountToFineAmount(defaultAssetAmounts(srcAsset), assetDecimals(srcAsset)), + ), + dstChain: Number(destChain), + dstAddress: Buffer.from(destAddress), + dstToken: Number(stateChainAssetFromAsset(destAsset)), + ccmParameters: messageMetadata + ? { + message: Buffer.from(messageMetadata.message.slice(2), 'hex'), + gasAmount: new BN(messageMetadata.gasBudget), + } + : null, + cfParameters: Buffer.from(messageMetadata?.cfParameters?.slice(2) ?? '', 'hex'), + decimals: assetDecimals(srcAsset), + }) + .accountsPartial({ + dataAccount: solanaVaultDataAccount, + tokenVaultAssociatedTokenAccount: new PublicKey( + getContractAddress('Solana', 'TOKEN_VAULT_ATA'), + ), + from: whaleKeypair.publicKey, + fromTokenAccount: getAssociatedTokenAddressSync( + new PublicKey(getContractAddress('Solana', 'SolUsdc')), + whaleKeypair.publicKey, + false, + ), + eventDataAccount: newEventAccountKeypair.publicKey, + swapEndpointDataAccount, + tokenSupportedAccount: new PublicKey( + getContractAddress('Solana', 'SolUsdcTokenSupport'), + ), + tokenProgram: TOKEN_PROGRAM_ID, + mint: new PublicKey(getContractAddress('Solana', 'SolUsdc')), + systemProgram: anchor.web3.SystemProgram.programId, + }) + .signers([whaleKeypair, newEventAccountKeypair]) + .transaction(); + const txHash = await sendAndConfirmTransaction(connection, tx, [ + whaleKeypair, + newEventAccountKeypair, + ]); + + console.log('tx', txHash); + return txHash; +} export type ContractSwapParams = { sourceAsset: Asset; destAsset: Asset; @@ -90,31 +218,35 @@ export async function performSwapViaContract( const tag = swapTag ?? ''; const srcChain = chainFromAsset(sourceAsset); - - // Generate a new wallet for each contract swap to prevent nonce issues when running in parallel - // with other swaps via deposit channels. - const mnemonic = Wallet.createRandom().mnemonic?.phrase ?? ''; - if (mnemonic === '') { - throw new Error('Failed to create random mnemonic'); - } - const wallet = Wallet.fromPhrase(mnemonic).connect(getDefaultProvider(getEvmEndpoint(srcChain))); + let wallet; try { - // Fund new key with native asset and asset to swap. - await send(chainGasAsset(srcChain) as InternalAsset, wallet.address); - await send(sourceAsset, wallet.address); - - if (erc20Assets.includes(sourceAsset)) { - // Doing effectively infinite approvals to make sure it doesn't fail. - // eslint-disable-next-line @typescript-eslint/no-use-before-define - await approveTokenVault( - sourceAsset, - ( - BigInt(amountToFineAmount(defaultAssetAmounts(sourceAsset), assetDecimals(sourceAsset))) * - 100n - ).toString(), - wallet, - ); + if (evmChains.includes(srcChain)) { + // Generate a new wallet for each contract swap to prevent nonce issues when running in parallel + // with other swaps via deposit channels. + const mnemonic = Wallet.createRandom().mnemonic?.phrase ?? ''; + if (mnemonic === '') { + throw new Error('Failed to create random mnemonic'); + } + wallet = Wallet.fromPhrase(mnemonic).connect(getDefaultProvider(getEvmEndpoint(srcChain))); + + // Fund new key with native asset and asset to swap. + await send(chainGasAsset(srcChain) as InternalAsset, wallet.address); + await send(sourceAsset, wallet.address); + + if (erc20Assets.includes(sourceAsset)) { + // Doing effectively infinite approvals to make sure it doesn't fail. + // eslint-disable-next-line @typescript-eslint/no-use-before-define + await approveTokenVault( + sourceAsset, + ( + BigInt( + amountToFineAmount(defaultAssetAmounts(sourceAsset), assetDecimals(sourceAsset)), + ) * 100n + ).toString(), + wallet, + ); + } } swapContext?.updateStatus(swapTag, SwapStatus.ContractApproved); @@ -126,26 +258,38 @@ export async function performSwapViaContract( ); } - // To uniquely identify the contractSwap, we need to use the TX hash. This is only known - // after sending the transaction, so we send it first and observe the events afterwards. - // There are still multiple blocks of safety margin inbetween before the event is emitted - const receipt = await executeContractSwap( - sourceAsset, - destAsset, - destAddress, - wallet, - messageMetadata, - ); + let txHash: string; + let sourceAddress: string; + + // TODO: Temporary before the SDK implements this. + if (evmChains.includes(srcChain)) { + // To uniquely identify the contractSwap, we need to use the TX hash. This is only known + // after sending the transaction, so we send it first and observe the events afterwards. + // There are still multiple blocks of safety margin inbetween before the event is emitted + const receipt = await executeContractSwap( + sourceAsset, + destAsset, + destAddress, + wallet!, + messageMetadata, + ); + txHash = receipt.hash; + sourceAddress = wallet!.address.toLowerCase(); + } else { + txHash = await executeSolContractSwap( + sourceAsset, + destAsset, + destAddress, + // wallet!, + messageMetadata, + ); + sourceAddress = getSolWhaleKeyPair().publicKey.toBase58(); + } + swapContext?.updateStatus(swapTag, SwapStatus.ContractExecuted); const ccmEventEmitted = messageMetadata - ? observeCcmReceived( - sourceAsset, - destAsset, - destAddress, - messageMetadata, - wallet.address.toLowerCase(), - ) + ? observeCcmReceived(sourceAsset, destAsset, destAddress, messageMetadata, sourceAddress) : Promise.resolve(); const [newBalance] = await Promise.all([ @@ -160,7 +304,7 @@ export async function performSwapViaContract( sourceAsset, destAsset, destAddress, - txHash: receipt.hash, + txHash, }; } catch (err) { console.error('err:', err); diff --git a/bouncer/shared/initialize_new_chains.ts b/bouncer/shared/initialize_new_chains.ts index 344d9acf26..732dbd8809 100644 --- a/bouncer/shared/initialize_new_chains.ts +++ b/bouncer/shared/initialize_new_chains.ts @@ -210,10 +210,7 @@ export async function initializeSolanaPrograms(solClient: Connection, solKey: st const solUsdcMintPubkey = new PublicKey(getContractAddress('Solana', 'SolUsdc')); - const [tokenSupportedAccount] = PublicKey.findProgramAddressSync( - [Buffer.from('supported_token'), solUsdcMintPubkey.toBuffer()], - solanaVaultProgramId, - ); + const tokenSupportedAccount = new PublicKey(getContractAddress('Solana', 'SolUsdcTokenSupport')); tx.add( new TransactionInstruction({ diff --git a/bouncer/shared/solana_keypair.json b/bouncer/shared/solana_keypair.json new file mode 100644 index 0000000000..dd9f7fa84f --- /dev/null +++ b/bouncer/shared/solana_keypair.json @@ -0,0 +1,6 @@ +[ + 6, 151, 150, 20, 145, 210, 176, 113, 98, 200, 192, 80, 73, 63, 133, 232, 208, 124, 81, 213, 117, + 199, 196, 243, 219, 33, 79, 217, 157, 69, 205, 140, 247, 157, 94, 2, 111, 18, 237, 198, 68, 58, + 83, 75, 44, 221, 80, 114, 35, 57, 137, 180, 21, 215, 89, 101, 115, 231, 67, 243, 229, 179, 134, + 251 +] diff --git a/bouncer/shared/utils.ts b/bouncer/shared/utils.ts index dfe68a4eb8..f38fe2c313 100644 --- a/bouncer/shared/utils.ts +++ b/bouncer/shared/utils.ts @@ -41,6 +41,7 @@ export const brokerMutex = new Mutex(); export const snowWhiteMutex = new Mutex(); export const ccmSupportedChains = ['Ethereum', 'Arbitrum', 'Solana'] as Chain[]; +export const evmChains = ['Ethereum', 'Arbitrum'] as Chain[]; export type Asset = SDKAsset; export type Chain = SDKChain; @@ -96,10 +97,20 @@ export function getContractAddress(chain: Chain, contract: string): string { return '8inHGLHXegST3EPLcpisQe9D1hDT9r7DJjS395L3yuYf'; case 'TOKEN_VAULT_PDA': return '7B13iu7bUbBX88eVBqTZkQqrErnTMazPmGLdE5RqdyKZ'; + case 'TOKEN_VAULT_ATA': + return '9CGLwcPknpYs3atgwtjMX7RhgvBgaqK8wwCvXnmjEoL9'; case 'DATA_ACCOUNT': return 'BttvFNSRKrkHugwDP6SpnBejCKKskHowJif1HGgBtTfG'; case 'SolUsdc': return process.env.SOL_USDC_ADDRESS ?? '24PNhTaNtomHhoy3fTRaMhAFCRj4uHqhZEEoWrKDbR5p'; + case 'SolUsdcTokenSupport': + return PublicKey.findProgramAddressSync( + [ + Buffer.from('supported_token'), + new PublicKey(getContractAddress('Solana', 'SolUsdc')).toBuffer(), + ], + new PublicKey(getContractAddress('Solana', 'VAULT')), + )[0].toBase58(); case 'CFTESTER': return '8pBPaVfTAcjLeNfC187Fkvi9b1XEFhRNJ95BQXXVksmH'; case 'SWAP_ENDPOINT': diff --git a/contract-interfaces/sol-program-idls/v1.0.0/types/swap_endpoint.ts b/contract-interfaces/sol-program-idls/v1.0.0/types/swap_endpoint.ts new file mode 100644 index 0000000000..8eae9704d2 --- /dev/null +++ b/contract-interfaces/sol-program-idls/v1.0.0/types/swap_endpoint.ts @@ -0,0 +1,661 @@ +/** + * Program IDL in camelCase format in order to be used in JS/TS. + * + * Note that this is only a type helper and is not the actual IDL. The original + * IDL can be found at `target/idl/swap_endpoint.json`. + */ +export type SwapEndpoint = { + "address": "35uYgHdfZQT4kHkaaXQ6ZdCkK5LFrsk43btTLbGCRCNT", + "metadata": { + "name": "swapEndpoint", + "version": "0.1.0", + "spec": "0.1.0", + "description": "Created with Anchor" + }, + "instructions": [ + { + "name": "closeEventAccounts", + "discriminator": [ + 165, + 102, + 61, + 1, + 185, + 77, + 189, + 121 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "writable": true, + "signer": true + }, + { + "name": "swapEndpointDataAccount", + "writable": true + } + ], + "args": [] + }, + { + "name": "initialize", + "discriminator": [ + 175, + 175, + 109, + 31, + 13, + 152, + 155, + 237 + ], + "accounts": [ + { + "name": "swapEndpointDataAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 100, + 97, + 116, + 97 + ] + } + ] + } + }, + { + "name": "signer", + "writable": true, + "signer": true + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [] + }, + { + "name": "xSwapNative", + "discriminator": [ + 163, + 38, + 92, + 226, + 243, + 105, + 141, + 196 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "writable": true + }, + { + "name": "from", + "writable": true, + "signer": true + }, + { + "name": "eventDataAccount", + "writable": true, + "signer": true + }, + { + "name": "swapEndpointDataAccount", + "writable": true + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "swapNativeParams", + "type": { + "defined": { + "name": "swapNativeParams" + } + } + } + ] + }, + { + "name": "xSwapToken", + "discriminator": [ + 69, + 50, + 252, + 99, + 229, + 83, + 119, + 235 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "tokenVaultAssociatedTokenAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "data_account.token_vault_pda", + "account": "dataAccount" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "from", + "writable": true, + "signer": true + }, + { + "name": "fromTokenAccount", + "writable": true + }, + { + "name": "eventDataAccount", + "writable": true, + "signer": true + }, + { + "name": "swapEndpointDataAccount", + "writable": true + }, + { + "name": "tokenSupportedAccount" + }, + { + "name": "tokenProgram", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + }, + { + "name": "mint" + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "swapTokenParams", + "type": { + "defined": { + "name": "swapTokenParams" + } + } + } + ] + } + ], + "accounts": [ + { + "name": "dataAccount", + "discriminator": [ + 85, + 240, + 182, + 158, + 76, + 7, + 18, + 233 + ] + }, + { + "name": "supportedToken", + "discriminator": [ + 56, + 162, + 96, + 99, + 193, + 245, + 204, + 108 + ] + }, + { + "name": "swapEndpointDataAccount", + "discriminator": [ + 79, + 152, + 191, + 225, + 128, + 108, + 11, + 139 + ] + }, + { + "name": "swapEvent", + "discriminator": [ + 150, + 251, + 114, + 94, + 200, + 113, + 248, + 70 + ] + } + ], + "events": [ + { + "name": "cantDeserializeEventAccount", + "discriminator": [ + 248, + 26, + 198, + 175, + 8, + 58, + 229, + 137 + ] + }, + { + "name": "eventAccountNotTracked", + "discriminator": [ + 202, + 29, + 253, + 107, + 20, + 196, + 36, + 210 + ] + } + ], + "errors": [ + { + "code": 6000, + "name": "mathOverflow", + "msg": "Overflow in arithmetic operation" + }, + { + "code": 6001, + "name": "mathUnderflow", + "msg": "Underflow in arithmetic operation" + } + ], + "types": [ + { + "name": "cantDeserializeEventAccount", + "type": { + "kind": "struct", + "fields": [ + { + "name": "eventAccount", + "type": "pubkey" + }, + { + "name": "payee", + "type": "pubkey" + } + ] + } + }, + { + "name": "ccmParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "message", + "type": "bytes" + }, + { + "name": "gasAmount", + "type": "u64" + } + ] + } + }, + { + "name": "dataAccount", + "docs": [ + "* ****************************************************************************\n * *************************** IMPORTANT NOTE *********************************\n * ****************************************************************************\n * If the vault is upgraded and the DataAccount struct is modified we need to\n * check the compatibility and ensure there is a proper migration process, given\n * that the Vault bytecode is the only thing being upgraded, not the data account.\n *\n * The easiest approach on upgrade is keeping the DataAccount unchanged and use\n * a new account struct for any new data that is required.\n *\n * DO NOT MODIFY THIS WITHOUT UNDERSTANDING THE CONSEQUENCES!\n * ****************************************************************************\n * ****************************************************************************" + ], + "type": { + "kind": "struct", + "fields": [ + { + "name": "aggKey", + "type": "pubkey" + }, + { + "name": "govKey", + "type": "pubkey" + }, + { + "name": "tokenVaultPda", + "type": "pubkey" + }, + { + "name": "tokenVaultBump", + "type": "u8" + }, + { + "name": "upgradeSignerPda", + "type": "pubkey" + }, + { + "name": "upgradeSignerPdaBump", + "type": "u8" + }, + { + "name": "suspended", + "type": "bool" + }, + { + "name": "suspendedLegacySwaps", + "type": "bool" + }, + { + "name": "suspendedEventSwaps", + "type": "bool" + }, + { + "name": "minNativeSwapAmount", + "type": "u64" + }, + { + "name": "maxDstAddressLen", + "type": "u16" + }, + { + "name": "maxCcmMessageLen", + "type": "u32" + }, + { + "name": "maxCfParametersLen", + "type": "u32" + }, + { + "name": "maxEventAccounts", + "type": "u32" + } + ] + } + }, + { + "name": "eventAccountNotTracked", + "type": { + "kind": "struct", + "fields": [ + { + "name": "eventAccount", + "type": "pubkey" + }, + { + "name": "payee", + "type": "pubkey" + } + ] + } + }, + { + "name": "supportedToken", + "type": { + "kind": "struct", + "fields": [ + { + "name": "tokenMintPubkey", + "type": "pubkey" + }, + { + "name": "minSwapAmount", + "type": "u64" + } + ] + } + }, + { + "name": "swapEndpointDataAccount", + "type": { + "kind": "struct", + "fields": [ + { + "name": "historicalNumberEventAccounts", + "type": "u128" + }, + { + "name": "openEventAccounts", + "type": { + "vec": "pubkey" + } + } + ] + } + }, + { + "name": "swapEvent", + "type": { + "kind": "struct", + "fields": [ + { + "name": "sender", + "type": "pubkey" + }, + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "amount", + "type": "u64" + }, + { + "name": "srcToken", + "type": { + "option": "pubkey" + } + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + } + ] + } + }, + { + "name": "swapNativeParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + } + ] + } + }, + { + "name": "swapTokenParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + }, + { + "name": "decimals", + "type": "u8" + } + ] + } + } + ] +}; diff --git a/contract-interfaces/sol-program-idls/v1.0.0/types/vault.ts b/contract-interfaces/sol-program-idls/v1.0.0/types/vault.ts new file mode 100644 index 0000000000..1bca1885c4 --- /dev/null +++ b/contract-interfaces/sol-program-idls/v1.0.0/types/vault.ts @@ -0,0 +1,2012 @@ +/** + * Program IDL in camelCase format in order to be used in JS/TS. + * + * Note that this is only a type helper and is not the actual IDL. The original + * IDL can be found at `target/idl/vault.json`. + */ +export type Vault = { + "address": "8inHGLHXegST3EPLcpisQe9D1hDT9r7DJjS395L3yuYf", + "metadata": { + "name": "vault", + "version": "0.1.0", + "spec": "0.1.0", + "description": "Created with Anchor" + }, + "instructions": [ + { + "name": "disableTokenSupport", + "discriminator": [ + 72, + 4, + 35, + 144, + 194, + 49, + 71, + 64 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "govKey", + "writable": true, + "signer": true + }, + { + "name": "tokenSupportedAccount", + "writable": true + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [] + }, + { + "name": "enableTokenSupport", + "discriminator": [ + 125, + 160, + 180, + 50, + 26, + 27, + 112, + 153 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "govKey", + "writable": true, + "signer": true + }, + { + "name": "tokenSupportedAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 115, + 117, + 112, + 112, + 111, + 114, + 116, + 101, + 100, + 95, + 116, + 111, + 107, + 101, + 110 + ] + }, + { + "kind": "account", + "path": "mint" + } + ] + } + }, + { + "name": "mint" + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "minSwapAmount", + "type": "u64" + } + ] + }, + { + "name": "executeCcmNativeCall", + "discriminator": [ + 125, + 5, + 11, + 227, + 128, + 66, + 224, + 178 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "signer": true + }, + { + "name": "receiverNative", + "writable": true + }, + { + "name": "cfReceiver", + "docs": [ + "the aggregate key signature." + ] + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + }, + { + "name": "instructionSysvar", + "address": "Sysvar1nstructions1111111111111111111111111" + } + ], + "args": [ + { + "name": "sourceChain", + "type": "u32" + }, + { + "name": "sourceAddress", + "type": "bytes" + }, + { + "name": "message", + "type": "bytes" + }, + { + "name": "amount", + "type": "u64" + } + ] + }, + { + "name": "executeCcmTokenCall", + "discriminator": [ + 108, + 184, + 162, + 123, + 159, + 222, + 170, + 35 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "signer": true + }, + { + "name": "receiverTokenAccount", + "writable": true + }, + { + "name": "cfReceiver", + "docs": [ + "without passing the aggregate key signature." + ] + }, + { + "name": "tokenProgram", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + }, + { + "name": "mint" + }, + { + "name": "instructionSysvar", + "address": "Sysvar1nstructions1111111111111111111111111" + } + ], + "args": [ + { + "name": "sourceChain", + "type": "u32" + }, + { + "name": "sourceAddress", + "type": "bytes" + }, + { + "name": "message", + "type": "bytes" + }, + { + "name": "amount", + "type": "u64" + } + ] + }, + { + "name": "fetchNative", + "discriminator": [ + 142, + 36, + 101, + 143, + 108, + 89, + 41, + 140 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "writable": true, + "signer": true + }, + { + "name": "depositChannelPda", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 99, + 104, + 97, + 110, + 110, + 101, + 108 + ] + }, + { + "kind": "arg", + "path": "seed" + } + ] + } + }, + { + "name": "depositChannelHistoricalFetch", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 104, + 105, + 115, + 116, + 95, + 102, + 101, + 116, + 99, + 104 + ] + }, + { + "kind": "account", + "path": "depositChannelPda" + } + ] + } + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "seed", + "type": "bytes" + }, + { + "name": "bump", + "type": "u8" + } + ] + }, + { + "name": "fetchTokens", + "discriminator": [ + 73, + 71, + 16, + 100, + 44, + 176, + 198, + 70 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "writable": true, + "signer": true + }, + { + "name": "depositChannelPda", + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 99, + 104, + 97, + 110, + 110, + 101, + 108 + ] + }, + { + "kind": "arg", + "path": "seed" + } + ] + } + }, + { + "name": "depositChannelAssociatedTokenAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "depositChannelPda" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "tokenVaultAssociatedTokenAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "data_account.token_vault_pda", + "account": "dataAccount" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "mint" + }, + { + "name": "tokenProgram", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + }, + { + "name": "depositChannelHistoricalFetch", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 104, + 105, + 115, + 116, + 95, + 102, + 101, + 116, + 99, + 104 + ] + }, + { + "kind": "account", + "path": "depositChannelAssociatedTokenAccount" + } + ] + } + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "seed", + "type": "bytes" + }, + { + "name": "bump", + "type": "u8" + }, + { + "name": "decimals", + "type": "u8" + } + ] + }, + { + "name": "initialize", + "discriminator": [ + 175, + 175, + 109, + 31, + 13, + 152, + 155, + 237 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 100, + 97, + 116, + 97 + ] + } + ] + } + }, + { + "name": "initializer", + "writable": true, + "signer": true, + "address": "HfasueN6RNPjSM6rKGH5dga6kS2oUF8siGH3m4MXPURp" + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "newAggKey", + "type": "pubkey" + }, + { + "name": "newGovKey", + "type": "pubkey" + }, + { + "name": "expectedTokenVaultPda", + "type": "pubkey" + }, + { + "name": "expectedTokenVaultPdaBump", + "type": "u8" + }, + { + "name": "expectedUpgradeSignerPda", + "type": "pubkey" + }, + { + "name": "expectedUpgradeSignerPdaBump", + "type": "u8" + }, + { + "name": "suspendedVault", + "type": "bool" + }, + { + "name": "suspendedLegacySwaps", + "type": "bool" + }, + { + "name": "suspendedEventSwaps", + "type": "bool" + }, + { + "name": "minNativeSwapAmount", + "type": "u64" + }, + { + "name": "maxDstAddressLen", + "type": "u16" + }, + { + "name": "maxCcmMessageLen", + "type": "u32" + }, + { + "name": "maxCfParametersLen", + "type": "u32" + }, + { + "name": "maxEventAccounts", + "type": "u32" + } + ] + }, + { + "name": "rotateAggKey", + "discriminator": [ + 78, + 81, + 143, + 171, + 221, + 165, + 214, + 139 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "aggKey", + "writable": true, + "signer": true + }, + { + "name": "newAggKey", + "writable": true + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + } + ], + "args": [ + { + "name": "skipTransferFunds", + "type": "bool" + } + ] + }, + { + "name": "setGovKeyWithAggKey", + "discriminator": [ + 66, + 64, + 58, + 40, + 15, + 75, + 215, + 162 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "aggKey", + "signer": true + } + ], + "args": [ + { + "name": "newGovKey", + "type": "pubkey" + } + ] + }, + { + "name": "setGovKeyWithGovKey", + "discriminator": [ + 251, + 142, + 231, + 255, + 111, + 143, + 165, + 106 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "govKey", + "signer": true + } + ], + "args": [ + { + "name": "newGovKey", + "type": "pubkey" + } + ] + }, + { + "name": "setProgramSwapsParameters", + "discriminator": [ + 129, + 254, + 31, + 151, + 111, + 149, + 135, + 77 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "govKey", + "signer": true + } + ], + "args": [ + { + "name": "minNativeSwapAmount", + "type": "u64" + }, + { + "name": "maxDstAddressLen", + "type": "u16" + }, + { + "name": "maxCcmMessageLen", + "type": "u32" + }, + { + "name": "maxCfParametersLen", + "type": "u32" + }, + { + "name": "maxEventAccounts", + "type": "u32" + } + ] + }, + { + "name": "setSuspendedState", + "discriminator": [ + 145, + 13, + 20, + 161, + 30, + 62, + 226, + 32 + ], + "accounts": [ + { + "name": "dataAccount", + "writable": true + }, + { + "name": "govKey", + "signer": true + } + ], + "args": [ + { + "name": "suspend", + "type": "bool" + }, + { + "name": "suspendLegacySwaps", + "type": "bool" + }, + { + "name": "suspendEventSwaps", + "type": "bool" + } + ] + }, + { + "name": "transferTokens", + "discriminator": [ + 54, + 180, + 238, + 175, + 74, + 85, + 126, + 188 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "signer": true + }, + { + "name": "tokenVaultPda" + }, + { + "name": "tokenVaultAssociatedTokenAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "data_account.token_vault_pda", + "account": "dataAccount" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "toTokenAccount", + "writable": true + }, + { + "name": "mint" + }, + { + "name": "tokenProgram", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + } + ], + "args": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "decimals", + "type": "u8" + } + ] + }, + { + "name": "transferVaultUpgradeAuthority", + "discriminator": [ + 114, + 247, + 72, + 110, + 145, + 65, + 236, + 153 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "signer": true + }, + { + "name": "programDataAddress", + "writable": true + }, + { + "name": "programAddress" + }, + { + "name": "newAuthority" + }, + { + "name": "signerPda", + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 115, + 105, + 103, + 110, + 101, + 114 + ] + } + ] + } + }, + { + "name": "bpfLoaderUpgradeable", + "address": "BPFLoaderUpgradeab1e11111111111111111111111" + } + ], + "args": [] + }, + { + "name": "upgradeProgram", + "docs": [ + "* ****************************************************************************\n * *************************** IMPORTANT NOTE *********************************\n * ****************************************************************************\n * The signer_pda is the upgrade authority for the vault program. Changing this\n * logic should be done with caution and understanding the consequences.\n *\n * DO NOT MODIFY THIS WITHOUT UNDERSTANDING THE CONSEQUENCES!\n * ****************************************************************************\n * ****************************************************************************" + ], + "discriminator": [ + 223, + 236, + 39, + 89, + 111, + 204, + 114, + 37 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "govKey", + "signer": true + }, + { + "name": "programDataAddress", + "writable": true + }, + { + "name": "programAddress", + "writable": true + }, + { + "name": "bufferAddress", + "writable": true + }, + { + "name": "spillAddress", + "writable": true + }, + { + "name": "sysvarRent", + "address": "SysvarRent111111111111111111111111111111111" + }, + { + "name": "sysvarClock", + "address": "SysvarC1ock11111111111111111111111111111111" + }, + { + "name": "signerPda", + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 115, + 105, + 103, + 110, + 101, + 114 + ] + } + ] + } + }, + { + "name": "bpfLoaderUpgradeable", + "address": "BPFLoaderUpgradeab1e11111111111111111111111" + } + ], + "args": [] + }, + { + "name": "xSwapNativeLegacy", + "discriminator": [ + 97, + 21, + 117, + 255, + 21, + 6, + 232, + 176 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "aggKey", + "writable": true + }, + { + "name": "from", + "writable": true, + "signer": true + }, + { + "name": "systemProgram", + "address": "11111111111111111111111111111111" + }, + { + "name": "eventAuthority", + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 95, + 95, + 101, + 118, + 101, + 110, + 116, + 95, + 97, + 117, + 116, + 104, + 111, + 114, + 105, + 116, + 121 + ] + } + ] + } + }, + { + "name": "program" + } + ], + "args": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + } + ] + }, + { + "name": "xSwapTokenLegacy", + "discriminator": [ + 248, + 32, + 195, + 34, + 38, + 180, + 117, + 127 + ], + "accounts": [ + { + "name": "dataAccount" + }, + { + "name": "tokenVaultAssociatedTokenAccount", + "writable": true, + "pda": { + "seeds": [ + { + "kind": "account", + "path": "data_account.token_vault_pda", + "account": "dataAccount" + }, + { + "kind": "const", + "value": [ + 6, + 221, + 246, + 225, + 215, + 101, + 161, + 147, + 217, + 203, + 225, + 70, + 206, + 235, + 121, + 172, + 28, + 180, + 133, + 237, + 95, + 91, + 55, + 145, + 58, + 140, + 245, + 133, + 126, + 255, + 0, + 169 + ] + }, + { + "kind": "account", + "path": "mint" + } + ], + "program": { + "kind": "const", + "value": [ + 140, + 151, + 37, + 143, + 78, + 36, + 137, + 241, + 187, + 61, + 16, + 41, + 20, + 142, + 13, + 131, + 11, + 90, + 19, + 153, + 218, + 255, + 16, + 132, + 4, + 142, + 123, + 216, + 219, + 233, + 248, + 89 + ] + } + } + }, + { + "name": "from", + "signer": true + }, + { + "name": "fromTokenAccount", + "writable": true + }, + { + "name": "tokenSupportedAccount" + }, + { + "name": "tokenProgram", + "address": "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA" + }, + { + "name": "mint" + }, + { + "name": "eventAuthority", + "pda": { + "seeds": [ + { + "kind": "const", + "value": [ + 95, + 95, + 101, + 118, + 101, + 110, + 116, + 95, + 97, + 117, + 116, + 104, + 111, + 114, + 105, + 116, + 121 + ] + } + ] + } + }, + { + "name": "program" + } + ], + "args": [ + { + "name": "amount", + "type": "u64" + }, + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + }, + { + "name": "decimals", + "type": "u8" + } + ] + } + ], + "accounts": [ + { + "name": "dataAccount", + "discriminator": [ + 85, + 240, + 182, + 158, + 76, + 7, + 18, + 233 + ] + }, + { + "name": "depositChannelHistoricalFetch", + "discriminator": [ + 188, + 68, + 197, + 38, + 48, + 192, + 81, + 100 + ] + }, + { + "name": "supportedToken", + "discriminator": [ + 56, + 162, + 96, + 99, + 193, + 245, + 204, + 108 + ] + } + ], + "events": [ + { + "name": "aggKeyRotated", + "discriminator": [ + 133, + 39, + 145, + 216, + 63, + 154, + 134, + 245 + ] + }, + { + "name": "govKeyRotated", + "discriminator": [ + 71, + 44, + 22, + 197, + 63, + 250, + 150, + 83 + ] + }, + { + "name": "govKeySetByAggKey", + "discriminator": [ + 135, + 202, + 24, + 202, + 91, + 182, + 141, + 24 + ] + }, + { + "name": "govKeySetByGovKey", + "discriminator": [ + 198, + 58, + 153, + 108, + 67, + 162, + 174, + 167 + ] + }, + { + "name": "programSwapsParametersSet", + "discriminator": [ + 173, + 82, + 238, + 223, + 74, + 121, + 243, + 142 + ] + }, + { + "name": "suspended", + "discriminator": [ + 220, + 179, + 163, + 2, + 249, + 252, + 157, + 102 + ] + }, + { + "name": "swapEvent", + "discriminator": [ + 64, + 198, + 205, + 232, + 38, + 8, + 113, + 226 + ] + }, + { + "name": "tokenSupportDisabled", + "discriminator": [ + 35, + 252, + 131, + 176, + 50, + 103, + 135, + 13 + ] + }, + { + "name": "tokenSupportEnabled", + "discriminator": [ + 11, + 203, + 178, + 141, + 170, + 213, + 67, + 234 + ] + } + ], + "errors": [ + { + "code": 6000, + "name": "invalidTokenVaultAccount", + "msg": "Token Vault pda account does not match the expected program id" + }, + { + "code": 6001, + "name": "suspended", + "msg": "Vault program is suspended" + }, + { + "code": 6002, + "name": "invalidRemainingAccount", + "msg": "An invalid account is provided as a remaining account" + }, + { + "code": 6003, + "name": "invalidRemainingAccountSigner", + "msg": "A remaining account can't be a signer" + }, + { + "code": 6004, + "name": "unchangedSuspendedState", + "msg": "Suspended state unchanged" + }, + { + "code": 6005, + "name": "invalidSwapParameters", + "msg": "Invalid swap parameters" + }, + { + "code": 6006, + "name": "invalidTokenVaultBump", + "msg": "Invalid token vault bump" + }, + { + "code": 6007, + "name": "invalidUpgradeSignerPda", + "msg": "Invalid upgrade signer pda" + }, + { + "code": 6008, + "name": "invalidUpgradeSignerPdaBump", + "msg": "Invalid upgrade signer bump" + }, + { + "code": 6009, + "name": "suspendedIxSwaps", + "msg": "Instruction swaps are suspended" + }, + { + "code": 6010, + "name": "suspendedEventSwaps", + "msg": "Event swaps are suspended" + }, + { + "code": 6011, + "name": "nativeAmountBelowMinimumSwapAmount", + "msg": "Native amount below minimum swap amount" + }, + { + "code": 6012, + "name": "tokenAmountBelowMinimumSwapAmount", + "msg": "Token amount below minimum swap amount" + }, + { + "code": 6013, + "name": "destinationAddressExceedsMaxLength", + "msg": "Destination address exceeds max length" + }, + { + "code": 6014, + "name": "cfParametersExceedsMaxLength", + "msg": "Cf Parameters exceeds max length" + }, + { + "code": 6015, + "name": "ccmMessageExceedsMaxLength", + "msg": "Ccm message exceeds max length" + } + ], + "types": [ + { + "name": "aggKeyRotated", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldAggKey", + "type": "pubkey" + }, + { + "name": "newAggKey", + "type": "pubkey" + } + ] + } + }, + { + "name": "ccmParams", + "type": { + "kind": "struct", + "fields": [ + { + "name": "message", + "type": "bytes" + }, + { + "name": "gasAmount", + "type": "u64" + } + ] + } + }, + { + "name": "dataAccount", + "docs": [ + "* ****************************************************************************\n * *************************** IMPORTANT NOTE *********************************\n * ****************************************************************************\n * If the vault is upgraded and the DataAccount struct is modified we need to\n * check the compatibility and ensure there is a proper migration process, given\n * that the Vault bytecode is the only thing being upgraded, not the data account.\n *\n * The easiest approach on upgrade is keeping the DataAccount unchanged and use\n * a new account struct for any new data that is required.\n *\n * DO NOT MODIFY THIS WITHOUT UNDERSTANDING THE CONSEQUENCES!\n * ****************************************************************************\n * ****************************************************************************" + ], + "type": { + "kind": "struct", + "fields": [ + { + "name": "aggKey", + "type": "pubkey" + }, + { + "name": "govKey", + "type": "pubkey" + }, + { + "name": "tokenVaultPda", + "type": "pubkey" + }, + { + "name": "tokenVaultBump", + "type": "u8" + }, + { + "name": "upgradeSignerPda", + "type": "pubkey" + }, + { + "name": "upgradeSignerPdaBump", + "type": "u8" + }, + { + "name": "suspended", + "type": "bool" + }, + { + "name": "suspendedLegacySwaps", + "type": "bool" + }, + { + "name": "suspendedEventSwaps", + "type": "bool" + }, + { + "name": "minNativeSwapAmount", + "type": "u64" + }, + { + "name": "maxDstAddressLen", + "type": "u16" + }, + { + "name": "maxCcmMessageLen", + "type": "u32" + }, + { + "name": "maxCfParametersLen", + "type": "u32" + }, + { + "name": "maxEventAccounts", + "type": "u32" + } + ] + } + }, + { + "name": "depositChannelHistoricalFetch", + "type": { + "kind": "struct", + "fields": [ + { + "name": "amount", + "type": "u128" + } + ] + } + }, + { + "name": "govKeyRotated", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldGovKey", + "type": "pubkey" + }, + { + "name": "newGovKey", + "type": "pubkey" + } + ] + } + }, + { + "name": "govKeySetByAggKey", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldGovKey", + "type": "pubkey" + }, + { + "name": "newGovKey", + "type": "pubkey" + } + ] + } + }, + { + "name": "govKeySetByGovKey", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldGovKey", + "type": "pubkey" + }, + { + "name": "newGovKey", + "type": "pubkey" + } + ] + } + }, + { + "name": "programSwapsParametersSet", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldMinSwapAmount", + "type": "u64" + }, + { + "name": "oldMaxDstAddressLen", + "type": "u16" + }, + { + "name": "oldMaxCcmMessageLen", + "type": "u32" + }, + { + "name": "oldMaxCfParametersLen", + "type": "u32" + }, + { + "name": "oldMaxEventAccounts", + "type": "u32" + }, + { + "name": "newMinSwapAmount", + "type": "u64" + }, + { + "name": "newMaxDstAddressLen", + "type": "u16" + }, + { + "name": "newMaxCcmMessageLen", + "type": "u32" + }, + { + "name": "newMaxCfParametersLen", + "type": "u32" + }, + { + "name": "newMaxEventAccounts", + "type": "u32" + } + ] + } + }, + { + "name": "supportedToken", + "type": { + "kind": "struct", + "fields": [ + { + "name": "tokenMintPubkey", + "type": "pubkey" + }, + { + "name": "minSwapAmount", + "type": "u64" + } + ] + } + }, + { + "name": "suspended", + "type": { + "kind": "struct", + "fields": [ + { + "name": "suspended", + "type": "bool" + }, + { + "name": "suspendedLegacySwaps", + "type": "bool" + }, + { + "name": "suspendedEventSwaps", + "type": "bool" + } + ] + } + }, + { + "name": "swapEvent", + "type": { + "kind": "struct", + "fields": [ + { + "name": "dstChain", + "type": "u32" + }, + { + "name": "dstAddress", + "type": "bytes" + }, + { + "name": "dstToken", + "type": "u32" + }, + { + "name": "srcToken", + "type": { + "option": "pubkey" + } + }, + { + "name": "amount", + "type": "u64" + }, + { + "name": "sender", + "type": "pubkey" + }, + { + "name": "ccmParameters", + "type": { + "option": { + "defined": { + "name": "ccmParams" + } + } + } + }, + { + "name": "cfParameters", + "type": "bytes" + } + ] + } + }, + { + "name": "tokenSupportDisabled", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldTokenSupported", + "type": { + "defined": { + "name": "supportedToken" + } + } + } + ] + } + }, + { + "name": "tokenSupportEnabled", + "type": { + "kind": "struct", + "fields": [ + { + "name": "oldTokenSupported", + "type": { + "defined": { + "name": "supportedToken" + } + } + }, + { + "name": "newTokenSupported", + "type": { + "defined": { + "name": "supportedToken" + } + } + } + ] + } + } + ] +}; From a6e2c9ad94c9cf36960890b476c9492a5abb94db Mon Sep 17 00:00:00 2001 From: Roy Yang Date: Tue, 29 Oct 2024 11:37:28 +1300 Subject: [PATCH 14/21] Moved Environment pallet's migration from Runtime into Pallet --- Cargo.lock | 1 + .../pallets/cf-broadcast/src/migrations.rs | 1 + state-chain/pallets/cf-environment/Cargo.toml | 2 ++ .../pallets/cf-environment/src/migrations.rs | 14 +++++++++++++- .../src/migrations/sol_api_environment.rs | 19 +++++++------------ state-chain/runtime/src/lib.rs | 7 +------ state-chain/runtime/src/migrations.rs | 1 - 7 files changed, 25 insertions(+), 20 deletions(-) rename state-chain/{runtime => pallets/cf-environment}/src/migrations/sol_api_environment.rs (86%) diff --git a/Cargo.lock b/Cargo.lock index ca2caab4c4..d872c46f72 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -7649,6 +7649,7 @@ dependencies = [ "sp-io 23.0.0", "sp-runtime 24.0.0", "sp-std 8.0.0", + "utilities", ] [[package]] diff --git a/state-chain/pallets/cf-broadcast/src/migrations.rs b/state-chain/pallets/cf-broadcast/src/migrations.rs index 6942d64c78..5e0b232198 100644 --- a/state-chain/pallets/cf-broadcast/src/migrations.rs +++ b/state-chain/pallets/cf-broadcast/src/migrations.rs @@ -7,5 +7,6 @@ mod migrate_timeouts; pub type PalletMigration = ( VersionedMigration, initialize_broadcast_timeout_storage::Migration, 6, 7>, VersionedMigration, migrate_timeouts::Migration, 7, 8>, + // Version 8 -> 9 is done in the Runtime: SerializeSolanaBroadcastMigration PlaceholderMigration, 9>, ); diff --git a/state-chain/pallets/cf-environment/Cargo.toml b/state-chain/pallets/cf-environment/Cargo.toml index 2f4b1bbf37..2a867c230b 100644 --- a/state-chain/pallets/cf-environment/Cargo.toml +++ b/state-chain/pallets/cf-environment/Cargo.toml @@ -26,6 +26,7 @@ serde = { default_features = false, version = '1.0.195', features = [ hex-literal = { version = '0.4.1', default-features = false } log = { version = '0.4.16', default-features = false } cf-runtime-upgrade-utilities = { path = '../../runtime-upgrade-utilities', default-features = false } +cf-utilities = { package = "utilities", path = "../../../utilities", default-features = false } # Parity deps codec = { package = 'parity-scale-codec', version = '3.6.1', default-features = false, features = [ @@ -61,6 +62,7 @@ std = [ 'sp-std/std', 'log/std', 'cf-runtime-upgrade-utilities/std', + 'cf-utilities/std', ] runtime-benchmarks = [ 'cf-chains/runtime-benchmarks', diff --git a/state-chain/pallets/cf-environment/src/migrations.rs b/state-chain/pallets/cf-environment/src/migrations.rs index 15e032cf04..5b40af9443 100644 --- a/state-chain/pallets/cf-environment/src/migrations.rs +++ b/state-chain/pallets/cf-environment/src/migrations.rs @@ -8,6 +8,9 @@ use frame_support::{pallet_prelude::DispatchError, sp_runtime}; #[cfg(feature = "try-runtime")] use sp_std::vec::Vec; +mod sol_api_environment; +pub use sol_api_environment::SolApiEnvironmentMigration; + pub struct VersionUpdate(sp_std::marker::PhantomData); impl OnRuntimeUpgrade for VersionUpdate { @@ -32,7 +35,16 @@ impl OnRuntimeUpgrade for VersionUpdate { } } -pub type PalletMigration = PlaceholderMigration, 13>; +// Migration for Updating Solana's Api Environments. +pub type PalletMigration = ( + cf_runtime_upgrade_utilities::VersionedMigration< + Pallet, + SolApiEnvironmentMigration, + 12, + 13, + >, + PlaceholderMigration, 13>, +); #[cfg(test)] mod tests { diff --git a/state-chain/runtime/src/migrations/sol_api_environment.rs b/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs similarity index 86% rename from state-chain/runtime/src/migrations/sol_api_environment.rs rename to state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs index 649b54682e..3249e85e9e 100644 --- a/state-chain/runtime/src/migrations/sol_api_environment.rs +++ b/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs @@ -1,9 +1,8 @@ -use frame_support::traits::OnRuntimeUpgrade; - use crate::*; -use frame_support::pallet_prelude::Weight; -use cf_chains::sol::SolAddress; +use frame_support::{pallet_prelude::Weight, traits::OnRuntimeUpgrade}; + +use cf_chains::{evm::H256, sol::SolAddress}; use cf_utilities::bs58_array; use codec::{Decode, Encode}; use scale_info::TypeInfo; @@ -22,15 +21,12 @@ pub mod old { } } -pub struct SolApiEnvironmentMigration; +pub struct SolApiEnvironmentMigration(PhantomData); -impl OnRuntimeUpgrade for SolApiEnvironmentMigration { +impl> OnRuntimeUpgrade for SolApiEnvironmentMigration { fn on_runtime_upgrade() -> Weight { log::info!("🌮 Running migration for Environment pallet: Updating SolApiEnvironment."); - let _ = pallet_cf_environment::SolanaApiEnvironment::::translate::< - old::SolApiEnvironment, - _, - >(|old_env| { + let _ = SolanaApiEnvironment::::translate::(|old_env| { old_env.map( |old::SolApiEnvironment { vault_program, @@ -40,8 +36,7 @@ impl OnRuntimeUpgrade for SolApiEnvironmentMigration { usdc_token_vault_ata, }| { let (swap_endpoint_program, swap_endpoint_program_data_account) = - match cf_runtime_upgrade_utilities::genesis_hashes::genesis_hash::( - ) { + match cf_runtime_upgrade_utilities::genesis_hashes::genesis_hash::() { cf_runtime_upgrade_utilities::genesis_hashes::BERGHAIN => ( SolAddress(bs58_array( "BnECXbsDFYPmhxcV57dodaWtJJjtGPE8Le3LAR7qieYb", diff --git a/state-chain/runtime/src/lib.rs b/state-chain/runtime/src/lib.rs index 3ab8ebbf9e..02a2d5e93d 100644 --- a/state-chain/runtime/src/lib.rs +++ b/state-chain/runtime/src/lib.rs @@ -19,10 +19,7 @@ use crate::{ }, Offence, }, - migrations::{ - serialize_solana_broadcast::{NoopUpgrade, SerializeSolanaBroadcastMigration}, - sol_api_environment::SolApiEnvironmentMigration, - }, + migrations::serialize_solana_broadcast::{NoopUpgrade, SerializeSolanaBroadcastMigration}, monitoring_apis::{ AuthoritiesInfo, BtcUtxos, EpochState, ExternalChainsBlockHeight, FeeImbalance, FlipSupply, LastRuntimeUpgradeInfo, MonitoringData, OpenDepositChannels, PendingBroadcasts, @@ -1267,8 +1264,6 @@ type MigrationsForV1_7 = ( VersionedMigration, NoopUpgrade, 8, 9>, VersionedMigration, NoopUpgrade, 8, 9>, VersionedMigration, NoopUpgrade, 8, 9>, - // Migration for Updating Solana's Api Environments. - VersionedMigration, SolApiEnvironmentMigration, 12, 13>, ); #[cfg(feature = "runtime-benchmarks")] diff --git a/state-chain/runtime/src/migrations.rs b/state-chain/runtime/src/migrations.rs index 09de81f1fa..03fc5f0beb 100644 --- a/state-chain/runtime/src/migrations.rs +++ b/state-chain/runtime/src/migrations.rs @@ -3,4 +3,3 @@ pub mod housekeeping; pub mod reap_old_accounts; pub mod serialize_solana_broadcast; -pub mod sol_api_environment; From 7136f6dfc77dee80184ff15a8346fb0a46b7813e Mon Sep 17 00:00:00 2001 From: Roy Yang Date: Tue, 29 Oct 2024 15:37:20 +1300 Subject: [PATCH 15/21] Fixed bouncer --- bouncer/shared/contract_swap.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bouncer/shared/contract_swap.ts b/bouncer/shared/contract_swap.ts index 9cf80a9ad4..3f647b1696 100644 --- a/bouncer/shared/contract_swap.ts +++ b/bouncer/shared/contract_swap.ts @@ -40,7 +40,7 @@ import { SwapEndpoint } from '../../contract-interfaces/sol-program-idls/v1.0.0/ import { Vault } from '../../contract-interfaces/sol-program-idls/v1.0.0/types/vault'; // Workaround because of anchor issue -const { BN } = anchor.default; +const { BN } = anchor; const erc20Assets: Asset[] = ['Flip', 'Usdc', 'Usdt', 'ArbUsdc']; From f8d38212164a99b6a2930baabb7f41c882407810 Mon Sep 17 00:00:00 2001 From: Roy Yang Date: Tue, 29 Oct 2024 18:07:16 +1300 Subject: [PATCH 16/21] Corrected placeholder migration version for the broadcaster pallet --- state-chain/pallets/cf-broadcast/src/migrations.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/state-chain/pallets/cf-broadcast/src/migrations.rs b/state-chain/pallets/cf-broadcast/src/migrations.rs index d706760962..5aa0d0d7c3 100644 --- a/state-chain/pallets/cf-broadcast/src/migrations.rs +++ b/state-chain/pallets/cf-broadcast/src/migrations.rs @@ -8,7 +8,7 @@ pub mod remove_aborted_broadcasts; pub type PalletMigration = ( VersionedMigration, initialize_broadcast_timeout_storage::Migration, 6, 7>, VersionedMigration, migrate_timeouts::Migration, 7, 8>, - PlaceholderMigration, 8>, // Migration 8->9 is SerializeSolanaBroadcastMigration in runtime lib. // Migration 9->10 is SolanaEgressSuccessWitnessMigration in runtime lib. + PlaceholderMigration, 10>, ); From 144852f7e86be9d44a189b35d022c1151bfffdf6 Mon Sep 17 00:00:00 2001 From: albert Date: Thu, 31 Oct 2024 09:24:27 +0100 Subject: [PATCH 17/21] chore: fix lint --- bouncer/shared/vault_swap.ts | 53 ++++++++++++++---------------------- 1 file changed, 21 insertions(+), 32 deletions(-) diff --git a/bouncer/shared/vault_swap.ts b/bouncer/shared/vault_swap.ts index 7e842837f9..9677b62a24 100644 --- a/bouncer/shared/vault_swap.ts +++ b/bouncer/shared/vault_swap.ts @@ -277,43 +277,32 @@ export async function performVaultSwap( ); } - // TODO: Temporary before the SDK implements this. if (evmChains.includes(srcChain)) { - // To uniquely identify the VaultSwap, we need to use the TX hash. This is only known - // after sending the transaction, so we send it first and observe the events afterwards. - // There are still multiple blocks of safety margin inbetween before the event is emitted - const receipt = await executeVaultSwap( - sourceAsset, - destAsset, - destAddress, - messageMetadata, - amountToSwap, - boostFeeBps, - fillOrKillParams, - dcaParams, - wallet, - );txHash = receipt.hash; - sourceAddress = wallet!.address.toLowerCase(); - } else { - txHash = await executeSolContractSwap( - sourceAsset, - destAsset, - destAddress, - messageMetadata, - ); - sourceAddress = getSolWhaleKeyPair().publicKey.toBase58(); - } + // To uniquely identify the VaultSwap, we need to use the TX hash. This is only known + // after sending the transaction, so we send it first and observe the events afterwards. + // There are still multiple blocks of safety margin inbetween before the event is emitted + const receipt = await executeVaultSwap( + sourceAsset, + destAsset, + destAddress, + messageMetadata, + amountToSwap, + boostFeeBps, + fillOrKillParams, + dcaParams, + wallet, + ); + txHash = receipt.hash; + sourceAddress = wallet!.address.toLowerCase(); + } else { + txHash = await executeSolContractSwap(sourceAsset, destAsset, destAddress, messageMetadata); + sourceAddress = getSolWhaleKeyPair().publicKey.toBase58(); + } swapContext?.updateStatus(swapTag, SwapStatus.VaultContractExecuted); const ccmEventEmitted = messageMetadata - ? observeCcmReceived( - sourceAsset, - destAsset, - destAddress, - messageMetadata, - sourceAddress, - ) + ? observeCcmReceived(sourceAsset, destAsset, destAddress, messageMetadata, sourceAddress) : Promise.resolve(); const [newBalance] = await Promise.all([ From d3f845c60bbb3d786cf0bf82112e95a607541952 Mon Sep 17 00:00:00 2001 From: albert Date: Mon, 11 Nov 2024 07:29:41 +0100 Subject: [PATCH 18/21] chore: run upgrade test --- .github/workflows/ci-development.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci-development.yml b/.github/workflows/ci-development.yml index bc66706607..149542ba6e 100644 --- a/.github/workflows/ci-development.yml +++ b/.github/workflows/ci-development.yml @@ -79,7 +79,7 @@ jobs: uses: ./.github/workflows/upgrade-test.yml secrets: inherit with: - run-job: false + run-job: true publish: needs: [package] uses: ./.github/workflows/_30_publish.yml From 87e8d800d085860d5c4427c7ac38e83d8afda2ec Mon Sep 17 00:00:00 2001 From: albert Date: Mon, 11 Nov 2024 08:01:49 +0100 Subject: [PATCH 19/21] chore: use Parity VersionedMigration --- state-chain/pallets/cf-environment/src/migrations.rs | 11 ++++++----- .../src/migrations/sol_api_environment.rs | 12 ++++++------ 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/state-chain/pallets/cf-environment/src/migrations.rs b/state-chain/pallets/cf-environment/src/migrations.rs index 11aeccd0e3..3c7a2aedf7 100644 --- a/state-chain/pallets/cf-environment/src/migrations.rs +++ b/state-chain/pallets/cf-environment/src/migrations.rs @@ -2,7 +2,7 @@ use crate::{Config, Pallet}; #[cfg(feature = "try-runtime")] use crate::{CurrentReleaseVersion, Get}; use cf_runtime_utilities::PlaceholderMigration; -use frame_support::traits::OnRuntimeUpgrade; +use frame_support::{migrations::VersionedMigration, traits::OnRuntimeUpgrade}; #[cfg(feature = "try-runtime")] use frame_support::{pallet_prelude::DispatchError, sp_runtime}; #[cfg(feature = "try-runtime")] @@ -37,13 +37,14 @@ impl OnRuntimeUpgrade for VersionUpdate { // Migration for Updating Solana's Api Environments. pub type PalletMigration = ( - cf_runtime_upgrade_utilities::VersionedMigration< - Pallet, - SolApiEnvironmentMigration, + VersionedMigration< 12, 13, + SolApiEnvironmentMigration, + Pallet, + ::DbWeight, >, - PlaceholderMigration, 13>, + PlaceholderMigration<13, Pallet>, ); #[cfg(test)] diff --git a/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs b/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs index 3249e85e9e..5f776cebff 100644 --- a/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs +++ b/state-chain/pallets/cf-environment/src/migrations/sol_api_environment.rs @@ -1,6 +1,6 @@ use crate::*; -use frame_support::{pallet_prelude::Weight, traits::OnRuntimeUpgrade}; +use frame_support::{pallet_prelude::Weight, traits::UncheckedOnRuntimeUpgrade}; use cf_chains::{evm::H256, sol::SolAddress}; use cf_utilities::bs58_array; @@ -23,7 +23,7 @@ pub mod old { pub struct SolApiEnvironmentMigration(PhantomData); -impl> OnRuntimeUpgrade for SolApiEnvironmentMigration { +impl> UncheckedOnRuntimeUpgrade for SolApiEnvironmentMigration { fn on_runtime_upgrade() -> Weight { log::info!("🌮 Running migration for Environment pallet: Updating SolApiEnvironment."); let _ = SolanaApiEnvironment::::translate::(|old_env| { @@ -36,8 +36,8 @@ impl> OnRuntimeUpgrade for SolApiEnvironmentMigration usdc_token_vault_ata, }| { let (swap_endpoint_program, swap_endpoint_program_data_account) = - match cf_runtime_upgrade_utilities::genesis_hashes::genesis_hash::() { - cf_runtime_upgrade_utilities::genesis_hashes::BERGHAIN => ( + match cf_runtime_utilities::genesis_hashes::genesis_hash::() { + cf_runtime_utilities::genesis_hashes::BERGHAIN => ( SolAddress(bs58_array( "BnECXbsDFYPmhxcV57dodaWtJJjtGPE8Le3LAR7qieYb", )), @@ -45,7 +45,7 @@ impl> OnRuntimeUpgrade for SolApiEnvironmentMigration "5mFsKrqCH5v9Q9uF5o6qrsUi1GV2myuhc23NAi5YFs4M", )), ), - cf_runtime_upgrade_utilities::genesis_hashes::PERSEVERANCE => ( + cf_runtime_utilities::genesis_hashes::PERSEVERANCE => ( SolAddress(bs58_array( "FXN1iLmQ47c962nackmzBWZxXE8BR9AXy8mu34oFdKiy", )), @@ -53,7 +53,7 @@ impl> OnRuntimeUpgrade for SolApiEnvironmentMigration "4hD7UM6rQtcqQWtzELvrafpmBYReVXvCpssB6qjY1Sg5", )), ), - cf_runtime_upgrade_utilities::genesis_hashes::SISYPHOS => ( + cf_runtime_utilities::genesis_hashes::SISYPHOS => ( SolAddress(bs58_array( "7G6TxoGDsgaZX3HaKkrKyy28tsdr7ZGmeeMbXpm8R5HZ", )), From b8c714d9f3dbefe4e8eb202a453bab3f6bc1ed4e Mon Sep 17 00:00:00 2001 From: Roy Yang Date: Tue, 12 Nov 2024 12:29:38 +1300 Subject: [PATCH 20/21] Fixed try-runtime error --- state-chain/chains/src/sol/api.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/state-chain/chains/src/sol/api.rs b/state-chain/chains/src/sol/api.rs index 678c6edfcc..543db442d8 100644 --- a/state-chain/chains/src/sol/api.rs +++ b/state-chain/chains/src/sol/api.rs @@ -118,10 +118,10 @@ pub enum SolanaTransactionType { #[deprecated] CcmTransferLegacy, SetGovKeyWithAggKey, - CloseEventAccounts, CcmTransfer { fallback: TransferAssetParams, }, + CloseEventAccounts, } /// The Solana Api call. Contains a call_type and the actual Transaction itself. From e3add5b717b7929212bf8c5dc28bffbc0c00a9c0 Mon Sep 17 00:00:00 2001 From: albert Date: Tue, 12 Nov 2024 07:23:30 +0100 Subject: [PATCH 21/21] chore: not run upgrade test --- .github/workflows/ci-development.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci-development.yml b/.github/workflows/ci-development.yml index 149542ba6e..bc66706607 100644 --- a/.github/workflows/ci-development.yml +++ b/.github/workflows/ci-development.yml @@ -79,7 +79,7 @@ jobs: uses: ./.github/workflows/upgrade-test.yml secrets: inherit with: - run-job: true + run-job: false publish: needs: [package] uses: ./.github/workflows/_30_publish.yml