作者:conduition

来源:https://conduition.io/bitcoin/dropkick/

前篇见此处

DrpKick

在了解了 承诺-揭晓 协议的许多微妙之处之后,我们来看一个 承诺-揭晓 挽救协议的具体实例,我认为,它能实现很高的安全性、激励合作挽救钱币,同时,让共识规则的变更和工程界面尽可能小。我称之为 “DrpKick ”,因为它是一个直接的两步骤挽救协议 ,一步是 在链上 “抛下(drop)” 一个承诺,然后在别的地方 “弹出(kick)” 自己的钱币。

DrpKick 使用了原版的 FawkesCoin 承诺-揭晓 方案,但是,在面对多种多样的子问题时,但凡有缓解措施可用,就挑选最直接的缓解措施集合,将效率和保持共识规则不变放在第一位。也就是说,DrpKick 使用:

  • 残值手续费,以激励 PQ UTXO 的持有者帮助聚合以及发布承诺。
  • 默克尔树聚合承诺,以减少验证者节点必须索引的信息数量,并鼓励好心的用户提供可扩容的承诺聚合服务(可能要收取残值手续费)。
  • SCV(简单承诺验证),让节点可以从索引负担重解放出来,并允许 轻节点/剪枝节点 验证揭晓。
  • 推迟揭晓,以减少矿工审查攻击的激励,同时无需强制实施任何显式的索引或承诺排序。我们接受大量矿工串谋的微小风险(详见本文关于博弈论的附录)。
  • 密钥认证,以允许用户纠正错误、发送替换交易以及在第一笔交易不充分时还有补救机会。对无法原生支持多签名或通过通用的 MPC 来形成合作式签名的 PQ 密码系统,我们可以选择使用多密钥认证,从而聚合者依然可以通过幼稚的多签名强制执行残值手续费。

证明

