Skip to content
Draft
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
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,7 @@ mod dip_did_proof_with_verified_relay_state_root {
type Hash = H256;
type Hashing = BlakeTwo256;
type Lookup = IdentityLookup<Self::AccountId>;
type MaxConsumers = ConstU32<16>;
type MaxConsumers = ConstU32<100>;
type Nonce = u64;
type OnKilledAccount = ();
type OnNewAccount = ();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ impl frame_system::Config for TestRuntime {
type Hash = H256;
type Hashing = BlakeTwo256;
type Lookup = IdentityLookup<Self::AccountId>;
type MaxConsumers = ConstU32<16>;
type MaxConsumers = ConstU32<100>;
type Nonce = u64;
type OnKilledAccount = ();
type OnNewAccount = ();
Expand Down
2 changes: 1 addition & 1 deletion pallets/attestation/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -261,7 +261,7 @@ pub(crate) mod runtime {
type BlockLength = ();
type SS58Prefix = SS58Prefix;
type OnSetCode = ();
type MaxConsumers = frame_support::traits::ConstU32<16>;
type MaxConsumers = frame_support::traits::ConstU32<100>;
}

parameter_types! {
Expand Down
2 changes: 1 addition & 1 deletion pallets/ctype/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ pub mod runtime {
type BlockLength = ();
type SS58Prefix = SS58Prefix;
type OnSetCode = ();
type MaxConsumers = frame_support::traits::ConstU32<16>;
type MaxConsumers = frame_support::traits::ConstU32<100>;
}

parameter_types! {
Expand Down
2 changes: 1 addition & 1 deletion pallets/delegation/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ pub(crate) mod runtime {
type BlockLength = ();
type SS58Prefix = SS58Prefix;
type OnSetCode = ();
type MaxConsumers = frame_support::traits::ConstU32<16>;
type MaxConsumers = frame_support::traits::ConstU32<100>;
}

parameter_types! {
Expand Down
2 changes: 1 addition & 1 deletion pallets/did/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ impl frame_system::Config for Test {
type BlockLength = ();
type SS58Prefix = SS58Prefix;
type OnSetCode = ();
type MaxConsumers = frame_support::traits::ConstU32<16>;
type MaxConsumers = frame_support::traits::ConstU32<100>;
}

parameter_types! {
Expand Down
2 changes: 1 addition & 1 deletion pallets/pallet-asset-switch/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ impl frame_system::Config for MockRuntime {
type Hash = H256;
type Hashing = BlakeTwo256;
type Lookup = IdentityLookup<Self::AccountId>;
type MaxConsumers = ConstU32<16>;
type MaxConsumers = ConstU32<100>;
type Nonce = u64;
type OnKilledAccount = ();
type OnNewAccount = ();
Expand Down
22 changes: 9 additions & 13 deletions pallets/pallet-bonded-coins/src/benchmarking.rs
Original file line number Diff line number Diff line change
Expand Up @@ -355,25 +355,18 @@ mod benchmarks {
}

#[benchmark]
fn reset_team() {
fn reset_team(c: Linear<1, { T::MaxCurrenciesPerPool::get() }>) {
let origin = T::DefaultOrigin::try_successful_origin().expect("creating origin should not fail");
let account_origin = origin
.clone()
.into_signer()
.expect("generating account_id from origin should not fail");
make_free_for_deposit::<T>(&account_origin);

let bonded_coin_id = T::BenchmarkHelper::calculate_bonded_asset_id(0);
create_bonded_asset::<T>(bonded_coin_id.clone());
let bonded_currencies = create_bonded_currencies_in_range::<T>(c, false);

let curve = get_linear_bonding_curve::<CurveParameterTypeOf<T>>();
let pool_id = create_pool::<T>(
curve,
[bonded_coin_id.clone()].to_vec(),
Some(account_origin),
None,
None,
);
let pool_id = create_pool::<T>(curve, bonded_currencies.clone(), Some(account_origin), None, None);

let admin: AccountIdOf<T> = account("admin", 0, 0);
let freezer: AccountIdOf<T> = account("freezer", 0, 0);
Expand All @@ -382,12 +375,15 @@ mod benchmarks {
freezer: freezer.clone(),
};

let max_currencies = T::MaxCurrenciesPerPool::get();
#[extrinsic_call]
_(origin as T::RuntimeOrigin, pool_id, fungibles_team, 0);
_(origin as T::RuntimeOrigin, pool_id, fungibles_team, max_currencies);

// Verify
assert_eq!(T::Fungibles::admin(bonded_coin_id.clone()), Some(admin));
assert_eq!(T::Fungibles::freezer(bonded_coin_id), Some(freezer));
bonded_currencies.iter().for_each(|asset_id| {
assert_eq!(T::Fungibles::admin(asset_id.clone()), Some(admin.clone()));
assert_eq!(T::Fungibles::freezer(asset_id.clone()), Some(freezer.clone()));
});
}

#[benchmark]
Expand Down
67 changes: 41 additions & 26 deletions pallets/pallet-bonded-coins/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ pub mod pallet {
Create as CreateFungibles, Destroy as DestroyFungibles, Inspect as InspectFungibles,
Mutate as MutateFungibles,
},
tokens::{Fortitude, Precision as WithdrawalPrecision, Preservation, Provenance},
tokens::{DepositConsequence, Fortitude, Precision as WithdrawalPrecision, Preservation, Provenance},
AccountTouch,
},
Hashable, Parameter,
Expand Down Expand Up @@ -315,6 +315,8 @@ pub mod pallet {
Slippage,
/// The calculated collateral is zero.
ZeroCollateral,
/// A pool has to contain at least one bonded currency.
ZeroBondedCurrency,
}

#[pallet::call]
Expand Down Expand Up @@ -372,6 +374,7 @@ pub mod pallet {
let checked_curve = curve.try_into().map_err(|_| Error::<T>::InvalidInput)?;

let currency_length = currencies.len();
ensure!(!currency_length.is_zero(), Error::<T>::ZeroBondedCurrency);

let currency_ids = T::NextAssetIds::try_get(currency_length.saturated_into())
.map_err(|e| e.into())
Expand Down Expand Up @@ -446,18 +449,17 @@ pub mod pallet {
Ok(())
}

/// Changes the managing team of a bonded currency which is issued by
/// this pool. The new team will be set to the provided team. The
/// currency index is used to select the currency that the team will
/// manage. The origin account must be a manager of the pool.
/// Changes the managing team of all bonded currencies issued by this
/// pool, setting it to the provided `team`. The origin account must be
/// a manager of the pool.
///
/// # Parameters
/// - `origin`: The origin of the call, requiring the caller to be a
/// manager of the pool.
/// - `pool_id`: The identifier of the pool.
/// - `team`: The new managing team.
/// - `currency_idx`: The index of the currency in the bonded currencies
/// vector.
/// - `currency_count`: The number of bonded currencies vector linked to
/// the pool. Required for weight estimations.
///
/// # Returns
/// - `DispatchResult`: The result of the dispatch.
Expand All @@ -466,40 +468,40 @@ pub mod pallet {
/// - `Error::<T>::PoolUnknown`: If the pool does not exist.
/// - `Error::<T>::NoPermission`: If the caller is not a manager of the
/// pool.
/// - `Error::<T>::IndexOutOfBounds`: If the currency index is out of
/// bounds.
/// - `Error::<T>::CurrencyCount`: If the actual number of currencies in
/// the pool is larger than `currency_count`.
/// - Other errors depending on the types in the config.
#[pallet::call_index(1)]
#[pallet::weight(T::WeightInfo::reset_team())]
pub fn reset_team(
origin: OriginFor<T>,
pool_id: T::PoolId,
team: PoolManagingTeam<AccountIdOf<T>>,
currency_idx: u32,
currency_count: u32,
) -> DispatchResult {
let who = T::DefaultOrigin::ensure_origin(origin)?;

let pool_details = Pools::<T>::get(&pool_id).ok_or(Error::<T>::PoolUnknown)?;

let number_of_currencies = Self::get_currencies_number(&pool_details);
ensure!(number_of_currencies <= currency_count, Error::<T>::CurrencyCount);

ensure!(pool_details.is_manager(&who), Error::<T>::NoPermission);
ensure!(pool_details.state.is_live(), Error::<T>::PoolNotLive);

let asset_id = pool_details
.bonded_currencies
.get(currency_idx.saturated_into::<usize>())
.ok_or(Error::<T>::IndexOutOfBounds)?;

let pool_id_account = pool_id.into();

let PoolManagingTeam { freezer, admin } = team;

T::Fungibles::reset_team(
asset_id.to_owned(),
pool_id_account.clone(),
admin,
pool_id_account,
freezer,
)
pool_details.bonded_currencies.into_iter().try_for_each(|asset_id| {
T::Fungibles::reset_team(
asset_id,
pool_id_account.clone(),
admin.clone(),
pool_id_account.clone(),
freezer.clone(),
)
})
}

/// Resets the manager of a pool. The new manager will be set to the
Expand Down Expand Up @@ -1116,8 +1118,7 @@ pub mod pallet {

if amount.is_zero()
|| T::Collaterals::can_deposit(pool_details.collateral.clone(), &who, amount, Provenance::Extant)
.into_result()
.is_err()
== DepositConsequence::BelowMinimum
{
// Funds are burnt but the collateral received is not sufficient to be deposited
// to the account. This is tolerated as otherwise we could have edge cases where
Expand Down Expand Up @@ -1427,8 +1428,10 @@ pub mod pallet {
Error::<T>::NothingToRefund
);

let has_holders = pool_details
.bonded_currencies
// cloning here lets us avoid cloning the pool details later
let bonded_currencies = pool_details.bonded_currencies.clone();

let has_holders = bonded_currencies
.iter()
.any(|asset_id| T::Fungibles::total_issuance(asset_id.clone()) > FungiblesBalanceOf::<T>::zero());
// no token holders to refund
Expand All @@ -1439,6 +1442,18 @@ pub mod pallet {
new_pool_details.state.start_refund();
Pools::<T>::set(&pool_id, Some(new_pool_details));

// reset team on currencies to avoid unexpected burns etc.
let pool_account = pool_id.clone().into();
for asset_id in bonded_currencies {
T::Fungibles::reset_team(
asset_id,
pool_account.clone(),
pool_account.clone(),
pool_account.clone(),
pool_account.clone(),
)?;
}

Self::deposit_event(Event::RefundingStarted { id: pool_id });

Ok(n_currencies)
Expand Down
39 changes: 36 additions & 3 deletions pallets/pallet-bonded-coins/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ pub mod runtime {
weights::constants::RocksDbWeight,
};
use frame_system::{EnsureRoot, EnsureSigned};
use pallet_assets::FrozenBalance;
use sp_core::U256;
use sp_runtime::{
traits::{BlakeTwo256, IdentifyAccount, IdentityLookup, Verify},
Expand All @@ -69,7 +70,7 @@ pub mod runtime {
self as pallet_bonded_coins,
traits::NextAssetIds,
types::{Locks, PoolStatus},
Config, DepositBalanceOf, FungiblesAssetIdOf, PoolDetailsOf,
AccountIdOf, Config, DepositBalanceOf, FungiblesAssetIdOf, FungiblesBalanceOf, PoolDetailsOf,
};

pub type Hash = sp_core::H256;
Expand Down Expand Up @@ -190,6 +191,28 @@ pub mod runtime {
}
}

/// Store freezes for the assets pallet.
#[storage_alias]
pub type Freezes<Assets: PalletInfoAccess> = StorageDoubleMap<
Assets,
Blake2_128Concat,
FungiblesAssetIdOf<Test>,
Blake2_128Concat,
AccountIdOf<Test>,
FungiblesBalanceOf<Test>,
OptionQuery,
>;

pub struct FreezesHook;

impl FrozenBalance<AssetId, AccountId, Balance> for FreezesHook {
fn died(_asset: AssetId, _who: &AccountId) {}

fn frozen_balance(asset: AssetId, who: &AccountId) -> Option<Balance> {
Freezes::<Assets>::get(asset, who)
}
}

frame_support::construct_runtime!(
pub enum Test
{
Expand Down Expand Up @@ -226,7 +249,7 @@ pub mod runtime {
type Hash = Hash;
type Hashing = BlakeTwo256;
type Lookup = IdentityLookup<Self::AccountId>;
type MaxConsumers = ConstU32<16>;
type MaxConsumers = ConstU32<100>;
type Nonce = u64;
type OnKilledAccount = ();
type OnNewAccount = ();
Expand Down Expand Up @@ -279,7 +302,7 @@ pub mod runtime {
type Currency = Balances;
type Extra = ();
type ForceOrigin = EnsureRoot<AccountId>;
type Freezer = ();
type Freezer = FreezesHook;
type MetadataDepositBase = ConstU128<0>;
type MetadataDepositPerByte = ConstU128<0>;
type RemoveItemsLimit = ConstU32<5>;
Expand Down Expand Up @@ -355,6 +378,7 @@ pub mod runtime {
// pool_id, PoolDetails
pools: Vec<(AccountId, PoolDetailsOf<Test>)>,
collaterals: Vec<AssetId>,
freezes: Vec<(AssetId, AccountId, Balance)>,
}

impl ExtBuilder {
Expand All @@ -378,6 +402,11 @@ pub mod runtime {
self
}

pub(crate) fn with_freezes(mut self, freezes: Vec<(AssetId, AccountId, Balance)>) -> Self {
self.freezes = freezes;
self
}

pub(crate) fn build(self) -> sp_io::TestExternalities {
let mut storage = frame_system::GenesisConfig::<Test>::default().build_storage().unwrap();

Expand Down Expand Up @@ -448,6 +477,10 @@ pub mod runtime {
});

NextAssetId::<BondingPallet>::set(next_asset_id);

self.freezes.iter().for_each(|(asset_id, account, amount)| {
Freezes::<Assets>::set(asset_id, account, Some(*amount));
});
});

ext
Expand Down
Loading