xcm_docs/fundamentals.rs
1// Copyright (C) Parity Technologies (UK) Ltd.
2// SPDX-License-Identifier: GPL-3.0-or-later WITH Classpath-exception-2.0
3// This file is part of Polkadot.
4
5// Polkadot is free software: you can redistribute it and/or modify
6// it under the terms of the GNU General Public License as published by
7// the Free Software Foundation, either version 3 of the License, or
8// (at your option) any later version.
9
10// Polkadot is distributed in the hope that it will be useful,
11// but WITHOUT ANY WARRANTY; without even the implied warranty of
12// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13// GNU General Public License for more details.
14
15// You should have received a copy of the GNU General Public License
16// along with Polkadot. If not, see <http://www.gnu.org/licenses/>.
17
18//! # XCM Fundamentals
19//!
20//! XCM standardizes usual actions users take in consensus systems, for example
21//! dealing with assets locally, on other chains, and locking them.
22//! XCM programs can both be executed locally or sent to a different consensus system.
23//! Examples of consensus systems are blockchains and smart contracts.
24//!
25//! The goal of XCM is to allow multi-chain ecosystems to thrive via specialization.
26//! Very specific functionalities can be abstracted away and standardized in this common language.
27//! Then, every member of the ecosystem can implement the subset of the language that makes sense
28//! for them.
29//!
30//! The language evolves over time to accomodate the needs of the community
31//! via the [RFC process](https://github.com/paritytech/xcm-format/blob/master/proposals/0032-process.md).
32//!
33//! XCM is the language, it deals with interpreting and executing programs.
34//! It does not deal with actually **sending** these programs from one consensus system to another.
35//! This responsibility falls to a transport protocol.
36//! XCM can even be interpreted on the local system, with no need of a transport protocol.
37//! However, automatic and composable workflows can be achieved via the use of one.
38//!
39//! At the core of XCM lies the XCVM, the Cross-Consensus Virtual Machine.
40//! It's the virtual machine that executes XCM programs.
41//! It is a specification that comes with the language.
42//!
43//! For these docs, we'll use a Rust implementation of XCM and the XCVM, consisting of the following
44//! parts:
45//! - [`XCM`](xcm): Holds the definition of an XCM program, the instructions and main concepts.
46//! - [`Executor`](xcm_executor): Implements the XCVM, capable of executing XCMs. Highly
47//! configurable.
48//! - [`Builder`](xcm_builder): A collection of types used to configure the executor.
49//! - [`XCM Pallet`](pallet_xcm): A FRAME pallet for interacting with the executor.
50//! - [`Simulator`](xcm_simulator): A playground to tinker with different XCM programs and executor
51//! configurations.
52//!
53//! XCM programs are composed of Instructions, which reference Locations and Assets.
54//!
55//! ## Locations
56//!
57//! Locations are XCM's vocabulary of places we want to talk about in our XCM programs.
58//! They are used to reference things like 32-byte accounts, governance bodies, smart contracts,
59//! blockchains and more.
60//!
61//! Locations are hierarchical.
62//! This means some places in consensus are wholly encapsulated in other places.
63//! Say we have two systems A and B.
64//! If any change in A's state implies a change in B's state, then we say A is interior to B.
65#![doc = simple_mermaid::mermaid!("../mermaid/location_hierarchy.mmd")]
66//! Parachains are interior to their Relay Chain, since a change in their state implies a change in
67//! the Relay Chain's state.
68//!
69//! Because of this hierarchy, the way we represent locations is with both a number of **parents**,
70//! times we move __up__ the hierarchy, and a sequence of **junctions**, the steps we take __down__
71//! the hierarchy after going up the specified number of parents.
72//!
73//! In Rust, this is specified with the following datatype:
74//! ```ignore
75//! pub struct Location {
76//! parents: u8,
77//! interior: Junctions,
78//! }
79//! ```
80//!
81//! Many junctions are available; parachains, pallets, 32 and 20 byte accounts, governance bodies,
82//! and arbitrary indices are the most common.
83//! A full list of available junctions can be found in the [format](https://github.com/paritytech/xcm-format#interior-locations--junctions)
84//! and [Junction enum](xcm::v4::prelude::Junction).
85//!
86//! We'll use a file system notation to represent locations, and start with relative locations.
87//! In the diagram, the location of parachain 1000 as seen from all other locations is as follows:
88//! - From the relaychain: `Parachain(1000)`
89//! - From parachain 1000 itself: `Here`
90//! - From parachain 2000: `../Parachain(1000)`
91//!
92//! Relative locations are interpreted by the system that is executing an XCM program, which is the
93//! receiver of a message in the case where it's sent.
94//!
95//! Locations can also be absolute.
96//! Keeping in line with our filesystem analogy, we can imagine the root of our filesystem to exist.
97//! This would be a location with no parents, that is also the parent of all systems that derive
98//! their own consensus, say Polkadot or Ethereum or Bitcoin.
99//! Such a location does not exist concretely, but we can still use this definition for it.
100//! This is the **universal location**.
101//! We need the universal location to be able to describe locations in an absolute way.
102#![doc = simple_mermaid::mermaid!("../mermaid/universal_location.mmd")]
103//! Here, the absolute location of parachain 1000 would be
104//! `GlobalConsensus(Polkadot)/Parachain(1000)`.
105//!
106//! ## Assets
107//!
108//! We want to be able to reference assets in our XCM programs, if only to be able to pay for fees.
109//! Assets are represented using locations.
110//!
111//! The native asset of a chain is represented by the location of that chain.
112//! For example, DOT is represented by the location of the Polkadot relaychain.
113//! If the interpreting chain has its own asset, it would be represented by `Here`.
114//!
115//! How do we represent other assets?
116//! The asset hub system parachain in Polkadot, for example, holds a lot of assets.
117//! To represent each of them, it uses the indices we mentioned, and it makes them interior to the
118//! assets pallet instance it uses.
119//! USDT, an example asset that lives on asset hub, is identified by the location
120//! `Parachain(1000)/PalletInstance(53)/GeneralIndex(1984)`, when seen from the Polkadot relaychain.
121#![doc = simple_mermaid::mermaid!("../mermaid/usdt_location.mmd")]
122//! Asset Hub also has another type of assets called `ForeignAssets`.
123//! These assets are identified by the XCM Location to their origin.
124//! Two such assets are a Parachain asset, like Moonbeam's GLMR, and KSM, from the cousin Kusama
125//! network. These are represented as `../Parachain(2004)/PalletInstance(10)` and
126//! `../../GlobalConsensus(Kusama)` respectively.
127//!
128//! The whole type can be seen in the [format](https://github.com/paritytech/xcm-format#6-universal-asset-identifiers)
129//! and [rust docs](xcm::v4::prelude::Asset).
130//!
131//! ## Instructions
132//!
133//! Given the vocabulary to talk about both locations -- chains and accounts -- and assets, we now
134//! need a way to express what we want the consensus system to do when executing our programs.
135//! We need a way of writing our programs.
136//!
137//! XCM programs are composed of a sequence of instructions.
138//!
139//! All available instructions can be seen in the [format](https://github.com/paritytech/xcm-format#5-the-xcvm-instruction-set)
140//! and the [Instruction enum](xcm::v4::prelude::Instruction).
141//!
142//! A very simple example is the following:
143//!
144//! ```ignore
145//! let message = Xcm(vec![
146//! TransferAsset { assets, beneficiary },
147//! ]);
148//! ```
149//!
150//! This instruction is enough to transfer `assets` from the account of the **origin** of a message
151//! to the `beneficiary` account. However, because of XCM's generality, fees need to be paid
152//! explicitly. This next example sheds more light on this:
153//!
154//! ```ignore
155//! let message = Xcm(vec![
156//! WithdrawAsset(assets),
157//! BuyExecution { fees: assets, weight_limit },
158//! DepositAsset { assets: AssetFilter(Wild(All)), beneficiary },
159//! ]);
160//! ```
161//!
162//! Here we see the process of transferring assets was broken down into smaller instructions, and we
163//! add the explicit fee payment step in the middle.
164//! `WithdrawAsset` withdraws assets from the account of the **origin** of the message for usage
165//! inside this message's execution. `BuyExecution` explicitly buys execution for this program using
166//! the assets specified in `fees`, with a sanity check of `weight_limit`. `DepositAsset` uses a
167//! wildcard, specifying all remaining `assets` after subtracting the fees and a `beneficiary`
168//! account.
169//!
170//! ## Next steps
171//!
172//! Continue with the [guides](crate::guides) for step-by-step tutorials on XCM,
173//! or jump to the [cookbook](crate::cookbook) to see examples.
174//!
175//! The [glossary](crate::glossary) can be useful if some of the terms are confusing.