diff --git a/rs/ledger_suite/icrc1/ledger/BUILD.bazel b/rs/ledger_suite/icrc1/ledger/BUILD.bazel index 3c7a7ce9e676..e332a5585ca9 100644 --- a/rs/ledger_suite/icrc1/ledger/BUILD.bazel +++ b/rs/ledger_suite/icrc1/ledger/BUILD.bazel @@ -235,17 +235,36 @@ package(default_visibility = ["//visibility:public"]) ] ] -rust_test( - name = "ledger_canister_test", - crate = ":_wasm_ledger_canister", - data = [ - ":ledger.did", - ], - env = { - "CARGO_MANIFEST_DIR": "rs/ledger_suite/icrc1/ledger", - }, - deps = ["@crate_index//:candid_parser"], -) +[ + rust_test( + name = "ledger_canister_test" + name_suffix, + crate = ":_wasm_ledger_canister" + name_suffix, + crate_features = features, + data = [ + ":ledger.did", + ], + env = { + "CARGO_MANIFEST_DIR": "rs/ledger_suite/icrc1/ledger", + }, + deps = ["@crate_index//:candid_parser"] + extra_deps, + ) + for (name_suffix, features, extra_deps) in [ + ( + "", + [], + [ + "//rs/ledger_suite/icrc1/tokens_u64", + ], + ), + ( + "_u256", + ["u256-tokens"], + [ + "//rs/ledger_suite/icrc1/tokens_u256", + ], + ), + ] +] [ rust_ic_test( diff --git a/rs/ledger_suite/icrc1/ledger/src/lib.rs b/rs/ledger_suite/icrc1/ledger/src/lib.rs index f24f1554fe99..4b11b6753c59 100644 --- a/rs/ledger_suite/icrc1/ledger/src/lib.rs +++ b/rs/ledger_suite/icrc1/ledger/src/lib.rs @@ -784,6 +784,10 @@ impl Ledger { pub fn copy_token_pool(&mut self) { self.stable_balances.token_pool = self.balances.token_pool; } + + pub fn set_index_principal(&mut self, index_principal: Principal) { + self.index_principal = Some(index_principal); + } } impl LedgerContext for Ledger { diff --git a/rs/ledger_suite/icrc1/ledger/src/main.rs b/rs/ledger_suite/icrc1/ledger/src/main.rs index 1891082ffc08..1f993151375a 100644 --- a/rs/ledger_suite/icrc1/ledger/src/main.rs +++ b/rs/ledger_suite/icrc1/ledger/src/main.rs @@ -260,6 +260,9 @@ fn post_upgrade_internal(args: Option) { initialize_total_volume(); + // TODO(FI-1747): Remove once this has been rolled out to the SNS and chain fusion ledgers. + ensure_index_principal(); + if upgrade_from_version < 3 { set_ledger_state(LedgerState::Migrating(LedgerField::Blocks)); log_message(format!("Upgrading from version {upgrade_from_version} which does not store blocks in stable structures, clearing stable blocks data.").as_str()); @@ -302,6 +305,332 @@ fn initialize_total_volume() { } } +struct LedgerSuite { + pub name: &'static str, + pub ledger: Principal, + pub index: Principal, +} + +#[cfg(not(feature = "u256-tokens"))] +const LEDGER_SUITES: &[LedgerSuite; 40] = &[ + // Chain fusion ledger suites + LedgerSuite { + name: "ckBTC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 6, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 8, 1, 1]), + }, + // Chain fusion test tokens + LedgerSuite { + name: "ckTestBTC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 1, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 3, 1, 1]), + }, + // SNSs + LedgerSuite { + name: "ALICE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 14, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 16, 1, 1]), + }, + LedgerSuite { + name: "BOOM-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 80, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 82, 1, 1]), + }, + LedgerSuite { + name: "CATALYZE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 90, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 92, 1, 1]), + }, + LedgerSuite { + name: "CECIL-THE-LION-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 44, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 46, 1, 1]), + }, + LedgerSuite { + name: "DECIDEAI-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 75, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 77, 1, 1]), + }, + LedgerSuite { + name: "DOLR-AI", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 43, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 45, 1, 1]), + }, + LedgerSuite { + name: "DRAGGINZ", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 12, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 14, 1, 1]), + }, + LedgerSuite { + name: "ELNA-AI", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 155, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 157, 1, 1]), + }, + LedgerSuite { + name: "ESTATEDAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 185, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 187, 1, 1]), + }, + LedgerSuite { + name: "FOMOWELL", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 9, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 11, 1, 1]), + }, + LedgerSuite { + name: "FUELEV", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 26, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 28, 1, 1]), + }, + LedgerSuite { + name: "GOLD-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 126, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 128, 1, 1]), + }, + LedgerSuite { + name: "IC-EXPLORER", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 33, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 35, 1, 1]), + }, + LedgerSuite { + name: "ICFC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 161, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 163, 1, 1]), + }, + LedgerSuite { + name: "ICLIGHTHOUSE-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 150, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 152, 1, 1]), + }, + LedgerSuite { + name: "ICPANDA", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 167, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 169, 1, 1]), + }, + LedgerSuite { + name: "ICPEX", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 49, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 51, 1, 1]), + }, + LedgerSuite { + name: "ICPSWAP", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 172, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 174, 1, 1]), + }, + LedgerSuite { + name: "ICVC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 232, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 234, 1, 1]), + }, + LedgerSuite { + name: "KINIC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 37, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 39, 1, 1]), + }, + LedgerSuite { + name: "KONGSWAP", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 243, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 245, 1, 1]), + }, + LedgerSuite { + name: "MIMIC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 54, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 56, 1, 1]), + }, + LedgerSuite { + name: "MOTOKO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 197, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 199, 1, 1]), + }, + LedgerSuite { + name: "NEUTRINITE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 136, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 138, 1, 1]), + }, + LedgerSuite { + name: "NFID-WALLET", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 21, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 23, 1, 1]), + }, + LedgerSuite { + name: "NUANCE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 103, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 105, 1, 1]), + }, + LedgerSuite { + name: "OPENCHAT", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 25, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 27, 1, 1]), + }, + LedgerSuite { + name: "ORIGYN", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 207, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 209, 1, 1]), + }, + LedgerSuite { + name: "PERSONAL-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 39, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 41, 1, 1]), + }, + LedgerSuite { + name: "POKEDBOTS", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 227, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 229, 1, 1]), + }, + LedgerSuite { + name: "SEERS", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 97, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 99, 1, 1]), + }, + LedgerSuite { + name: "SNEED", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 144, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 146, 1, 1]), + }, + LedgerSuite { + name: "SONIC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 109, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 111, 1, 1]), + }, + LedgerSuite { + name: "SWAMPIES", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 202, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 204, 1, 1]), + }, + LedgerSuite { + name: "TACO-DAO", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 56, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 1, 58, 1, 1]), + }, + LedgerSuite { + name: "TRAX", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 131, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 133, 1, 1]), + }, + LedgerSuite { + name: "WATERNEURON", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 215, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 217, 1, 1]), + }, + LedgerSuite { + name: "YUKU-AI", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 177, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 0, 0, 179, 1, 1]), + }, +]; + +#[cfg(feature = "u256-tokens")] +const LEDGER_SUITES: &[LedgerSuite; 16] = &[ + // Chain fusion ledger suites + LedgerSuite { + name: "ckETH", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 157, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 158, 1, 1]), + }, + LedgerSuite { + name: "ckEURC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 236, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 237, 1, 1]), + }, + LedgerSuite { + name: "ckUNI", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 206, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 207, 1, 1]), + }, + LedgerSuite { + name: "ckWBTC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 175, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 176, 1, 1]), + }, + LedgerSuite { + name: "ckLINK", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 137, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 138, 1, 1]), + }, + LedgerSuite { + name: "ckXAUT", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 243, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 244, 1, 1]), + }, + LedgerSuite { + name: "ckPEPE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 144, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 145, 1, 1]), + }, + LedgerSuite { + name: "ckWSTETH", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 197, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 198, 1, 1]), + }, + LedgerSuite { + name: "ckSHIB", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 156, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 157, 1, 1]), + }, + LedgerSuite { + name: "ckUSDC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 91, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 92, 1, 1]), + }, + LedgerSuite { + name: "ckUSDT", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 185, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 186, 1, 1]), + }, + LedgerSuite { + name: "ckOCT", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 150, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 151, 1, 1]), + }, + // Chain fusion test tokens + LedgerSuite { + name: "ckSepoliaETH", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 88, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 0, 154, 1, 1]), + }, + LedgerSuite { + name: "ckSepoliaUSDC", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 22, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 23, 1, 1]), + }, + LedgerSuite { + name: "ckSepoliaLINK", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 115, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 116, 1, 1]), + }, + LedgerSuite { + name: "ckSepoliaPEPE", + ledger: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 135, 1, 1]), + index: Principal::from_slice(&[0, 0, 0, 0, 2, 48, 1, 136, 1, 1]), + }, +]; + +/// Ensure the principal of the index canister corresponding to this ledger canister is set. +/// This will only set the index principal if: +/// - The index principal is not already set, and; +/// - The ledger principal of the current canister is found in the list of ledgers. +fn ensure_index_principal() { + let index_principal = Access::with_ledger(|ledger| ledger.index_principal()); + if index_principal.is_none() { + let ledger_canister_id = ic_cdk::api::id(); + for suite in LEDGER_SUITES { + if ledger_canister_id == suite.ledger { + Access::with_ledger_mut(|ledger| { + ledger.set_index_principal(suite.index); + log_message(&format!( + "Set index principal of ledger canister {} for {} to {}", + suite.ledger, suite.name, suite.index + )); + }); + return; + } + } + log_message(&format!( + "Not setting index principal of ledger canister {}", + ledger_canister_id + )); + } +} + fn migrate_next_part(instruction_limit: u64) { let instructions_migration_start = instruction_counter(); STABLE_UPGRADE_MIGRATION_STEPS.with(|n| *n.borrow_mut() += 1); @@ -1169,3 +1498,338 @@ fn check_candid_interface() { ) }); } + +#[cfg(feature = "u256-tokens")] +#[test] +fn test_principals_u256() { + const LEDGER_SUITES_STRINGS: &[LedgerSuiteStrings; 16] = &[ + // Chain fusion ledger suites + LedgerSuiteStrings { + name: "ckETH", + ledger: "ss2fx-dyaaa-aaaar-qacoq-cai", + index: "s3zol-vqaaa-aaaar-qacpa-cai", + }, + LedgerSuiteStrings { + name: "ckEURC", + ledger: "pe5t5-diaaa-aaaar-qahwa-cai", + index: "pd4vj-oqaaa-aaaar-qahwq-cai", + }, + LedgerSuiteStrings { + name: "ckUNI", + ledger: "ilzky-ayaaa-aaaar-qahha-cai", + index: "imymm-naaaa-aaaar-qahhq-cai", + }, + LedgerSuiteStrings { + name: "ckWBTC", + ledger: "bptq2-faaaa-aaaar-qagxq-cai", + index: "dso6s-wiaaa-aaaar-qagya-cai", + }, + LedgerSuiteStrings { + name: "ckLINK", + ledger: "g4tto-rqaaa-aaaar-qageq-cai", + index: "gvqys-hyaaa-aaaar-qagfa-cai", + }, + LedgerSuiteStrings { + name: "ckXAUT", + ledger: "nza5v-qaaaa-aaaar-qahzq-cai", + index: "nmhmy-riaaa-aaaar-qah2a-cai", + }, + LedgerSuiteStrings { + name: "ckPEPE", + ledger: "etik7-oiaaa-aaaar-qagia-cai", + index: "eujml-dqaaa-aaaar-qagiq-cai", + }, + LedgerSuiteStrings { + name: "ckWSTETH", + ledger: "j2tuh-yqaaa-aaaar-qahcq-cai", + index: "jtq73-oyaaa-aaaar-qahda-cai", + }, + LedgerSuiteStrings { + name: "ckSHIB", + ledger: "fxffn-xiaaa-aaaar-qagoa-cai", + index: "fqedz-2qaaa-aaaar-qagoq-cai", + }, + LedgerSuiteStrings { + name: "ckUSDC", + ledger: "xevnm-gaaaa-aaaar-qafnq-cai", + index: "xrs4b-hiaaa-aaaar-qafoa-cai", + }, + LedgerSuiteStrings { + name: "ckUSDT", + ledger: "cngnf-vqaaa-aaaar-qag4q-cai", + index: "cefgz-dyaaa-aaaar-qag5a-cai", + }, + LedgerSuiteStrings { + name: "ckOCT", + ledger: "ebo5g-cyaaa-aaaar-qagla-cai", + index: "egp3s-paaaa-aaaar-qaglq-cai", + }, + // Chain fusion test tokens + LedgerSuiteStrings { + name: "ckSepoliaETH", + ledger: "apia6-jaaaa-aaaar-qabma-cai", + index: "sh5u2-cqaaa-aaaar-qacna-cai", + }, + LedgerSuiteStrings { + name: "ckSepoliaUSDC", + ledger: "yfumr-cyaaa-aaaar-qaela-cai", + index: "ycvkf-paaaa-aaaar-qaelq-cai", + }, + LedgerSuiteStrings { + name: "ckSepoliaLINK", + ledger: "r52mc-qaaaa-aaaar-qafzq-cai", + index: "ri55p-riaaa-aaaar-qaf2a-cai", + }, + LedgerSuiteStrings { + name: "ckSepoliaPEPE", + ledger: "hw4ru-taaaa-aaaar-qagdq-cai", + index: "g3sv2-4iaaa-aaaar-qagea-cai", + }, + ]; + assert_ledger_suite_principals(LEDGER_SUITES_STRINGS, LEDGER_SUITES); +} + +#[cfg(not(feature = "u256-tokens"))] +#[test] +fn test_principals_u64() { + const LEDGER_SUITES_STRINGS: &[LedgerSuiteStrings; 40] = &[ + // Chain fusion ledger suites + LedgerSuiteStrings { + name: "ckBTC", + ledger: "mxzaz-hqaaa-aaaar-qaada-cai", + index: "n5wcd-faaaa-aaaar-qaaea-cai", + }, + // Chain fusion test tokens + LedgerSuiteStrings { + name: "ckTestBTC", + ledger: "mc6ru-gyaaa-aaaar-qaaaq-cai", + index: "mm444-5iaaa-aaaar-qaabq-cai", + }, + // SNSs + LedgerSuiteStrings { + name: "ALICE", + ledger: "oj6if-riaaa-aaaaq-aaeha-cai", + index: "mtcaz-pyaaa-aaaaq-aaeia-cai", + }, + LedgerSuiteStrings { + name: "BOOM-DAO", + ledger: "vtrom-gqaaa-aaaaq-aabia-cai", + index: "v5tde-5aaaa-aaaaq-aabja-cai", + }, + LedgerSuiteStrings { + name: "CATALYZE", + ledger: "uf2wh-taaaa-aaaaq-aabna-cai", + index: "ux4b6-7qaaa-aaaaq-aaboa-cai", + }, + LedgerSuiteStrings { + name: "CECIL-THE-LION-DAO", + ledger: "jg2ra-syaaa-aaaaq-aaewa-cai", + index: "jiy4i-jiaaa-aaaaq-aaexa-cai", + }, + LedgerSuiteStrings { + name: "DECIDEAI-DAO", + ledger: "xsi2v-cyaaa-aaaaq-aabfq-cai", + index: "xaonm-oiaaa-aaaaq-aabgq-cai", + }, + LedgerSuiteStrings { + name: "DOLR-AI", + ledger: "6rdgd-kyaaa-aaaaq-aaavq-cai", + index: "6dfr2-giaaa-aaaaq-aaawq-cai", + }, + LedgerSuiteStrings { + name: "DRAGGINZ", + ledger: "zfcdd-tqaaa-aaaaq-aaaga-cai", + index: "zlaol-iaaaa-aaaaq-aaaha-cai", + }, + LedgerSuiteStrings { + name: "ELNA-AI", + ledger: "gemj7-oyaaa-aaaaq-aacnq-cai", + index: "gwk6g-ciaaa-aaaaq-aacoq-cai", + }, + LedgerSuiteStrings { + name: "ESTATEDAO", + ledger: "bliq2-niaaa-aaaaq-aac4q-cai", + index: "bfk5s-wyaaa-aaaaq-aac5q-cai", + }, + LedgerSuiteStrings { + name: "FOMOWELL", + ledger: "o4zzi-qaaaa-aaaaq-aaeeq-cai", + index: "os3ua-lqaaa-aaaaq-aaefq-cai", + }, + LedgerSuiteStrings { + name: "FUELEV", + ledger: "nfjys-2iaaa-aaaaq-aaena-cai", + index: "nxppl-wyaaa-aaaaq-aaeoa-cai", + }, + LedgerSuiteStrings { + name: "GOLD-DAO", + ledger: "tyyy3-4aaaa-aaaaq-aab7a-cai", + index: "efv5g-kqaaa-aaaaq-aacaa-cai", + }, + LedgerSuiteStrings { + name: "IC-EXPLORER", + ledger: "ifwyg-gaaaa-aaaaq-aaeqq-cai", + index: "iluvo-5qaaa-aaaaq-aaerq-cai", + }, + LedgerSuiteStrings { + name: "ICFC", + ledger: "ddsp7-7iaaa-aaaaq-aacqq-cai", + index: "dnqcx-eyaaa-aaaaq-aacrq-cai", + }, + LedgerSuiteStrings { + name: "ICLIGHTHOUSE-DAO", + ledger: "hhaaz-2aaaa-aaaaq-aacla-cai", + index: "gnpcd-yqaaa-aaaaq-aacma-cai", + }, + LedgerSuiteStrings { + name: "ICPANDA", + ledger: "druyg-tyaaa-aaaaq-aactq-cai", + index: "c3324-riaaa-aaaaq-aacuq-cai", + }, + LedgerSuiteStrings { + name: "ICPEX", + ledger: "lvfsa-2aaaa-aaaaq-aaeyq-cai", + index: "l3h7i-bqaaa-aaaaq-aaezq-cai", + }, + LedgerSuiteStrings { + name: "ICPSWAP", + ledger: "ca6gz-lqaaa-aaaaq-aacwa-cai", + index: "co4lr-qaaaa-aaaaq-aacxa-cai", + }, + LedgerSuiteStrings { + name: "ICVC", + ledger: "m6xut-mqaaa-aaaaq-aadua-cai", + index: "mqvz3-xaaaa-aaaaq-aadva-cai", + }, + LedgerSuiteStrings { + name: "KINIC", + ledger: "73mez-iiaaa-aaaaq-aaasq-cai", + index: "7vojr-tyaaa-aaaaq-aaatq-cai", + }, + LedgerSuiteStrings { + name: "KONGSWAP", + ledger: "o7oak-iyaaa-aaaaq-aadzq-cai", + index: "onixt-eiaaa-aaaaq-aad2q-cai", + }, + LedgerSuiteStrings { + name: "MIMIC", + ledger: "4c4fd-caaaa-aaaaq-aaa3a-cai", + index: "5ithz-aqaaa-aaaaq-aaa4a-cai", + }, + LedgerSuiteStrings { + name: "MOTOKO", + ledger: "k45jy-aiaaa-aaaaq-aadcq-cai", + index: "ks7eq-3yaaa-aaaaq-aaddq-cai", + }, + LedgerSuiteStrings { + name: "NEUTRINITE", + ledger: "f54if-eqaaa-aaaaq-aacea-cai", + index: "ft6fn-7aaaa-aaaaq-aacfa-cai", + }, + LedgerSuiteStrings { + name: "NFID-WALLET", + ledger: "mih44-vaaaa-aaaaq-aaekq-cai", + index: "mgfru-oqaaa-aaaaq-aaelq-cai", + }, + LedgerSuiteStrings { + name: "NUANCE", + ledger: "rxdbk-dyaaa-aaaaq-aabtq-cai", + index: "q5mdq-biaaa-aaaaq-aabuq-cai", + }, + LedgerSuiteStrings { + name: "OPENCHAT", + ledger: "2ouva-viaaa-aaaaq-aaamq-cai", + index: "2awyi-oyaaa-aaaaq-aaanq-cai", + }, + LedgerSuiteStrings { + name: "ORIGYN", + ledger: "lkwrt-vyaaa-aaaaq-aadhq-cai", + index: "jqkzp-liaaa-aaaaq-aadiq-cai", + }, + LedgerSuiteStrings { + name: "PERSONAL-DAO", + ledger: "ixqp7-kqaaa-aaaaq-aaetq-cai", + index: "j57nf-iaaaa-aaaaq-aaeuq-cai", + }, + LedgerSuiteStrings { + name: "POKEDBOTS", + ledger: "np5km-uyaaa-aaaaq-aadrq-cai", + index: "n535v-yiaaa-aaaaq-aadsq-cai", + }, + LedgerSuiteStrings { + name: "SEERS", + ledger: "rffwt-piaaa-aaaaq-aabqq-cai", + index: "rlh33-uyaaa-aaaaq-aabrq-cai", + }, + LedgerSuiteStrings { + name: "SNEED", + ledger: "hvgxa-wqaaa-aaaaq-aacia-cai", + index: "h3e2i-naaaa-aaaaq-aacja-cai", + }, + LedgerSuiteStrings { + name: "SONIC", + ledger: "qbizb-wiaaa-aaaaq-aabwq-cai", + index: "qpkuj-nyaaa-aaaaq-aabxq-cai", + }, + LedgerSuiteStrings { + name: "SWAMPIES", + ledger: "lrtnw-paaaa-aaaaq-aadfa-cai", + index: "ldv2p-dqaaa-aaaaq-aadga-cai", + }, + LedgerSuiteStrings { + name: "TACO-DAO", + ledger: "kknbx-zyaaa-aaaaq-aae4a-cai", + index: "kepm7-ciaaa-aaaaq-aae5a-cai", + }, + LedgerSuiteStrings { + name: "TRAX", + ledger: "emww2-4yaaa-aaaaq-aacbq-cai", + index: "e6qbd-qiaaa-aaaaq-aaccq-cai", + }, + LedgerSuiteStrings { + name: "WATERNEURON", + ledger: "jcmow-hyaaa-aaaaq-aadlq-cai", + index: "iidmm-fiaaa-aaaaq-aadmq-cai", + }, + LedgerSuiteStrings { + name: "YUKU-AI", + ledger: "atbfz-diaaa-aaaaq-aacyq-cai", + index: "a5dir-yyaaa-aaaaq-aaczq-cai", + }, + ]; + + assert_ledger_suite_principals(LEDGER_SUITES_STRINGS, LEDGER_SUITES); +} + +#[cfg(test)] +struct LedgerSuiteStrings { + pub name: &'static str, + pub ledger: &'static str, + pub index: &'static str, +} + +#[cfg(test)] +fn assert_ledger_suite_principals( + ledger_suite_strings: &[LedgerSuiteStrings], + ledger_suite_principals: &[LedgerSuite], +) { + assert_eq!(ledger_suite_strings.len(), ledger_suite_principals.len()); + let mut found = 0; + for suite in ledger_suite_strings { + for principal_suite in ledger_suite_principals { + if suite.name == principal_suite.name { + assert_eq!( + Principal::from_text(suite.ledger).unwrap(), + principal_suite.ledger + ); + assert_eq!( + Principal::from_text(suite.index).unwrap(), + principal_suite.index + ); + found += 1; + break; + } + } + } + assert_eq!(found, ledger_suite_principals.len()); +} diff --git a/rs/ledger_suite/icrc1/ledger/tests/tests.rs b/rs/ledger_suite/icrc1/ledger/tests/tests.rs index c92089472538..1fb876c5502f 100644 --- a/rs/ledger_suite/icrc1/ledger/tests/tests.rs +++ b/rs/ledger_suite/icrc1/ledger/tests/tests.rs @@ -605,6 +605,15 @@ fn test_icrc106_set_index_in_upgrade() { ); } +#[test] +fn test_icrc106_set_hardcoded_index_in_upgrade() { + ic_ledger_suite_state_machine_tests::icrc_106::test_icrc106_set_hardcoded_index_in_upgrade( + ledger_wasm(), + encode_init_args, + encode_icrc106_upgrade_args, + ); +} + #[test] fn test_upgrade_from_mainnet_ledger_version() { ic_ledger_suite_state_machine_tests::icrc_106::test_upgrade_downgrade_with_mainnet_ledger( diff --git a/rs/ledger_suite/icrc1/tests/golden_state_upgrade_downgrade.rs b/rs/ledger_suite/icrc1/tests/golden_state_upgrade_downgrade.rs index c2155010c639..0997cc97856b 100644 --- a/rs/ledger_suite/icrc1/tests/golden_state_upgrade_downgrade.rs +++ b/rs/ledger_suite/icrc1/tests/golden_state_upgrade_downgrade.rs @@ -1,6 +1,6 @@ use crate::common::{index_ng_wasm, ledger_wasm, load_wasm_using_env_var}; use crate::index::verify_ledger_archive_and_index_block_parity; -use candid::{Encode, Nat, Principal}; +use candid::{Decode, Encode, Nat, Principal}; use canister_test::Wasm; use ic_base_types::{CanisterId, PrincipalId}; use ic_icrc1::Block; @@ -16,6 +16,7 @@ use ic_ledger_suite_state_machine_tests::{ use ic_nns_test_utils_golden_nns_state::new_state_machine_with_golden_fiduciary_state_or_panic; use ic_state_machine_tests::{StateMachine, UserError}; use icrc_ledger_types::icrc1::account::Account; +use icrc_ledger_types::icrc106::errors::Icrc106Error; use lazy_static::lazy_static; use std::str::FromStr; @@ -211,6 +212,8 @@ impl LedgerSuiteConfig { previous_ledger_state, )); } + // Verify that the index principal was set in the ledger + self.check_index_principal(state_machine, ledger_canister_id, index_canister_id); // Downgrade back to the mainnet canister versions self.downgrade_to_mainnet(state_machine); if self.extended_testing { @@ -224,6 +227,36 @@ impl LedgerSuiteConfig { } } + fn check_index_principal( + &self, + env: &StateMachine, + ledger_canister_id: CanisterId, + index_canister_id: CanisterId, + ) { + match Decode!( + &env.query(ledger_canister_id, "icrc106_get_index_principal", Encode!().unwrap()) + .expect("failed to query icrc106_get_index_principal") + .bytes(), + Result + ) + .expect("failed to decode icrc106_get_index_principal response") + { + Ok(index_principal) => { + assert_eq!( + index_principal, + index_canister_id.get().0, + "Index principal does not match index canister id" + ) + } + Err(err) => { + panic!( + "Failed to get index principal for ledger {}: {:?}", + ledger_canister_id, err + ); + } + } + } + fn print_ledger_metrics(&self, state_machine: &StateMachine) { let ledger_id = CanisterId::unchecked_from_principal(PrincipalId::from_str(self.ledger_id).unwrap()); @@ -691,20 +724,20 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "ux4b6-7qaaa-aaaaq-aaboa-cai", "Catalyze", ); + const CECIL_THE_LION_DAO_LEDGER_SUITE: (&str, &str, &str) = ( + "jg2ra-syaaa-aaaaq-aaewa-cai", + "jiy4i-jiaaa-aaaaq-aaexa-cai", + "Cecil The Lion DAO", + ); const DECIDEAI_LEDGER_SUITE: (&str, &str, &str) = ( "xsi2v-cyaaa-aaaaq-aabfq-cai", "xaonm-oiaaa-aaaaq-aabgq-cai", "DecideAI", ); - const DOGMI_LEDGER_SUITE: (&str, &str, &str) = ( - "np5km-uyaaa-aaaaq-aadrq-cai", - "n535v-yiaaa-aaaaq-aadsq-cai", - "DOGMI", - ); const DOLR_AI_LEDGER_SUITE: (&str, &str, &str) = ( "6rdgd-kyaaa-aaaaq-aaavq-cai", "6dfr2-giaaa-aaaaq-aaawq-cai", - "YRAL", + "DOLR", ); const DRAGGINZ_LEDGER_SUITE: (&str, &str, &str) = ( "zfcdd-tqaaa-aaaaq-aaaga-cai", @@ -736,10 +769,15 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "efv5g-kqaaa-aaaaq-aacaa-cai", "GoldDAO", ); - const ICGHOST_LEDGER_SUITE: (&str, &str, &str) = ( - "4c4fd-caaaa-aaaaq-aaa3a-cai", - "5ithz-aqaaa-aaaaq-aaa4a-cai", - "ICGhost", + const IC_EXPLORER_LEDGER_SUITE: (&str, &str, &str) = ( + "ifwyg-gaaaa-aaaaq-aaeqq-cai", + "iluvo-5qaaa-aaaaq-aaerq-cai", + "IC Explorer", + ); + const ICFC_LEDGER_SUITE: (&str, &str, &str) = ( + "ddsp7-7iaaa-aaaaq-aacqq-cai", + "dnqcx-eyaaa-aaaaq-aacrq-cai", + "ICFC", ); const ICLIGHTHOUSE_LEDGER_SUITE: (&str, &str, &str) = ( "hhaaz-2aaaa-aaaaq-aacla-cai", @@ -751,10 +789,10 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "c3324-riaaa-aaaaq-aacuq-cai", "ICPanda DAO", ); - const ICPCC_LEDGER_SUITE: (&str, &str, &str) = ( - "lrtnw-paaaa-aaaaq-aadfa-cai", - "ldv2p-dqaaa-aaaaq-aadga-cai", - "ICPCC DAO LLC", + const ICPEX_LEDGER_SUITE: (&str, &str, &str) = ( + "lvfsa-2aaaa-aaaaq-aaeyq-cai", + "l3h7i-bqaaa-aaaaq-aaezq-cai", + "ICPEX", ); const ICPSWAP_LEDGER_SUITE: (&str, &str, &str) = ( "ca6gz-lqaaa-aaaaq-aacwa-cai", @@ -776,6 +814,11 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "onixt-eiaaa-aaaaq-aad2q-cai", "KongSwap", ); + const MIMIC_LEDGER_SUITE: (&str, &str, &str) = ( + "4c4fd-caaaa-aaaaq-aaa3a-cai", + "5ithz-aqaaa-aaaaq-aaa4a-cai", + "Mimic", + ); const MOTOKO_LEDGER_SUITE: (&str, &str, &str) = ( "k45jy-aiaaa-aaaaq-aadcq-cai", "ks7eq-3yaaa-aaaaq-aaddq-cai", @@ -801,16 +844,21 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "2awyi-oyaaa-aaaaq-aaanq-cai", "OpenChat", ); - const OPENFPL_LEDGER_SUITE: (&str, &str, &str) = ( - "ddsp7-7iaaa-aaaaq-aacqq-cai", - "dnqcx-eyaaa-aaaaq-aacrq-cai", - "OpenFPL", - ); const ORIGYN_LEDGER_SUITE: (&str, &str, &str) = ( "lkwrt-vyaaa-aaaaq-aadhq-cai", "jqkzp-liaaa-aaaaq-aadiq-cai", "Origyn", ); + const PERSONAL_DAO_LEDGER_SUITE: (&str, &str, &str) = ( + "ixqp7-kqaaa-aaaaq-aaetq-cai", + "j57nf-iaaaa-aaaaq-aaeuq-cai", + "Personal DAO", + ); + const POKEDBOTS_LEDGER_SUITE: (&str, &str, &str) = ( + "np5km-uyaaa-aaaaq-aadrq-cai", + "n535v-yiaaa-aaaaq-aadsq-cai", + "PokedBots", + ); const SEERS_LEDGER_SUITE: (&str, &str, &str) = ( "rffwt-piaaa-aaaaq-aabqq-cai", "rlh33-uyaaa-aaaaq-aabrq-cai", @@ -826,6 +874,16 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { "qpkuj-nyaaa-aaaaq-aabxq-cai", "Sonic", ); + const SWAMPIES_LEDGER_SUITE: (&str, &str, &str) = ( + "lrtnw-paaaa-aaaaq-aadfa-cai", + "ldv2p-dqaaa-aaaaq-aadga-cai", + "Swampies", + ); + const TACO_LEDGER_SUITE: (&str, &str, &str) = ( + "kknbx-zyaaa-aaaaq-aae4a-cai", + "kepm7-ciaaa-aaaaq-aae5a-cai", + "TACO DAO", + ); const TRAX_LEDGER_SUITE: (&str, &str, &str) = ( "emww2-4yaaa-aaaaq-aacbq-cai", "e6qbd-qiaaa-aaaaq-aaccq-cai", @@ -853,8 +911,8 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { ALICE_LEDGER_SUITE, BOOMDAO_LEDGER_SUITE, CATALYZE_LEDGER_SUITE, + CECIL_THE_LION_DAO_LEDGER_SUITE, DECIDEAI_LEDGER_SUITE, - DOGMI_LEDGER_SUITE, DOLR_AI_LEDGER_SUITE, DRAGGINZ_LEDGER_SUITE, ELNAAI_LEDGER_SUITE, @@ -862,23 +920,28 @@ fn should_upgrade_icrc_sns_canisters_with_golden_state() { FOMOWELL_LEDGER_SUITE, // FUEL_EV_LEDGER_SUITE, // Skipping FuelEV for now, as the index canister was uninstalled GOLDDAO_LEDGER_SUITE, - ICGHOST_LEDGER_SUITE, + IC_EXPLORER_LEDGER_SUITE, + ICFC_LEDGER_SUITE, ICLIGHTHOUSE_LEDGER_SUITE, ICPANDA_LEDGER_SUITE, - ICPCC_LEDGER_SUITE, + ICPEX_LEDGER_SUITE, ICPSWAP_LEDGER_SUITE, ICVC_LEDGER_SUITE, KINIC_LEDGER_SUITE, KONG_SWAP_LEDGER_SUITE, + MIMIC_LEDGER_SUITE, MOTOKO_LEDGER_SUITE, NEUTRINITE_LEDGER_SUITE, NFID_WALLET_LEDGER_SUITE, NUANCE_LEDGER_SUITE, - OPENFPL_LEDGER_SUITE, ORIGYN_LEDGER_SUITE, + PERSONAL_DAO_LEDGER_SUITE, + POKEDBOTS_LEDGER_SUITE, SEERS_LEDGER_SUITE, SNEED_LEDGER_SUITE, SONIC_LEDGER_SUITE, + SWAMPIES_LEDGER_SUITE, + TACO_LEDGER_SUITE, TRAX_LEDGER_SUITE, WATERNEURON_LEDGER_SUITE, YUKU_LEDGER_SUITE, diff --git a/rs/ledger_suite/tests/sm-tests/src/icrc_106.rs b/rs/ledger_suite/tests/sm-tests/src/icrc_106.rs index 9f4bbd267d42..08b34ed0aa89 100644 --- a/rs/ledger_suite/tests/sm-tests/src/icrc_106.rs +++ b/rs/ledger_suite/tests/sm-tests/src/icrc_106.rs @@ -1,4 +1,6 @@ use super::*; +use ic_state_machine_tests::StateMachineBuilder; +use std::str::FromStr; pub fn test_icrc106_supported_even_if_index_not_set( ledger_wasm: Vec, @@ -83,6 +85,67 @@ pub fn test_icrc106_set_index_in_upgrade( assert_index_set(&env, canister_id, index_principal); } +pub fn test_icrc106_set_hardcoded_index_in_upgrade( + ledger_wasm: Vec, + encode_init_args: fn(InitArgs) -> T, + encode_upgrade_args: fn(Option) -> U, +) where + T: CandidType, + U: CandidType, +{ + let env = StateMachineBuilder::new() + .with_extra_canister_range(std::ops::RangeInclusive::::new( + CanisterId::from_u64(0x2300000), + CanisterId::from_u64(0x23FFFFE), + )) + .build(); + + #[cfg(not(feature = "u256-tokens"))] + // For u64 tokens, use the ckBTC ledger canister ID + let ledger_principal_id = PrincipalId::from_str("mxzaz-hqaaa-aaaar-qaada-cai") + .expect("should parse canister ID from string"); + #[cfg(feature = "u256-tokens")] + // For u256 tokens, use the ckETH ledger canister ID + let ledger_principal_id = PrincipalId::from_str("ss2fx-dyaaa-aaaar-qacoq-cai") + .expect("should parse canister ID from string"); + + let canister_id = + env.create_canister_with_cycles(Some(ledger_principal_id), Cycles::zero(), None); + let ledger_init_args = encode_init_args(init_args(vec![])); + env.install_existing_canister( + canister_id, + ledger_wasm.clone(), + Encode!(&ledger_init_args).unwrap(), + ) + .expect("should successfully install ledger canister"); + + assert_index_not_set(&env, canister_id, true); + + let args = encode_upgrade_args(None); + let encoded_upgrade_args = Encode!(&args).unwrap(); + env.upgrade_canister(canister_id, ledger_wasm.clone(), encoded_upgrade_args) + .expect("should successfully upgrade ledger canister"); + + #[cfg(not(feature = "u256-tokens"))] + // For u64 tokens, use the ckBTC index canister ID + let index_principal_id = Principal::from_str("n5wcd-faaaa-aaaar-qaaea-cai") + .expect("should parse canister ID from string"); + #[cfg(feature = "u256-tokens")] + // For u64 tokens, use the ckETH index canister ID + let index_principal_id = Principal::from_str("s3zol-vqaaa-aaaar-qacpa-cai") + .expect("should parse canister ID from string"); + + // The index should now be set + assert_index_set(&env, canister_id, index_principal_id); + + let args = encode_upgrade_args(None); + let encoded_upgrade_args = Encode!(&args).unwrap(); + env.upgrade_canister(canister_id, ledger_wasm, encoded_upgrade_args) + .expect("should successfully upgrade ledger canister"); + // Passing `None` should not change the previously set index + assert_index_set(&env, canister_id, index_principal_id); +} + pub fn test_upgrade_downgrade_with_mainnet_ledger( mainnet_ledger_wasm: Vec, ledger_wasm: Vec,