Bytom 交易验证流程

交易映射

交易验证时需要首先将inputs、outputs描述的TxData转换成Entriy描述的的bc.Tx。
Entry 是区块链中很多组件都实现的一个接口。比如交易中实现了此接口的组件包括Spend,Issuance,Coinbase,
Output,Retirement,TxHeader 等。验证前需要将TxData中的元素转换成对应的Entry组件,
实现相同接口后方便对各个部分进行统一验证。

1
2
3
4
5
6
7
8
// TxData encodes a transaction in the blockchain.
type TxData struct {
Version uint64
SerializedSize uint64
TimeRange uint64
Inputs []*TxInput
Outputs []*TxOutput
}
1
2
3
4
5
6
7
8
9
//验证交易结构
type Tx struct {
*TxHeader //header 指针
ID Hash //header entryID
Entries map[Hash]Entry //交易组件对应的entries
InputIDs []Hash // TxData.Inputs的 entryID
SpentOutputIDs []Hash //SpendInput的Output entryID
GasInputIDs []Hash //btm spend 和 coinbase 的entryID
}

对于inputs
IssuanceInput 转化成 bc.Issuance。
SpendInput 转换成两个组件一个bc.Output,一个bc.Spend。
CoinbaseInput 转化成 bc.Coinbase。

对于outpus
TxOutput根据ControlProgram是否可以spend被转换为Retirement(不可花费)和Output(可花费)。

每个交易还会添加一个TxHeader 和 一个 Mux。TxHeader中的ResultIds记录了所有交易输出组件的entryID,
是交易验证的入口。Mux用来连接输入和输出。
具体映射关系如下图:

交易转换及验证图

交易验证

从header开始,沿着上面的图从右侧向左对各组件进行依次验证,每一种组件有单独的验证规则,具体验证规则见上图。

由于各组件都实现了Entry接口,所以可以使用同一个函数对所有的组件进行验证。

1
2
验证各组件的函数入口
func checkValid(vs *validationState, e bc.Entry) (err error)