当前位置:网站首页>波卡跨链通信源码探秘: 要素篇
波卡跨链通信源码探秘: 要素篇
2022-06-30 12:23:00 【InfoQ】
- 互操作性强
- 优异的可扩展性
- 超强的普适性
- 异构跨链具备强一致性
- 独有的共享安全机制, 安全性好
- 通信的参与对象
- 通信过程中传递的内容
- 通信过程如何实施, 即通信协议
波卡跨链的参与对象
- 区块链
- 智能合约
- 转接桥
- 甚至pallets.
波卡跨链传递的内容
XCM
Cross-Consensus Message Format
跨共识消息格式
Xcm<Call>
enum
#[scale_info(bounds(), skip_type_params(Call))]
pub enum Xcm<Call> {
//...snippets
WithdrawAsset(MultiAssets),
ReserveAssetDeposited(MultiAssets),
ReceiveTeleportedAsset(MultiAssets),
//...snippets
}
Tuple Struct
#[scale_info(bounds(), skip_type_params(Call))]
pub struct Xcm<Call>(pub Vec<Instruction<Call>>);
Instruction<Call>
enum
//....snippets
#[scale_info(bounds(), skip_type_params(Call))]
pub enum Instruction<Call> {
WithdrawAsset(MultiAssets),
ReserveAssetDeposited(MultiAssets),
ReceiveTeleportedAsset(MultiAssets),
//....snippets
}
enum
Instruction<Call>
Instruction<Call>
Instruction<Call>
WithdrawAsset
origin
Instruction<Call>
XCVM
xcm-executor
XcmExecuteor
pub struct XcmExecutor<Config: config::Config> {
pub holding: Assets,
pub origin: Option<MultiLocation>,
pub original_origin: MultiLocation,
pub trader: Config::Trader,
/// The most recent error result and instruction index into the fragment in which it occurred,
/// if any.
pub error: Option<(u32, XcmError)>,
/// The surplus weight, defined as the amount by which `max_weight` is
/// an over-estimate of the actual weight consumed. We do it this way to avoid needing the
/// execution engine to keep track of all instructions' weights (it only needs to care about
/// the weight of dynamically determined instructions such as `Transact`).
pub total_surplus: u64,
pub total_refunded: u64,
pub error_handler: Xcm<Config::Call>,
pub error_handler_weight: u64,
pub appendix: Xcm<Config::Call>,
pub appendix_weight: u64,
_config: PhantomData<Config>,
}
XcmExcutor
execute
impl<Config: config::Config> XcmExecutor<Config> {
//...snippets
pub fn execute(&mut self, xcm: Xcm<Config::Call>) -> Result<(), ExecutorError> {
//...snippets
if let Err(e) = self.process_instruction(instr) {
*r = Err(ExecutorError { index: i as u32, xcm_error: e, weight: 0 });
},
//...snippets
}
execute
process_instruction
process_instruction
fn process_instruction(&mut self, instr: Instruction<Config::Call>) -> Result<(), XcmError> {
match instr {
//...snippets
TransferReserveAsset { mut assets, dest, xcm } => {
let origin = self.origin.as_ref().ok_or(XcmError::BadOrigin)?;
// Take `assets` from the origin account (on-chain) and place into dest account.
for asset in assets.inner() {
Config::AssetTransactor::beam_asset(asset, origin, &dest)?;
}
let ancestry = Config::LocationInverter::ancestry();
assets.reanchor(&dest, &ancestry).map_err(|()| XcmError::MultiLocationFull)?;
let mut message = vec![ReserveAssetDeposited(assets), ClearOrigin];
message.extend(xcm.0.into_iter());
Config::XcmSender::send_xcm(dest, Xcm(message)).map_err(Into::into)
}
//...snippets
}
//...snippets
},
波卡跨链的通信协议
- XCMP, 全称 Cross-Chain Message Passing, 即跨链消息协议, 该协议使用Merkle 树来确保通信安全验证, 并基于此有一个简单的排队系统; 在XCMP协议执行过程中, 中继链仅仅将跨链交易相关元数据(metadata)以哈希的形式储存, 因此占用的资源和执行效率极高. XCMP有两种形式:
- 直接通信,xcm消息数据在平行链之间直接传输, 对于中继链来说仅仅可以只有一个“知会”的动作, 这种方式可扩展性极高, 目前还在开发之中.
- 中继通信,即通过中继链来传递, 具体的就是通过VMP来实现, VMP的详细见下文.
- XCMP-Lite, 即HRMP(Horizontal Relay-routed Message Passing 水平中继路由消息传递协议). 由于XCMP中平行链直接通信的模式还在开发中, 因此目前在Polkadot和Kusama中继链上, 使用的是HRMP作为现阶段的过渡.从以上可以看出, HRMP的消息传递中, 数据是直接以Vec
- HRMP与XCMP使用相同的接口和功能, 但最大的区别在于HRMP将所有消息内容都储存在中继链中, 因此占用的资源和执行效率远远不如XCMP. 以下是 HRMP源码中的2个消息结构体代码, 同样为了便于理解, 这里做了精简处理:
pub struct InboundHrmpMessage<BlockNumber = crate::BlockNumber> {
pub sent_at: BlockNumber,
pub data: sp_std::vec::Vec<u8>,
}
pub struct OutboundHrmpMessage<Id> {
pub recipient: Id,
pub data: sp_std::vec::Vec<u8>,
}
这种近似“明文”的方式存储全部消息数据的.
- VMP (Vertical Message Passing 垂直消息传递协议) ,VMP其实是一个统称, 用来与HRMP的“水平”相对照; HRMP的H 即“Horizontal 水平”, 是指平行链与平行链之间的沟通; 而VMP的V即“Vertical垂直”则主要指中继链和平行链之间的通讯, VMP包含2个协议:
- UMP (Upward Message Passing 上行消息传递协议): 由平行链往中继链传递消息, 称为“向上传递”, 由于各个平行链向中继链发送的消息的内容可能千差万别, 因此
UMP
模块主要提供了一个名为UmpSink
的trait
来统一约束. 使用trait来统一约束的好处, 是尽量给予各个平行链灵活自由.
pub trait UmpSink {
fn process_upward_message(
origin: ParaId,
msg: &[u8],
max_weight: Weight,
) -> Result<Weight, (MessageId, Weight)>;
}
impl UmpSink for () {
fn process_upward_message(
_: ParaId,
_: &[u8],
_: Weight,
) -> Result<Weight, (MessageId, Weight)> {
Ok(0)
}
}
- **DMP (Downward Message Passing 下行消息传递协议**) : 由中继链向平行链传递消息, 称为“向下传递”; 这个就可以相对地统一格式, 因此源码中定义了一个`DownwardMessage`类型, 本质是一个`Vec<u8>`类型, 并用`InboundDownwardMessage`结构体包裹起来, 以便放入队列中去处理
pub type DownwardMessage = sp_std::vec::Vec<u8>;
#[derive(Encode, Decode, Clone, sp_runtime::RuntimeDebug, PartialEq, TypeInfo)]
#[cfg_attr(feature = "std", derive(MallocSizeOf))]
pub struct InboundDownwardMessage<BlockNumber = crate::BlockNumber> {
pub sent_at: BlockNumber,
pub msg: DownwardMessage,
}
总结
参考资料
- https://wiki.polkadot.network/docs/learn-crosschain
- https://research.web3.foundation/en/latest/polkadot/XCMP/index.html
- https://cointelegraphcn.com/news/is-cosmos-and-polkadots-cross-chain-the-same-thing ?????
- https://medium.com/polkadot-network/xcm-the-cross-consensus-message-format-3b77b1373392
- https://github.com/paritytech/xcm-format
边栏推荐
- Shell基础入门
- Substrate 源码追新导读: 质押额度大幅度削减, RocksDB可以完全被Disable
- kubeedge的核心理念
- Sublist3r error reporting solution
- JMeter性能测试之相关术语及性能测试通过标准
- 黑马笔记---集合(Collection的常用方法与遍历方式)
- Discussion on JMeter operation principle
- 项目中遇到一个有趣的事情
- "Xiaodeng" user personal data management in operation and maintenance
- Tencent two sides: @bean and @component are used on the same class. What happens?
猜你喜欢
Qt读写Excel--QXlsx工作表显示/隐藏状态设置4
[300+ continuous sharing of selected interview questions from large manufacturers] column on interview questions of big data operation and maintenance (II)
独立站即web3.0,国家“十四五“规划要求企业建数字化网站!
电机控制park变换公式推导
Why should offline stores do new retail?
Reading the table data of Tencent documents in the applet
【MySQL】MySQL的安装与配置
Visual studio configures QT and implements project packaging through NSIS
FlinkSQL自定义UDATF实现TopN
Dark horse notes - collection (common methods and traversal methods of collection)
随机推荐
浅谈 JMeter 运行原理
JMeter性能测试之相关术语及性能测试通过标准
ffmpeg 杂项
MySQL判断执行条件为NULL时,返回0,出错问题解决 Incorrect parameter count in the call to native function ‘ISNULL‘,
SQLSERVER 查询编码是 936 简体中文GBK,那我是写936 还是写GBK?
MySql实现两个查询结果相除
Redis cache problem
Google refutes rumors and gives up tensorflow. It's still alive!
解决numpy.core._exceptions.UFuncTypeError: ufunc ‘add‘ did not contain a loop with signature matchin问题
全面解析免费及收费SSH工具的基本特性和总结
你想要的异常知识点都在这里了
SuperMap 3D SDKs_ Unity plug-in development - connect data services for SQL queries
Wechat launched the picture big bang function; Apple's self-developed 5g chip may have failed; Microsoft solves the bug that causes edge to stop responding | geek headlines
"Xiaodeng" user personal data management in operation and maintenance
Questionnaire star questionnaire packet capturing analysis
如何利用AI技术优化独立站客服系统?听听专家怎么说!
Unity脚本的基础语法(3)-访问游戏对象组件
Discussion on JMeter operation principle
黑马笔记---常用日期API
【 surprise】 la vitesse de téléchargement de Thunderbolt n'est pas aussi rapide que celle de la machine virtuelle