跳转到正文
buybitcoinsmart

术语表 /协议与升级

密钥路径花费

密钥路径花费是什么?
密钥路径花费是指用针对调整后输出密钥的一个签名来花费 Taproot 输出,所公布的见证数据恰好只有一个元素,也不会泄露任何备选脚本的信息。

规定于 BIP-341。

Taproot 输出既可以通过为其密钥签名来花费,也可以通过披露已承诺的脚本来花费,而密钥路径是其中不引人注目的一种。BIP-341规定该见证数据恰好为一个元素,即默认 sighash 下的一个64字节 Schnorr 签名,使整个输入为230权重单位,即57.5 vbytes。对持有者而言,共享保险库和单人付款在链上看起来没有区别。

运作方式

密钥路径花费为输出密钥签名,而输出密钥并非任何人选定的密钥:BIP-341将其构造为 Q = P + int(t)G,其中 P 是内部公钥,t 是 P 与脚本树默克尔根一起的带标签哈希。

因此,签名意味着对私钥一侧施加同样的偏移。当内部点的 y 坐标为奇数时,参考例程会先对私钥取负,因为 taproot 调整作用于32字节的 x-only 密钥,然后再加上 t 并对曲线的阶取模。其结果按 BIP-340签名,并单独放入见证栈。

验证首先是一项计数检查,然后才是密码学检查。节点读取见证程序的32字节,若见证栈为空则立即失败;当栈中有两个或更多元素且最后一个元素以0x50 开头时,将该元素作为附注(annex)剥离。如果恰好剩下一个元素,则该花费为密钥路径花费,且该元素必须能作为 BIP-340签名针对输出密钥通过验证。该流程中没有任何一步会告诉节点是否曾承诺过脚本树。

当隐含 SIGHASH_DEFAULT(值为0x00,覆盖整笔交易)时,签名为64字节。附加其他 sighash 字节时则为65字节,而在最后一位带有0x00 的65字节签名会被有意拒绝:若允许这种签名,矿工或任何转发节点都可以把64字节的签名填充到65字节,从而改变 wtxid 和发送方原本预期的费率。

签名所覆盖的消息最多为206字节。它承诺交易版本和锁定时间,承诺每个输入的输出点、金额、先前 scriptPubKey 和序列号的哈希,并承诺各项输出。

大小的算术由此得出。按 BIP-141,交易权重为基础大小乘以三再加总大小,虚拟大小为该权重除以四,对整笔交易向上取整。一个 Taproot 输入贡献41个基础字节(36字节的输出点、空 scriptSig 的1个长度字节、4字节的序列号)和66个见证字节(栈计数、长度前缀、签名),即41乘以3再加107,得230权重单位,也就是57.5 vbytes。

BIP-341中有一条建议常让钱包开发者措手不及。完全没有脚本的输出也应当承诺一个调整值,该值计算为仅对内部密钥取的带标签哈希,而不是原样公布内部密钥。规范说明了原因:当两方把各自的密钥相加为共享输出密钥时,其中一方可以悄悄加入一个调整值,隐藏一条仅其本人可花费的脚本路径,而另一方无从察觉。

购买比特币时为何重要

Taproot 的签名消息,是硬件钱包无需信任所连接的计算机就能算出您手续费的原因。

在 BIP-143(SegWit 版本0规则)下,消息只承诺被签名输入所花费的金额,别无其他。为三输入交易中的一个输入签名的设备,必须被告知另外两个金额,却无法核对,而这正是被攻陷的主机借以让您签署远高于屏幕所示手续费的漏洞。BIP-341则承诺交易所花费的每个输入的金额以及它们全部的先前 scriptPubKey,因此签名方可以自行汇总。该升级同样适用于脚本路径花费,但密钥路径才是本站41项钱包评测中大多数设备所有者会遇到的情形。

在这一切适用之前,您的钱包必须能够派生密钥,而在这些评测中情况参差不齐。KeepKey 于2025年2月在固件7.10.0中加入了对 Taproot 输出的支持。MetaMask 自己的公告仍把 Taproot 列为日后推出,因此无论其比特币支持的其余部分如何,它都无法给您一个用于收款的 bc1p 地址。

