比特币源码研读7-程序入口函数解析(6)

上一节提到了一个问题:比特币默认的日志输出文件是哪个? 不知道大家找到了没,现在答案公布如下:

如果有看过我的第一篇文章“比特币源码研读1——下载与编译” 就知道,我们安装的路径为个人的目录下,那么比特币默认的日志文件就在:

~/.bitcoin/debug.log

tips: 这里说明下,有一种情况是看不到debug.log这个日志文件的——你从未运行过程序,解决方案就是跑以下的命令:

bitcoind

或是

bitcoind -daemon

如果不想下载一百多G的数据文件,对于第一个命令bitcoind,直接ctrl+c即可;第二个命令的话杀掉后台进程就可以了。


好了,我们接下来继续讲解参数的初始化设置。

InitParameterInteraction(): 该函数具体实现于init.cpp文件中,主要分为7部分,先看第一部分:

(1) 绑定并监听地址

// when specifying an explicit binding address, you want to listen on it

// even when -connect or -proxy is specified

if (IsArgSet("-bind")) {

if (SoftSetBoolArg("-listen", true))

LogPrintf("%s: parameter interaction: -bind set -> setting -listen=1\n", __func__);

}

if (IsArgSet("-whitebind")) {

if (SoftSetBoolArg("-listen", true))

LogPrintf("%s: parameter interaction: -whitebind set -> setting -listen=1\n", __func__);

}

就是当你显式指定一个绑定地址,就监控该地址,即使你指定了“-connect”或者“-proxy”参数。

从代码可以看出,有两种方式来绑定地址:"-bind" 和 "-whitebind",这两种的处理方式也一样,都是通过函数SoftSetBoolArg设置 参数“-listen”为 true,表示对地址进行监听。

另外,关于记录日志的函数 LogPrintf,以后会经常碰面,这里介绍一下,它是以预编译方式定义于util.h文件中。从定义中看出,真正实现打印功能的函数是 LogPrintStr, 其定义于util.h文件中。

其中,“\” 表示换行, 实现代码在util.cpp文件中:

int LogPrintStr(const std::string &str)

{

int ret = 0; // Returns total number of characters written

static std::atomic_bool fStartedNewLine(true);

std::string strTimestamped = LogTimestampStr(str, &fStartedNewLine);

if (fPrintToConsole)

{

// print to console

ret = fwrite(strTimestamped.data(), 1, strTimestamped.size(), stdout);

fflush(stdout);

}

else if (fPrintToDebugLog)

{

boost::call_once(&DebugPrintInit, debugPrintInitFlag);

boost::mutex::scoped_lock scoped_lock(*mutexDebugLog);

// buffer if we haven't opened the log yet

if (fileout == NULL) {

assert(vMsgsBeforeOpenLog);

ret = strTimestamped.length();

vMsgsBeforeOpenLog->push_back(strTimestamped);

}

else

{

// reopen the log file, if requested

if (fReopenDebugLog) {

fReopenDebugLog = false;

fs::path pathDebug = GetDataDir() / "debug.log";

if (fsbridge::freopen(pathDebug,"a",fileout) != NULL)

setbuf(fileout, NULL); // unbuffered

}

ret = FileWriteStr(strTimestamped, fileout);

}

}

return ret;

}

大概逻辑如下:

1. 通过调用函数LogTimestampStr为日志加上时间戳;

2. 根据全局变量fPrintToConsole判断是否打印到控制台,默认值为false, 即不打印;

3. 根据全局变量fPrintToDebugLog判断是否打印到日志文件debug.log,默认是true,即打印;

好了,继续InitParameterInteraction函数讲解。

(2) 连接可信任节点

if (gArgs.IsArgSet("-connect")) {

// when only connecting to trusted nodes, do not seed via DNS, or listen by default

if (SoftSetBoolArg("-dnsseed", false))

LogPrintf("%s: parameter interaction: -connect set -> setting -dnsseed=0\n", __func__);

if (SoftSetBoolArg("-listen", false))

LogPrintf("%s: parameter interaction: -connect set -> setting -listen=0\n", __func__);

}

首先判断gArgs是否有"-connect"参数,如果有,将“dnsseed”和"-listen"参数设置为false,即只有当网络连接到可信任节点时,才取消通过DNS广播方式查找节点地址,不监听默认的地址。

这里需要注意的是,全局参数对象mapArgs中如果有“-listen” 参数,即在此之前已经设置了“-listen” 参数,则不会再重新设置了,即“-listen” 参数的值就不会变了。

这也就是当你在(1)中设置了”-bind”和”-whitebind”参数,那么即使你指定了“-connect”或者“-proxy”参数也无效。

(3)代理模式

if (IsArgSet("-proxy")) {

// to protect privacy, do not listen by default if a default proxy server is specified

if (SoftSetBoolArg("-listen", false))

LogPrintf("%s: parameter interaction: -proxy set -> setting -listen=0\n", __func__);

// to protect privacy, do not use UPNP when a proxy is set. The user may still specify -listen=1

// to listen locally, so don't rely on this happening through -listen below.

if (SoftSetBoolArg("-upnp", false))

LogPrintf("%s: parameter interaction: -proxy set -> setting -upnp=0\n", __func__);

// to protect privacy, do not discover addresses by default

if (SoftSetBoolArg("-discover", false))

LogPrintf("%s: parameter interaction: -proxy set -> setting -discover=0\n", __func__);

}

如注释,设置代理是为了保护隐私,假如已经指定了代理服务器,将"-listen"、"-upnp"以及"-discover"均设为false,表示只使用指定的代理服务器,不使用UPNP监听端口,不去查找默认的地址。换言之,只使用代理参数提供的监听地址及端口。

