Inv 清单的两个字段:比特币网络如何用存货宣告与提货请求组织每一轮对话 图 1
Inv 清单的两个字段:比特币网络如何用存货宣告与提货请求组织每一轮对话 · 图 1

比特币网络里几乎每一次信息交换都从一张清单开始:对端先递来一串“我这里有这些”,你挑出缺的,回一份“请给我这几样”,然后数据才真正流动。这张清单在协议里叫 inv——inventory,存货清单。它结构极简,每个条目只有两个字段,但条目里那个不起眼的类型数字,浓缩了比特币网络二十年叠加出来的兼容史:从最早的两种取值,到今天要靠一个三十一亿量级的标志位才能表达的见证形态。把 inv 读懂,等于拿到了观察节点日常对话的钥匙。

先看结构。v31.0 的 protocol.h 里,每个 inv 条目由一个三十二位无符号类型值加一个三十二字节哈希组成,序列化就这两行。哈希好理解——它说的是“哪一个”;类型说的是“以什么身份要它”。同一笔交易可以有两种被提及的方式:以普通交易哈希被提及,或以见证哈希被提及,类型值不同,取回的数据完整度就不同。这不是修辞差异,而是隔离见证落地后协议的核心分叉:不带见证标志的交易请求意味着“只给我旧格式的那份”,带标志则意味着“连见证数据一起给我”。

类型值的谱系在源码枚举里逐行可考。基础层:MSG_TX 为 1、MSG_BLOCK 为 2,这两个数字从协议诞生就在。第二层是专用变体:MSG_FILTERED_BLOCK 为 3,服务布隆过滤器收款的轻量客户端(BIP 37 一族);MSG_CMPCT_BLOCK 为 4,压缩区块(BIP 152 一族);MSG_WTX 为 5,按见证哈希公告交易(BIP 339)。第三层是标志位机制:源码定义 MSG_WITNESS_FLAG 为二的三十次方,把它按位或到基础值上,MSG_WITNESS_BLOCKMSG_WITNESS_TX 就从 2 和 1 变成十亿量级的数字。这种“低位枚举加高位标志”的写法让老节点读不懂新类型时会当成未知条目处理,而新节点始终能从任意值里拆出基础类型——叠加而不推翻,是这套编码的全部哲学。

inv 的对话学比编码更有意思。在正常节点上,一条 inv 是“宣告”,一次 getdata 是“提货”:getdata 的请求体用的就是和 inv 一模一样的清单结构,等于把对方递来的清单原样勾选后递回去。两个值得记住的对称点。其一,宣告条目数有硬上限:v31.0 的 net_processing.cppMAX_INV_SZ 为五万,超过这个数的 inv 整条作废并记日志——五万条足够宣告一个满载大区块的全部交易,又不至于让一条消息成为内存炸弹。其二,回货请求在发送侧另有节流:一次性组装的 getdata 批量在一千条量级(MAX_GETDATA_SZ,注释注明仅用于发送方向,接收侧为兼容不设此限),同时每条连接在途的区块请求被压在小窗口内,同步因此呈现“小步快跑”的节奏。

随着协商机制升级,同一份“我这里有”不再只有 inv 一种载体。握手阶段若双方都支持 wtxidrelay(BIP 339),交易公告就改用见证哈希作条目,去掉了“同一笔交易因是否有见证而像两个东西”的歧义;若进一步启用交易对账(sendtxrcncl 消息,BIP 330 一族),节点之间用盐值化的短 ID 集合核对彼此已知的交易,大量重复宣告直接被省掉。区块侧还有 sendheaders 协商(BIP 130):谈成的节点不再为新区块发 inv,而是直接把区块头递过来,宣告这一步干脆消失。于是“为什么最近抓不到 inv”在某些链段是正常现象:机制演进的终点常常是少发消息。

这些细节对运营者的实用之处在三处。第一,读日志与抓包时,类型数字的十进制形态就是判据:个位与低位值是无见证时代的旧语言,四十亿上下的值(基础值加标志位)说明对方在按见证兼容方式说话;类型 5 出现则代表 WTXID 中继在工作。第二,提货失败的显式回执同样走清单结构——当请求的东西不存在或已过期,对端用 notfound 按同格式回“没有”,脚本处理未确认交易依赖时应当检查这个分支,而不是干等超时。第三,宣告与提货的额度体系决定了“邀请很多、上链很慢”场景下的真实瓶颈定位:inv 五万上限与 getdata 批量限制都不限速你的交易进入对方内存池这件事,卡单的因果永远回到费率与依赖结构,而不是清单消息本身。

最后放一个整体视角:比特币网络没有目录服务、没有广播总线,所有信息发现都退化成最朴素的“清单加提货”两轮对话。inv 就是这两轮对话的名词与动词。两个字段、几个数字、一道五万条上限,撑起了每秒钟上万笔交易的互相知会——简单到可以被任何语言在几十行里实现,严谨到每种新数据形态只需在同一个位域里占一格。这份克制正是比特币网络能同时容纳两千多个版本共存、仍让每个节点平等对话的底层语法。

风险提示:本文为网络协议机制说明,不构成任何投资建议;文中枚举值与常量以比特币核心 v31.0 源码为准,后续版本可能调整,请以对应版本源码为准。

Inv 清单的两个字段:比特币网络如何用存货宣告与提货请求组织每一轮对话 图 2
Inv 清单的两个字段:比特币网络如何用存货宣告与提货请求组织每一轮对话 · 图 2