DrpKick 的证明过程是这样的:

  • 令 $H$ 为一种抗碰撞的哈希函数
  • 令 $f$ 为一种量子难解的单向函数 $f: \mathbb W \rightarrow \mathbb S$,其中
    • $\mathbb W$ 为见证的空间
    • $\mathbb S$ 为比特币地址的空间
  • 令 $d$ 为一个很长的时延(以区块数量为单位),比如 1440 个区块(10 天)
  • 令 $0 \le \delta < 1$ 是一个手续费比率(一个分数,通常来说非常小)。
  1. 找出一组见证 $w = \lbrace w_1, w_2, … w_n \rbrace $ ,使得所有的 $f(w_i) = s_i$ 都是比特币 UTXO $u = \lbrace u_1, u_2, … u_n \rbrace $ 的地址(脚本脚本)
  • 基本上,见证都可以合并、后续再重构,例如派生相关地址的 BIP32 扩展私钥
  1. 生成一个后量子签名密钥 $Q$
  • 我们也可以让 $Q$ 是一个多签名的团体公钥,这将让聚合者可以联合签名、在揭晓交易重收取残值手续费
  1. 在一个区块中发布锚定时间的承诺 $H(H(w, Q), Q)$ ,比如,在一个 OP_RETURN 输出中、在一个脚本公钥中、或者在一棵默克尔树中(与其它这样发布的承诺一起)
  2. 计算一个开启证明 $\pi$ ,这个证据可以用来验证承诺 $H(H(w, Q), Q)$ 的历史出处
  3. 一旦承诺 $H(H(w, Q), Q)$ 得到 $d$ 个区块确认,构造一笔交易 $T$ ,它花费 $u = \lbrace u_1, u_2, … u_n \rbrace $ 到任意输出
  • $T$ 应该支付被 UTXO 的价值的一定比例 $\delta$ 给矿工作为手续费,以防范审查攻击(详见 “参数” 章节
  1. 使用 $Q$ 签名 $T$ ,生成一个后量子签名 $\mathbf{sig}$
  2. 产生一组传统交易的输入的见证 $W$ ,以满足传统共识验证规则(例如 EC 签名)
  3. 附加见证 $w$、 PQ 公钥 $Q$、 签名 $\mathsf{sig}$、传统见证 $W$ 以及开启证明 $\pi$ ,产生一笔签名的揭晓交易 $T’ = (T, w, Q, \mathsf{sig}, W, \pi)$
  4. 发布 $T’$

验证

验证者在面对一个揭晓交易 $T’ = (T, w, Q, \mathsf{sig}, W, \pi)$ 时,必须:

  1. 根据所有传统的共识规则来验证 $T$ 以及传统见证 $W$ (软分叉兼容性)
  2. 鉴别承诺开启证据 $\pi$ ,断言 $H(H(w, Q), Q)$ 在 至少 $d$ 个 区块以前已承诺到区块链
  3. 验证 $\mathsf{sig}$ 是 $Q$ 对 $T$ 的有效签名
  4. 分解 $w = \lbrace w_1, w_2, … w_n \rbrace $
  5. 对每一个 $i \in \lbrace 1 … n \rbrace $ ,验证 UTXO $u_i$ 的脚本公钥 $s_i = f(w_i)$

如果上述所有步骤都成功,那么验证者就知道:

  • 对每一个 UTXO $u_i$ 的脚本公钥 $s_i = f(w_i)$ ,这个花费者知道一个量子难解的见证 $w_i$
  • 这个花费者在至少 $d$ 个区块以前就知道这些见证
  • 这个花费者授权了使用 PQ签名密钥 $Q$
  • 公钥 $Q$ 授权了交易 $T$

这就完成了对花费交易 $T$ 的鉴别;基于这样的假设:在 $w$ 第一次揭晓之前,这个花费者是持有有效承诺 $H(H(w, Q), Q)$ 至少 $d$ 个区块的唯一的人。

好处

DrpKick:

  • 适用于任意的知识不对称(哈希化地址、BIP32,等等)
  • 在量子攻击者面前是可靠的,只要 PQ 签名方案不可伪造
  • 开启证明的体积与一个区块中承诺的数量呈对数增长
  • 允许改变揭晓交易的细节,而不需要等待第二笔承诺交易得到确认
  • 允许用户通过可以强制执行的残值手续费激励承诺聚合者和发布者
  • 支持批量挽救多个 UTXO
  • 验证复杂性随开启证明的体积呈线性增长

并且,DrpKick:

  • 不需要硬分叉
  • 不允许重复花费
  • 不强迫承诺过期
  • 不允许捣蛋
  • 不会给比特币节点增加任何拒绝服务式攻击界面
  • 不允许脚本轮换
  • 不需要显式的承诺索引 —— 比特币区块头自身足以聚合许多承诺
  • 不需要繁重的密码学,唯一例外是 PQ 签名方案。整个方案基本上就是将 OpenTimestamps 改用在新场景中。

缺点

  • 承诺揭晓 步骤之间,用户需要等待很长时间( $d$ 个区块)
  • 理论上,如果矿工可以持续审查交易长达 $d$ 个区块,那么可以盗窃钱币
    • 在现实中,这应该概率极小,因为需要占绝对多数的算力持有者串谋,且串谋持续至少 $d$ 个区块。(详见本文关于博弈论的附录
  • 开启证明 $\pi$ 可能非常大,因为它需要嵌入完整的交易,并且交易包含了对 $H(H(w, Q), Q)$ 的承诺
    • 使用一种标准的交易格式模板,由验证者预先填充,可以缓解这个问题。这会限制承诺交易的形状,但会让证据的体积小得多,因为证明者将不需要提供完整的承诺交易
  • 揭晓交易需要至少一个 PQ 签名,这个签名的体积可能很大(取决于所用的方案)
  • 聚合者可以用虚假承诺来充数,导致该聚合者的所有用户的开启证明 $\pi$ 的体积膨胀
    • 这可以通过抗 Dos 措施来缓解,比如验证码、工作量证明、残值手续费和暗箱支付
  • 一个 PQ 签名足以授权一个很大的 UTXO 集合 $u = \lbrace u_1, u_2, … u_n \rbrace $。这种效率可能会带来一种奇怪的激励,就是一些用户会 希望 使用 承诺-揭晓 来汇总许多输入,因为 DrpKick 将允许更小的见证体积和更快的签名速度(在花费大量 UTXO 的时候,相较于要为每个输入提供一个 PQ 签名)。 这究竟是一种不当激励,还是一种迂回的从单个签名人聚合多个签名的方式?需要更多研究。
  • 如果 DrpKick 得到部署,用于鉴别 不可判定的 KA(详见“知识不对称” 章节), 那么,就像任何应用于不可判定的 KA 的挽救协议一样,最终的软分叉会导致没收:一个受限制的传统 UTXO 的子集 —— 大小未知 —— 将被没收,因为他们缺乏所需的 KA 。就我所知,这是一个未解的难题,DrpKick 也无济于事。

用法

DrpKick 用户可以获得一个非常简单的挽救体验:连接互联网、生成一个 PQ 密钥 $Q$ ,在区块链上 抛下 一个承诺 $H(H(w, Q), Q)$ (可以通过查询一个聚合服务端)。然后,用户将相应的开启证明 $\pi$ 保存在磁盘中,然后就可以离线。用户可以在 几天/几周/几个月 之后回到线上,只要等待 $d$ 个区块就行。

在 $d$ 个区块之后,这个用户随时可以 弹出 对应的钱币:使用一笔揭晓交易、支付到在花费时才选定的任何目标地址,然后通过 $Q$ 的签名来授权。如果这个用户弄丢了 $\pi$ ,那么只需制作一个新的 —— 老的那个开启证明会隐藏在某些古老的默克尔树中,随时间消逝,而不会导致区块链或者 UTXO 集膨胀。

本质上,添加承诺就是 “推迟导入” 她的传统钱币到使用 $Q$ 的 PQ 钱包中;而钱包软件可以设计使用体验并作相应的解析。

是否导入一个传统钱包? Y/N

请输入你的传统种子词

现在,等待 1000 个区块,然后你的资金就将可用

聚合服务运营者 可以跟用户一起构造 PQ 密钥 $Q$(多签名密钥,例如,通过级联、MPC 或交互式多签名协议)。这让聚合服务可以强制执行对揭晓交易 $T$ 的约束,例如强制支付残值手续费。结合 $H(w, Q)$(这是用户可以安全分享的)和联合的 PQ 密钥 $Q$,聚合者就可以造出承诺和 $H(H(w, Q), Q)$ 的开启证据。然后,可以把承诺交给发布者,也可以子集发布,而开启证明则交给用户,使得用户可以验证自己的承诺交易已经确认。

传统的验证者节点将忽略未知的交易字段,然后使用传统的共识规则来验证花费; $W$ 中的传统见证都能满足这些验证规则。

新的验证者节点并不需要保留任何额外的索引或下载额外的区块数据,也不需要新的密码学原语:验证者只需要添加额外的验证规则、检查一些高效单向函数的输出,然后再验证特定的一类 UTXO 是应用正确的规则(根据在具体语境下使用的 KA) —— 这些是本提议有意留白的。

参数

使用本文附录中的博弈论,我们可以为 DrpKick 找出一组参数,以尽可能降低交易遭到审查攻击的风险,办法是激励占少数的矿工愿意在自己的区块模板中 包含 揭晓交易,即使其它的哈希率提供者主动 审查 揭晓交易。

必须让下列等式成立:

$$
\overbrace{\left(1 - (1-h_i)^d\right) \cdot \delta \cdot v}^{\text{include reward}} \quad >
\overbrace{h_i \cdot v}^{\text{censor reward}}
$$

  • $0 < h_i < 1$ 是考虑要不要审查一笔揭晓交易的矿工的哈希率占比
  • $d$ 是 DrpKick 的揭晓时延(以区块数量为单位)
  • $v$ 是揭晓交易所挽救的钱币的价值
  • $\delta$ 是手续费比例($v$ 的一部分要支付给矿工)

为了简化讨论,我们设 $v = 1$ 。

打包奖励 超过 审查奖励 时(哪怕仅仅是对一个小矿工而言),就足以激励所有的矿工选择 打包。具体来说,我们发现,在时延为 $d$ 个区块时,要让至少一名持有哈希率占比 $h_i$ 的矿工认定 打包奖励 高于 审查奖励,$\delta > h_i$ 是前提。只要一个矿工这么项,就足以打破 审查 策略的纳什均衡,并开启走向 “所有矿工都选择打包” 的螺旋。

如果我们固定区块 $d$ ,那么我们可以计算 最低费率 $\delta$ ,就是求解下列等式中的 $\delta$ :

$$
\delta \left( 1 - \left( 1 - h_i \right)^d \right) = h_i
$$

尤其是在 $h_i$ 趋于 $0$ 的极限情况下,这就可以说服审查收益较小的小矿工。首先,我们必须作一些调整,改写成我们在求解极限:

$$
\delta = \lim_{h_i \to 0} \frac{h_i}{1 - \left( 1 - h_i \right)^d}
$$

这个极限是一个不定式:当 $h_i \to 0$ ,我们有 $\delta \to \frac{0}{0}$ ,这是无法定义的。为了计算 $\delta$ ,我们必须使用洛必达法则,该法则指出:

$$
\lim_{x \to c} \frac{f(x)}{g(x)} = \lim_{x \to c} \frac{f’(x)}{g’(x)}
$$

其中 $f’$ 和 $g’$ 是对应函数对 $x$ 的一阶导数。

$h_i$ 对 $h_i$ 的导数显然是 1,因此,我们有:

$$
\begin{align}
\delta &= \lim_{h_i \to 0} \frac{h_i}{1 - \left( 1 - h_i \right)^d} \\
&= \lim_{h_i \to 0} \frac{1}{\frac{d}{d h_i} \left( 1 - \left( 1 - h_i \right)^d \right)} \\
&= \lim_{h_i \to 0} \frac{1}{ d \left( 1 - h_i \right)^{d-1} } \\
\end{align}
$$

随着 $h_i$ 趋近于 0 ,因子 $\left( 1 - h_i \right)^{d-1}$ 趋近于 1,所以,出人意料的,计算最低费率 $\delta$ 的通用公式非常简单:

$$
\delta = \frac{1}{d}
$$

以下是一些可用的案例参数集合:

最低费率 $\delta$区块时延 $d$
0.0250
0.01100
0.005200
0.0025400
$\frac{1}{1440}$1440

请记住,这里的 $\delta$ 是 最低费率 。举个例子,如果一个 DrpKick 协议实例设置 $d = 50$,那么一笔揭晓交易使用 $\delta = 0.02$ 的费率,就不能激励 任何 矿工跳出默认的 审查 策略(除非已经有一些诚实的哈希率多数,选择了出于原则而 打包 )。

为了确保矿工的策略是 打包,DrpKick 揭晓必须支付大于 $\delta \cdot v = \frac{v}{d}$ 的手续费,这个数额与所挽救的钱币的总价值 $v$ 呈正比。所用的费率越高,小矿工越有可能选择打包,产生上面提到的螺旋,走向新的诚实的、合作的纳什均衡,让甚至掌握大量哈希率的矿池也不得不选择 打包

参数刚度。请注意,最低费率 $\delta$ 与区块时延 $d$ 是对一个 DrpKick 协议实例来说是严格固定的参数。 这一点意味着,为了挽救已有的传统 UTXO,这些 UTXO 无法追溯性地承诺一个具体的 DrpKick 区块时延。DrpKick 协议实例必须在部署之前就在全局固定 $d$ 和 $\delta$ ,并且一旦部署,共识验证规则就会给 每一次DrpKick 揭晓无差别地应用这些参数,并且 无法 变更或者在用户基础上作定制化。在部署之前,必须极端小心地挑选最优的参数。必须找到一个平衡点:使用更长的区块时延意味着用户必须等待更长时间,才能救回自己的钱币;但更短的区块时延意味着用户必须支付更多手续费给矿工,才能避免审查攻击。

与 LifeBoat 对比

DrpKick 相比 LifeBoat(以及 “LifeJacket”)有许多优势,但也有一些劣势:

LifeBoat/LifeJacketDropKick
面对矿工审查攻击稍微安全一些。需要支付一笔与钱币的价值成比例的牺牲手续费,以反激励矿工审查攻击。
允许非常快(大约 6 个区块)的挽救体验。在 承诺 与 揭晓 阶段之间需要经历漫长的时延(以数百个甚至数千个区块计)。
每一个承诺都必须明文发布到区块链上,以允许排序。承诺可以隐藏在一个默克尔树承诺中。
所有承诺都必须由节点预先索引。承诺不需要索引。
需要持有 PQ 钱币,或要通过另外的方式给其他人支付,以发布承诺。承诺可以很容易地聚合,从而将成本降低到近乎零。任何手续费都可以从被挽救的钱币支付。
一条承诺只能授权一笔消息(TXID)。可以认证一个或多个 PQ 密钥,签名任意数量的消息或其它信息。
只支持两种知识不对称:BIP32 和哈希化地址。支持任何可以表达为单向地址派生函数的知识不对称。
  • DrpKick 相比其它 承诺-揭晓 协议(比如 LifeBoat)的主要优势是其简洁性,它的高效的委托承诺系统,以及它的通用性。在考虑要在 Bitcoin Core 或在其它现有的软件中可靠的实现时,这一切都让 DrpKick 更有吸引力。
  • DrpKick 的主要缺点就是,我们需要这些(可以说有些松散的)博弈论证明以及激励因素(比例手续费),来分析其对矿工审查的安全性,而 LifeBoat 面对此类攻击实现了更紧的安全性(仅受制于大规模重组),并且揭晓者的成本是固定的。

结论

虽然 SNARKs 和 ZKPs 也许学起来很有趣、值得运行基准测试,我个人非常怀疑它在比特币的共识层中有什么用处,至少在挽救协议上没有。比特币本质上倾向于非常保守主义的密码工具, 开发者的目标也是朴实、简单和高性能。虽然 SNARK 的假设很少,它们在真实世界中的代码实现却非常庞大。并且,在 SNARKs 的未来还有许多技术提升空间,所以,过早将它引入比特币可能会无意中错过不远的将来就会出现的所有进步。

有趣的是,ZKP 依然会在 DrpKick 中扮演一个有用的角色,因为它允许用户证明自己知道对任意语句 $s = f(w)$ 的真正见证 $w$ 而无需揭晓 $w$ ,这就允许脱链验证见证。对于聚合者来说,这是有用的抗 DoS 措施,他们天然希望过滤掉轰炸式的承诺提交,而 ZKP 将让他们能够做到这一点,即使证明系统不健全,后果也微乎其微。(如果证明系统不是 零知识的,会有许多后果,因为一个证据可能会揭晓秘密见证 $w$ !)

相反,我认为,DrpKick 这样的 承诺-揭晓 挽救协议,或者 Tadge Dryja 的 “Lifeboat” 这样的提议,是为比特币的共识规则不停机部署挽救协议的更好选择。它们只需要少量哈希函数的用法创新;没有复杂的代数、电路、约束系统、多项式承诺系统或交互式的断言机证明。DrpKick 开启证明的体积虽然比 Lifeboat 的大,但依然比基于哈希函数的 SNARK 小得多,而且基本上跟一个 SPV 证明一样大,通常是小于 1 kB 的 —— 依然比绝大部分 PQ 签名方案(的签名)都要小!

需要进一步的研究来了解 DrpKick 应对永久小体量哈希率重组审查攻击的安全性(详见 关于 “51% 攻击” 的章节), 并确定将 DrpKick 作为软分叉融入现有共识规则的最佳策略,希望不要在 Q-day 之后引入诱发隐私性降级的反常激励。

参考文献

我在这篇文章中讨论的许多都不是我的原创观念 —— 它已经在邮件组中连篇累牍地讨论数年了。在比特币之外,承诺-揭晓 协议在密码学中的讨论可以追溯到 1998 年,甚至已经被提议用作一种单独的密码货币(FawkesCoin)的花费鉴权手段。

不过,许多基本概念都与比特币特有的术语有关(比如,签名一个 “TXID” 而不是一条 “消息”、承诺一个 “公钥” 而不是一个 “见证”)。许多解决方案都是碎片化的,散落在邮件组中,并且其取舍要么在当时尚不知晓,要么(至少)没有得到明确说明。

我希望这篇文章能将这些分散的知识整合到一个地方。如果你知道更多关于 承诺-揭晓 的 想法/解决方案,是我在这里没有讨论的,欢迎联系我。我有可能知道一些想法但忽略了它们,但如果我错过了什么有趣的技巧,我很乐意知道 。

附录:博弈论

(译本略)