比特币源代码--16--bitcoind(main函数)应用程序参数交互—— AppInitParameterInteraction(3)

1、哈希假定有效参数

hashAssumeValid = uint256S(gArgs.GetArg("-assumevalid", chainparams.GetConsensus().defaultAssumeValid.GetHex()));
    if (!hashAssumeValid.IsNull())
        LogPrintf("Assuming ancestors of block %s have valid signatures.\n", hashAssumeValid.GetHex());
    else
        LogPrintf("Validating signatures for all blocks.\n");

-assumevalid=blockid:表示在blockid以前的全部区块都假设正确的,也就是不用再去验证。若是没有设置,那么就要验证以前全部区块的签名信息。函数

assumevalid参数的默认值能够经过chainparams.GetConsensus().defaultAssumeValid.GetHex()得到,这个默认值的得到过程包括3个步骤:ui

(1)得到链上共识参数:经过chainparams.GetConsensus()得到链上共识参数,返回类型为Consensus::Params,其详细定义能够在consensus/Params.h中找到,Params为一个结构体,该结构体主要定义了影响链上共识的重要参数,好比:创世块(hashGenesisBlock)、奖励减半时间间隔(nSubsidyHalvingInterval)、各类BIP启动时的区块高度、工做量证实参数(powLimitfPowAllowMinDifficultyBlocks等)、难度调整间隔计算函数(DifficultyAdjustmentInterval)以及默认假定有效对象(defaultAssumeValid命令行

(2)默认假定有效对象:默认假定有效对象在Consensus::Params中定义uint256 defaultAssumeValid,其类型uint256是一个类,定义于src/uint256.h中,其基类为模板类base_blob,主要用于存储固定大小不透明二进制数值模板,在其后实现了uint160与uint256两个子类,分别实现了160位与256位二进制数值存储类,因此在此处咱们能够看到默认假定有效对象主要是须要存储二进制值,而经过base_blob与uint256能够发现该二进制数为区块的哈希值;日志

(3)获取哈希值:最后一步就是获取哈希值的十六进值,其获取方式经过GetHex()实现。code

 

assumevalid参数的值也能够由用户在命令行中输入,输入形式为包含64位数的十六进制值,其样式以下:对象

0x00000000000a4d0a398161ffc163c503763b1f4360639393e0e4c8e300e0caec

在得到十六进制值后,咱们经过uint256S函数将其转换为uint256对象,该函数定义于src/unit256.h中。其函数实现以下:rem

/* uint256 from const char *.
 * This is a separate function because the constructor uint256(const char*) can result
 * in dangerously catching uint256(0).
 */
inline uint256 uint256S(const char *str)
{
    uint256 rv;
    rv.SetHex(str);
    return rv;
}

最后判断hashAssumeValid的有效性,若是不为空,则假定该哈希值对应区块的全部父区块都具有有效的签名,不然须要验证全部区块的签名,并将判断信息输入在日志中。hashAssumeValid主要在src/Validation.cpp的ConnectBlock函数中使用。hash

 

2、交易池大小限定参数

// mempool limits
    int64_t nMempoolSizeMax = gArgs.GetArg("-maxmempool", DEFAULT_MAX_MEMPOOL_SIZE) * 1000000;
    int64_t nMempoolSizeMin = gArgs.GetArg("-limitdescendantsize", DEFAULT_DESCENDANT_SIZE_LIMIT) * 1000 * 40;
    if (nMempoolSizeMax < 0 || nMempoolSizeMax < nMempoolSizeMin)
        return InitError(strprintf(_("-maxmempool must be at least %d MB"), std::ceil(nMempoolSizeMin / 1000000.0)));

首先计算mempool的最大值,后面乘以1000000是将单位从MB转换成B,而后计算最小的限制,其中,-limitdescendantsize的含义以下,后面乘以1000将单位从KB转化成B,再乘以40表示最小能够容纳40个这个的交易族。it

-limitdescendantsize:若是某个交易在mempool中全部的祖先size之和超过该限制值,那么则拒绝接受该交易。单位为KB。io

在每一个节点内部均可以设置如下几种费用来避免接收过多的交易,

  •     minrelaytxfee:最小的转发费用,若是交易费小于这个值,节点就直接忽略该交易。默认值为0.00001 BTC/KB。
  •     dustrelayfee:用来断定一笔交易时候是不是dust tx,若是是的话则忽略该交易。默认值为0.00001BTC/KB。
  •     incrementalrelayfee:用来改变mempool最低交易费用的变量,当mempool中的交易数量超过阈值时,交易费用阈值便会增长,增长的程度就由incrementalrelayfee决定。默认值为0.00001BTC/KB。

 

 

在代码中DEFAULT_MAX_MEMPOOL_SIZE常量定义于src/policy/policy.h(33)中,其表明的是交易池最大存储容量(MB)数值,经过其定义咱们能够看到其最大容量为300MB。

/** Default for -maxmempool, maximum megabytes of mempool memory usage */
static const unsigned int DEFAULT_MAX_MEMPOOL_SIZE = 300;

而交易池最小存储容量对应的默认值为DEFAULT_DESCENDANT_SIZE_LIMIT常量,定义于src/validation.h(67),其单位为KB,经过其定义咱们能够看到其最小存储容量为101KB。

/** Default for -limitdescendantsize, maximum kilobytes of in-mempool descendants */
static const unsigned int DEFAULT_DESCENDANT_SIZE_LIMIT = 101;