以下是微软官方网站对UPnP的解释:

通用即插即用 (UPnP) 是一种用于 PC 机和智能设备(或仪器)的常见对等网络连接的体系结构,尤其是在家庭中。UPnP 以Internet标准和技术(例如 TCP/IP、HTTP 和 XML)为基础,使这样的设备彼此可自动连接和协同工作,从而使网络(尤其是家庭网络)对更多的人成为可能。

(4)监听设置

全局变量DEFAULT_LISTEN 默认值为true, 即不设置监听,将 "-upnp"、"-discover"以及"-listenonion"(匿名地址监听)均设为false

if (!GetBoolArg("-listen", DEFAULT_LISTEN)) {

// do not map ports or try to retrieve public IP when not listening (pointless)

if (SoftSetBoolArg("-upnp", false))

LogPrintf("%s: parameter interaction: -listen=0 -> setting -upnp=0\n", __func__);

if (SoftSetBoolArg("-discover", false))

LogPrintf("%s: parameter interaction: -listen=0 -> setting -discover=0\n", __func__);

if (SoftSetBoolArg("-listenonion", false))

LogPrintf("%s: parameter interaction: -listen=0 -> setting -listenonion=0\n", __func__);

}

tips: listenonion,即匿名地址监听,这里涉及到通信机制的一个概念:第二代洋葱路由(onion routing)。

Tor(The Onion Router)是第二代洋葱路由(onion routing)的一种实现,用户通过Tor可以在因特网上进行匿名交流。Tor专门防范流量过滤、嗅探分析,让用户免受其害。最初该项目由美国海军研究实验室赞助。2004年后期,Tor成为电子前哨基金会的一个项目。2005年后期,EFF不再赞助Tor项目,但他们继续维持Tor的官方网站。

(5)外部IP地址设置

if (IsArgSet("-externalip")) {

// if an explicit public IP is specified, do not try to find others

if (SoftSetBoolArg("-discover", false))

LogPrintf("%s: parameter interaction: -externalip set -> setting -discover=0\n", __func__);

}

如果显式指定了公共IP地址,就不用查找其他的监听地址了。

(6)区块模式设置

// disable whitelistrelay in blocksonly mode

if (GetBoolArg("-blocksonly", DEFAULT_BLOCKSONLY)) {

if (SoftSetBoolArg("-whitelistrelay", false))

LogPrintf("%s: parameter interaction: -blocksonly=1 -> setting -whitelistrelay=0\n", __func__);

}

全局变量DEFAULT_BLOCKSONLY默认值为False,只有DEFAULT_BLOCKSONLY的值为true,GetBoolArg才为true,这时才会将"-whitelistrelay"设置为false,即区块模式下白名单列表失效。

tips: 这里的blocksonly参数是比特币客户端以调试状态启动时才会使用的,我们可以从src/init.cpp里面的帮助信息函数HelpMessage中得到相关信息:

if (showDebug)

strUsage += HelpMessageOpt("-blocksonly", strprintf(_("Whether to operate in a blocks only mode (default: %u)"), DEFAULT_BLOCKSONLY));

关于DEFAULT_BLOCKSONLY, 我们已经知道其默认值为False,即默认情况下不会只以区块模式运行。假定只在该模式下运行,那么此时全网的交易都不会被打包,钱包的交易广播功能将失效,也就是我们看到的walletbroadcast参数此时需要设置为false,否则互斥。

(7)强制白名单节点连接参数设置

// Forcing relay from whitelisted hosts implies we will accept relays from them in the first place.

if (GetBoolArg("-whitelistforcerelay", DEFAULT_WHITELISTFORCERELAY)) {

if (SoftSetBoolArg("-whitelistrelay", true))

LogPrintf("%s: parameter interaction: -whitelistforcerelay=1 -> setting -whitelistrelay=1\n", __func__);

}

DEFAULT_WHITELISTFORCERELAY默认为true,则参数"-whitelistrelay"设置为true,即比特币网络中的信息将优先在白名单节点间传递。

至此InitParameterInteraction函数已经解读完毕。下一节将讲解初始化基本环境搭建,敬请期待!


作者:区块链研习社比特币源码研读班 Jacky

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 159,015评论 4 362
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,262评论 1 292
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,727评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,986评论 0 205
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,363评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,610评论 1 219
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,871评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,582评论 0 198
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,297评论 1 242
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,551评论 2 246
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,053评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,385评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,035评论 3 236
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,079评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,841评论 0 195
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,648评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,550评论 2 270

推荐阅读更多精彩内容

  • NAME dnsmasq - A lightweight DHCP and caching DNS server....
    ximitc阅读 2,652评论 0 0
  • Android Gradle必备使用技巧,未完待续,欢迎关注公众号flysnow_org,第一时间看后续技巧。 在...
    飞雪无情flysnow_org阅读 1,592评论 0 6
  • 昨天在纽约回学校的大巴站上看到了这样一对母女。 妈妈让女儿捡起我脚附近的一枚5分硬币,女儿问:Why? mom! ...
    Wicky吴佳欣阅读 419评论 0 0
  • 语言能力是每个人都必须具备的素质之一,好口才会给你带来好的运气和财气,拥有好口才,就等于拥有了成功的人生。本书用精...
    酷听听书阅读 517评论 0 0
  • 非常值得记录的一天,纵生乐亭团队迎来第二个看懂基本法的人~~郝珊珊,自己看懂,三天决定转正并三点预备转正!让我又一...
    4d4007053eb1阅读 149评论 0 0