Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion pallets/subtensor/src/macros/hooks.rs
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,9 @@ mod hooks {
// Fix RootClaimed overclaim caused by single-subnet hotkey swap bug
.saturating_add(migrations::migrate_fix_root_claimed_overclaim::migrate_fix_root_claimed_overclaim::<T>())
// Mint missing SubnetTAO and SubnetLocked into subnet accounts to make TotalIssuance match in balances and subtensor
.saturating_add(migrations::migrate_subnet_balances::migrate_subnet_balances::<T>());
.saturating_add(migrations::migrate_subnet_balances::migrate_subnet_balances::<T>())
// Fix testnet Subtensor TotalIssuance after the EVM fees issue.
.saturating_add(migrations::migrate_fix_total_issuance_evm_fees::migrate_fix_total_issuance_evm_fees::<T>());
weight
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
use super::*;
use frame_support::traits::fungible::Inspect;
use frame_support::weights::Weight;

pub fn migrate_fix_total_issuance_evm_fees<T: Config>() -> Weight {
let migration_name = b"migrate_fix_total_issuance_evm_fees".to_vec();
let mut weight = T::DbWeight::get().reads(1);

if HasMigrationRun::<T>::get(&migration_name) {
log::info!(
"Migration '{:?}' has already run. Skipping.",
String::from_utf8_lossy(&migration_name)
);
return weight;
}

log::info!(
"Running migration '{}'",
String::from_utf8_lossy(&migration_name)
);

// Fix testnet TotalIssuance after the earlier EVM fees issue caused the
// Subtensor pallet's accounting to diverge from the balances pallet.
let balances_total_issuance = <T as Config>::Currency::total_issuance();
let subtensor_total_issuance_before = TotalIssuance::<T>::get();
TotalIssuance::<T>::put(balances_total_issuance);
weight = weight.saturating_add(T::DbWeight::get().reads_writes(2, 1));

log::info!(
"Subtensor TotalIssuance fixed for EVM fees issue: previous: {}, new: {}",
subtensor_total_issuance_before,
balances_total_issuance
);

HasMigrationRun::<T>::insert(&migration_name, true);
weight = weight.saturating_add(T::DbWeight::get().writes(1));

log::info!(
target: "runtime",
"Migration '{}' completed successfully.",
String::from_utf8_lossy(&migration_name)
);

weight
}
1 change: 1 addition & 0 deletions pallets/subtensor/src/migrations/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ pub mod migrate_fix_root_claimed_overclaim;
pub mod migrate_fix_root_subnet_tao;
pub mod migrate_fix_root_tao_and_alpha_in;
pub mod migrate_fix_staking_hot_keys;
pub mod migrate_fix_total_issuance_evm_fees;
pub mod migrate_init_tao_flow;
pub mod migrate_init_total_issuance;
pub mod migrate_kappa_map_to_default;
Expand Down
12 changes: 12 additions & 0 deletions pallets/subtensor/src/subnets/subnet.rs
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,9 @@ impl<T: Config> Pallet<T> {

let owner_alpha_stake = AlphaBalance::ZERO;

// With the full lock retained in the reserve, this will normally be zero.
let tao_recycled_for_registration = actual_tao_lock_amount.saturating_sub(total_pool_tao);

// Core pool + ownership
SubnetTAO::<T>::insert(netuid_to_register, total_pool_tao);
SubnetAlphaIn::<T>::insert(netuid_to_register, total_pool_alpha);
Expand All @@ -245,6 +248,15 @@ impl<T: Config> Pallet<T> {
SubnetAlphaInProvided::<T>::insert(netuid_to_register, AlphaBalance::ZERO);
SubnetAlphaOut::<T>::insert(netuid_to_register, owner_alpha_stake);
SubnetVolume::<T>::insert(netuid_to_register, 0u128);
RAORecycledForRegistration::<T>::insert(netuid_to_register, tao_recycled_for_registration);

if tao_recycled_for_registration > TaoBalance::ZERO
&& let Some(subnet_account_id) = Self::get_subnet_account_id(netuid_to_register)
{
// The subnet account ID is guaranteed to have adequate balance for this
// recycle because of transfer operation earlier. No need to check this result.
let _ = Self::recycle_tao(&subnet_account_id, tao_recycled_for_registration);
}

if total_pool_tao > TaoBalance::ZERO {
// Record in TotalStake the initial TAO in the pool.
Expand Down
40 changes: 39 additions & 1 deletion pallets/subtensor/src/tests/migration.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ use frame_support::{
StorageHasher, Twox64Concat, assert_ok,
storage::unhashed::{get, get_raw, put, put_raw},
storage_alias,
traits::{StorageInstance, StoredMap},
traits::{Currency, StorageInstance, StoredMap, fungible::Inspect},
weights::Weight,
};
use safe_math::SafeDiv;
Expand Down Expand Up @@ -4356,3 +4356,41 @@ fn test_migrate_subnet_balances() {
assert!(HasMigrationRun::<Test>::get(MIGRATION_NAME.to_vec()));
});
}

#[test]
fn test_migrate_fix_total_issuance_evm_fees() {
new_test_ext(1).execute_with(|| {
const MIGRATION_NAME: &[u8] = b"migrate_fix_total_issuance_evm_fees";

let account = U256::from(42);
let balances_total_issuance = TaoBalance::from(123_456_789_u64);
Balances::make_free_balance_be(&account, balances_total_issuance);

let broken_subtensor_total_issuance = TaoBalance::from(987_654_321_u64);
TotalIssuance::<Test>::put(broken_subtensor_total_issuance);

assert_eq!(Balances::total_issuance(), balances_total_issuance);
assert_eq!(
TotalIssuance::<Test>::get(),
broken_subtensor_total_issuance
);
assert!(!HasMigrationRun::<Test>::get(MIGRATION_NAME.to_vec()));

let weight = crate::migrations::migrate_fix_total_issuance_evm_fees::migrate_fix_total_issuance_evm_fees::<Test>();

assert!(!weight.is_zero(), "weight must be non-zero");
assert_eq!(TotalIssuance::<Test>::get(), balances_total_issuance);
assert!(HasMigrationRun::<Test>::get(MIGRATION_NAME.to_vec()));

let second_wrong_value = TaoBalance::from(555_u64);
TotalIssuance::<Test>::put(second_wrong_value);

crate::migrations::migrate_fix_total_issuance_evm_fees::migrate_fix_total_issuance_evm_fees::<Test>();

assert_eq!(
TotalIssuance::<Test>::get(),
second_wrong_value,
"migration must not run more than once"
);
});
}
Loading