Transactional processing for XCM (#1222)

Moved from: https://github.com/paritytech/polkadot/pull/6951

closes https://github.com/paritytech/polkadot-sdk/issues/490

- [x] update cumulus

--- 
This PR introduces transactional processing of certain xcm instructions.
For the list of instructions checkout
https://github.com/paritytech/polkadot-sdk/issues/490. The transactional
processing is implemented as an xcm-executor config item. The two
implementations in this PR are `FrameTransactionalProcessor` and `()`.
The `()` implementation does no transactional processing. Each
implementation of the `ProcessTransaction` trait has an
`IS_TRANSACTIONAL` const that tells the XCVM if transactional processing
is actually implemented. If Transactional processing is implemented,
changes to touched registers should also be rolled back to prevent
inconsistencies.


Note for reviewers:
Check out the following safety assumption:
https://github.com/paritytech/polkadot-sdk/pull/1222/files#diff-4effad7d8c1c9de19fd27e18661cbf2128c8718f3b2420a27d2f816e0749ea53R30

---------

Co-authored-by: Keith Yeung <kungfukeith11@gmail.com>
Co-authored-by: Francisco Aguirre <franciscoaguirreperez@gmail.com>
Co-authored-by: command-bot <>
This commit is contained in:
Just van Stam
2024-01-24 17:30:27 +01:00
committed by GitHub
parent a78ff7d770
commit 50eb12cf2f
54 changed files with 675 additions and 295 deletions
+45 -42
View File
@@ -26,26 +26,6 @@ mod tests;
#[cfg(feature = "std")]
pub mod test_utils;
mod location_conversion;
#[allow(deprecated)]
pub use location_conversion::ForeignChainAliasAccount;
pub use location_conversion::{
Account32Hash, AccountId32Aliases, AccountKey20Aliases, AliasesIntoAccountId32,
ChildParachainConvertsVia, DescribeAccountId32Terminal, DescribeAccountIdTerminal,
DescribeAccountKey20Terminal, DescribeAllTerminal, DescribeBodyTerminal, DescribeFamily,
DescribeLocation, DescribePalletTerminal, DescribeTerminus, DescribeTreasuryVoiceTerminal,
GlobalConsensusConvertsFor, GlobalConsensusParachainConvertsFor, HashedDescription,
LocalTreasuryVoiceConvertsVia, ParentIsPreset, SiblingParachainConvertsVia,
};
mod origin_conversion;
pub use origin_conversion::{
BackingToPlurality, ChildParachainAsNative, ChildSystemParachainAsSuperuser, EnsureXcmOrigin,
OriginToPluralityVoice, ParentAsSuperuser, RelayChainAsNative, SiblingParachainAsNative,
SiblingSystemParachainAsSuperuser, SignedAccountId32AsNative, SignedAccountKey20AsNative,
SignedToAccountId32, SovereignSignedViaLocation,
};
mod asset_conversion;
#[allow(deprecated)]
pub use asset_conversion::ConvertedConcreteAssetId;
@@ -61,8 +41,11 @@ pub use barriers::{
WithComputedOrigin,
};
mod process_xcm_message;
pub use process_xcm_message::ProcessXcmMessage;
mod controller;
pub use controller::{
Controller, ExecuteController, ExecuteControllerWeightInfo, QueryController,
QueryControllerWeightInfo, QueryHandler, SendController, SendControllerWeightInfo,
};
mod currency_adapter;
#[allow(deprecated)]
@@ -73,6 +56,9 @@ pub use fee_handling::{
deposit_or_burn_fee, HandleFee, XcmFeeManagerFromComponents, XcmFeeToAccount,
};
mod filter_asset_location;
pub use filter_asset_location::{AllAssets, Case, LocationWithAssetFilters, NativeAsset};
mod fungible_adapter;
pub use fungible_adapter::{FungibleAdapter, FungibleMutateAdapter, FungibleTransferAdapter};
@@ -82,14 +68,16 @@ pub use fungibles_adapter::{
LocalMint, MintLocation, NoChecking, NonLocalMint,
};
mod nonfungibles_adapter;
pub use nonfungibles_adapter::{
NonFungiblesAdapter, NonFungiblesMutateAdapter, NonFungiblesTransferAdapter,
};
mod weight;
pub use weight::{
FixedRateOfFungible, FixedWeightBounds, TakeRevenue, UsingComponents, WeightInfoBounds,
mod location_conversion;
#[allow(deprecated)]
pub use location_conversion::ForeignChainAliasAccount;
pub use location_conversion::{
Account32Hash, AccountId32Aliases, AccountKey20Aliases, AliasesIntoAccountId32,
ChildParachainConvertsVia, DescribeAccountId32Terminal, DescribeAccountIdTerminal,
DescribeAccountKey20Terminal, DescribeAllTerminal, DescribeBodyTerminal, DescribeFamily,
DescribeLocation, DescribePalletTerminal, DescribeTerminus, DescribeTreasuryVoiceTerminal,
GlobalConsensusConvertsFor, GlobalConsensusParachainConvertsFor, HashedDescription,
LocalTreasuryVoiceConvertsVia, ParentIsPreset, SiblingParachainConvertsVia,
};
mod matches_location;
@@ -101,12 +89,34 @@ pub use matches_token::IsConcrete;
mod matcher;
pub use matcher::{CreateMatcher, MatchXcm, Matcher};
mod filter_asset_location;
pub use filter_asset_location::{AllAssets, Case, LocationWithAssetFilters, NativeAsset};
mod nonfungibles_adapter;
pub use nonfungibles_adapter::{
NonFungiblesAdapter, NonFungiblesMutateAdapter, NonFungiblesTransferAdapter,
};
mod origin_aliases;
pub use origin_aliases::AliasForeignAccountId32;
mod origin_conversion;
pub use origin_conversion::{
BackingToPlurality, ChildParachainAsNative, ChildSystemParachainAsSuperuser, EnsureXcmOrigin,
OriginToPluralityVoice, ParentAsSuperuser, RelayChainAsNative, SiblingParachainAsNative,
SiblingSystemParachainAsSuperuser, SignedAccountId32AsNative, SignedAccountKey20AsNative,
SignedToAccountId32, SovereignSignedViaLocation,
};
mod pay;
pub use pay::{FixedLocation, LocatableAssetId, PayAccountId32OnChainOverXcm, PayOverXcm};
mod process_xcm_message;
pub use process_xcm_message::ProcessXcmMessage;
mod routing;
pub use routing::{WithTopicSource, WithUniqueTopic};
mod transactional;
pub use transactional::FrameTransactionalProcessor;
mod universal_exports;
pub use universal_exports::{
ensure_is_remote, BridgeBlobDispatcher, BridgeMessage, DispatchBlob, DispatchBlobError,
@@ -114,14 +124,7 @@ pub use universal_exports::{
NetworkExportTableItem, SovereignPaidRemoteExporter, UnpaidLocalExporter, UnpaidRemoteExporter,
};
mod origin_aliases;
pub use origin_aliases::AliasForeignAccountId32;
mod pay;
pub use pay::{FixedLocation, LocatableAssetId, PayAccountId32OnChainOverXcm, PayOverXcm};
mod controller;
pub use controller::{
Controller, ExecuteController, ExecuteControllerWeightInfo, QueryController,
QueryControllerWeightInfo, QueryHandler, SendController, SendControllerWeightInfo,
mod weight;
pub use weight::{
FixedRateOfFungible, FixedWeightBounds, TakeRevenue, UsingComponents, WeightInfoBounds,
};
@@ -742,6 +742,7 @@ impl Config for TestConfig {
type CallDispatcher = TestCall;
type SafeCallFilter = Everything;
type Aliasers = AliasForeignAccountId32<SiblingPrefix>;
type TransactionalProcessor = ();
}
pub fn fungible_multi_asset(location: Location, amount: u128) -> Asset {
@@ -175,6 +175,7 @@ type OriginConverter = (
);
type Barrier = AllowUnpaidExecutionFrom<Everything>;
#[derive(Clone)]
pub struct DummyWeightTrader;
impl WeightTrader for DummyWeightTrader {
fn new() -> Self {
@@ -217,6 +218,7 @@ impl xcm_executor::Config for XcmConfig {
type CallDispatcher = RuntimeCall;
type SafeCallFilter = Everything;
type Aliasers = Nothing;
type TransactionalProcessor = ();
}
parameter_types! {
@@ -0,0 +1,40 @@
// Copyright 2021 Parity Technologies (UK) Ltd.
// This file is part of Polkadot.
// Polkadot is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// Polkadot is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with Polkadot. If not, see <http://www.gnu.org/licenses/>.
use frame_support::storage::{with_transaction, TransactionOutcome};
use sp_runtime::DispatchError;
use xcm::latest::prelude::*;
use xcm_executor::traits::ProcessTransaction;
/// Transactional processor implementation using frame transactional layers.
pub struct FrameTransactionalProcessor;
impl ProcessTransaction for FrameTransactionalProcessor {
const IS_TRANSACTIONAL: bool = true;
fn process<F>(f: F) -> Result<(), XcmError>
where
F: FnOnce() -> Result<(), XcmError>,
{
with_transaction(|| -> TransactionOutcome<Result<_, DispatchError>> {
let output = f();
match &output {
Ok(()) => TransactionOutcome::Commit(Ok(output)),
_ => TransactionOutcome::Rollback(Ok(output)),
}
})
.map_err(|_| XcmError::ExceedsStackLimit)?
}
}
+2 -1
View File
@@ -232,12 +232,13 @@ impl<
}
fn refund_weight(&mut self, weight: Weight, context: &XcmContext) -> Option<Asset> {
log::trace!(target: "xcm::weight", "UsingComponents::refund_weight weight: {:?}, context: {:?}", weight, context);
log::trace!(target: "xcm::weight", "UsingComponents::refund_weight weight: {:?}, context: {:?}, available weight: {:?}, available amount: {:?}", weight, context, self.0, self.1);
let weight = weight.min(self.0);
let amount = WeightToFee::weight_to_fee(&weight);
self.0 -= weight;
self.1 = self.1.saturating_sub(amount);
let amount: u128 = amount.saturated_into();
log::trace!(target: "xcm::weight", "UsingComponents::refund_weight amount to refund: {:?}", amount);
if amount > 0 {
Some((AssetIdValue::get(), amount).into())
} else {