注:纯粹是自己的记录,没有任何参考价值
面对着不知所云的比特币源码,我尝试着采用逐字阅读的笨办法来解读。同时也参考菜菜子的文章还有网上搜索来的解读。
本次选取的是merkle.h,面对浩瀚的程序,我选择挨个打开,当看到merkle.h时,有一种熟悉感,因为区块头里面有Merkle树的根值,那就从它开始了。
// Copyright (c) 2015 The Bitcoin Core developers
// Distributed under the MIT software license, see the accompanying
//file COPYING orhttp://www.opensource.org/licenses/mit-license.php.
一般每段程序前面都会有这样几句,BIECOIN Core团队开发的程序,根据MIT软件开发协议发布,见下文,文件附件及网址。
#ifndef BITCOIN_MERKLE
#define BITCOIN_MERKLE
搜索解释:头件的中的#ifndef,这是"if not defined"的简写,是宏定义的一种。比如你有两个C文件,这两个C文件都include了同一个头文件。而编译时,这两个C文件要一同编译成一个可运行文件,于是问题来了,大量的声明冲突。条件指示符#ifndef的最主要目的是防止头文件的重复包含和编译。一般格式是这样的:
#ifndef <标识>
#define <标识>
...
...
#endif
查看程序,果然在最后有#endif。
#include
#include
#include是在程序编译之前要处理的内容,称为编译预处理命令。编译预处理命令还有很多,它们都以“#”开头,并且不用分号结尾,所以不是c语言的程序语句。
C系统的编程语言中,声明在这个地方插入别的文件中的代码,打“<>”这种尖括号,说的是,这个文件是编程环境标配拥有的文件,到默认的标配的地方去找这个文件。
stdint.h是标准C库的头文件,#include 属于STL库 模板库,但为什么没有后缀呢,这是C++里包含的东西写库的人为了和标准C和C++库区分开,所有的模板库的文件都没有后缀。
#include "primitives/transaction.h"
#include "primitives/block.h"
#include "uint256.h"
下面紧接着就是打“”的文件了,表示这不是编程环境标配拥有的文件,要在你的工程文件所在的目录中找,或是在编程环境设定中要查找的目录中去找。或者说标准模板库里没有,但是我需要经常用到,那好我自己就编写一段保存起来,用的时候再调用,因为是自己制作的,那就放在工程文件里,而不是放在标准库房里。这和我们的工作很相似。
uint256 ComputeMerkleRoot(const std::vector& leaves, bool* mutated = NULL);
std::vector ComputeMerkleBranch(const std::vector& leaves, uint32_t position);
uint256 ComputeMerkleRootFromBranch(const uint256& leaf, const std::vector& branch, uint32_t position);
下面就是注释了,
/*
* Compute the Merkle root of the transactions in a block.
* *mutated is set to true if a duplicated subtree was found.
*/
我尝试着将/*用在程序中,发现了规律,这很小的发现虽说时别人的基本功,因为枯燥的阅读添加了乐趣。计算区块里交易的Merkle根值。当找到复制出的子树时,指针变量mutated就被置1。
uint256 BlockMerkleRoot(const CBlock& block, bool* mutated = NULL);
/*
* Compute the Merkle root of the witness transactions in a block.
* *mutated is set to true if a duplicated subtree was found.
*/
Witness见证
uint256 BlockWitnessMerkleRoot(const CBlock& block, bool* mutated = NULL);
/*
* Compute the Merkle branch for the tree of transactions in a block, for a
* given position.
* This can be verified using ComputeMerkleRootFromBranch.
*/
我理解的意思是,计算出根植来了,当你想要查询交易时,可以根据构造出的二叉树结构来很快查询到,上一条是构造,这一条是查询某条交易。
std::vector BlockMerkleBranch(const CBlock& block, uint32_t position);
#endif
因为涉及到uint256.h,又找来该头文件来读一读
// Copyright (c) 2009-2010 Satoshi Nakamoto
// Copyright (c) 2009-2016 The Bitcoin Core developers
// Distributed under the MIT software license, see the accompanying
// file COPYING orhttp://www.opensource.org/licenses/mit-license.php.
同样是前面一段描述,多了一行中本聪的版本。
#ifndef BITCOIN_UINT256_H
#define BITCOIN_UINT256_H
#include
#include
#include
#include
#include
#include
#include "crypto/common.h"
和前面一样,先把一些工具拿来备着,等用到的时候立等可取。
自己的感觉就像是面对一本书,一个字都不认识,开始从字母开始,研究半天大概明白了一个字的意思。