手续费在每个输入上以小幅度偏向密钥路径,而这一差额会朝着多数读者购买的方向累积。BIP-143自带测试向量中已签名的 P2WPKH 输入带有71字节的签名和33字节的密钥,计入栈计数和长度前缀后为107个见证字节,合计271权重单位,即67.75 vbytes。密钥路径输入比这少10.25 vbytes,因此分别积累了30笔小额购买、之后再合并的持币者,可使那一笔交易减少约307 vbytes。

请明确隐私究竟带来了什么。隐藏您的花费策略并不等于隐藏您的历史:如果这些比特币来自本站评测的63家交易所之一,该平台已经掌握您的身份证件和提币地址,任何签名格式都改变不了这一点。仍然隐藏的是,这笔币究竟由一个密钥保管,还是由带有律师恢复分支的签名阈值保管,而后一个事实正是让某个地址值得被盯上的原因。

taproot_sign_key 逐步解析

taproot_sign_key 是 BIP-341发布的、用于生成这一见证数据的参考例程,全部只有九行 Python 代码。

它接收一棵脚本树、内部私钥、一个 sighash 类型,以及 BIP-340所要求的辅助随机数。当脚本树为空时,它将调整输入设为空字节串;否则该输入为树辅助函数返回的默克尔根。它用该值调整内部私钥,对 sighash 签名,仅当类型不为零时才附加哈希类型字节,并返回只含一项的列表。这一项就是整个见证数据。

有两处细节值得留意。空分支并不是看上去的未调整情形,因为传入空字节串会使调整值成为仅对内部密钥取的带标签哈希,这恰恰是规范对无脚本输出所建议的不可花费承诺。另外,随机数参数属于 BIP-340而非 Taproot:密钥调整完成后,结果就是一个普通的 Schnorr 签名,这也是密钥路径花费无需特殊处理即可批量验证的原因。

密钥路径花费 vs P2TR

P2TR 是输出类型,而密钥路径花费是清空这类输出的两种方式之一。无论日后通过哪条路径花光,这笔币始终是 P2TR 币。当有人告诉您 Taproot 地址是私密的,这一区别就很重要:无论哪种方式,向其收款公布的都只是一个32字节的密钥,别无其他,而人们所说的隐私出现在花费的时刻,并且只有在走密钥路径时才成立。

密钥路径花费 vs MuSig2

MuSig2 是产生密钥路径花费所需签名的一种方式,而不是密钥路径花费的必要条件。单一所有者用单个密钥签名,每次付款都是密钥路径花费,根本不涉及聚合协议。二者之所以被混为一谈,是因为聚合是更有意思的情形:MuSig2 让多方得到一个密钥和一个签名,因此他们的结算走同一条路径,占用同样的57.5 vbytes,与付午餐钱的人无异。反过来也成立,因为聚合密钥可以放在脚本叶子中,此时花费它属于恰好使用 MuSig2 的脚本路径花费。

请勿混淆

常见问题

密钥路径花费能证明该输出背后没有脚本吗?

不能。节点只能看到一个签名,无法判断是否承诺了脚本树,这正是该设计的要点。BIP-341更进一步,建议即使输出完全没有脚本,也对密钥进行调整,因为当输出密钥是多方密钥的聚合时,否则其中一方可能加入隐藏的脚本路径,并单独花费这笔币。

密钥路径花费比脚本路径花费更便宜吗?

是的,通常相差很大。密钥路径输入只携带一个64字节的签名,总计57.5 vbytes,而脚本路径花费必须公开所用的叶子脚本,外加一个33字节的控制块,脚本树每多一层,控制块就再增加32字节。

如何判断我的钱包是否使用密钥路径花费?

请先查看它是否能派生 Taproot 地址。如果它提供 bc1p 地址,并用单个签名从该地址花费,那就是密钥路径花费。目前的支持情况仍不均衡:KeepKey 在2025年2月发布的固件7.10.0中加入了 Taproot 输出,而 MetaMask 表示 Taproot 尚未支持。

接着阅读

相关术语

协议与升级中的更多术语

阅读本页英文版