协议演进 / BIP/比特币改进提案 / BIP-125
BIP-125
付款人用输入的 nSequence 小于 0xffffffff-1 来明确声明:这笔未确认交易将来可以用更高手续费的版本替换。本 BIP 目前处于已部署状态。
一、档案卡
| 编号 | BIP-125 |
|---|---|
| 标题 | Opt-in Full Replace-by-Fee Signaling |
| 作者 | David A. Harding <[email protected]>, Peter Todd <[email protected]> |
| 指定日期 | 2015-12-04 |
| 层级 | Applications(应用) |
| 类型 | Specification(规范类) |
| 状态 | Deployed(已部署) |
| 阅读版 | https://bips.dev/125 |
| 官方原文 | https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki |
二、放在哪一族
交易替换与内存池策略族,核心是 nSequence 的用法。它与相对锁定时间一族相邻又必须分清:
BIP-68:用共识强制的序列号表达相对锁定时间
BIP-112:CHECKSEQUENCEVERIFY
BIP-125 原文明确说:opt-in full-RBF 与其他 nSequence 用法没有已知的问题性冲突,与比特币 0.1 实现里的共识锁定时间、BIP-68、BIP-112 都兼容。
它处理的是节点策略(mempool 里一笔未确认交易能不能被另一笔顶掉),不是共识规则:交易一旦上链,就不存在“替换”一说。理解这一族的关键是分清三件事:付款人有没有发信号、节点愿不愿意按信号替换、收款人要不要把未确认交易当作已付款。
三、它要解决什么
3.1 发出去的交易改不动
原文的出发点:许多节点不会把内存池里的一笔交易,换成另一笔花费相同输入的交易。付款人因此很难调整已经发出的交易——例如确认迟迟不来想加手续费,或者有其他正当的替换需求,都做不到。
3.2 直接恢复全量替换,又会伤到“先见”预期
历史上,中本聪的原始实现本就用每个输入的 nSequence 支持内存池内替换,后来在 0.3.12 版被移除,理由包括替换交易不必多付手续费,矿工没有动力打包,也没有内建的速率限制防止中继带宽被滥用。
等到有人做出 RBF 补丁想重新启用替换时,一部分收款人已经形成了预期:先看到的那一版交易,很可能就是最终被确认的那一版。于是出现了折中方案 RBF First Seen Safe(RBF-FSS):替换交易必须按不低于原金额支付原交易的全部输出,原始的 RBF 则被称为 full-RBF。但 FSS 每次替换都要多加一个输入:钱包没有闲置输入时用不了,不同来源的输入混在一起损隐私,还白白增大交易体积。
opt-in full-RBF 的解法是回到中本聪的原始语义(只微调一点,让用 locktime 的人能退出):付款人自己先发信号声明“可替换”,依赖先见版本的收款人可以据此忽略这类未确认交易;同时付款人享有 full-RBF 的效率,不必背 FSS 的额外输入。
四、规则本身
4.1 两种发信号方式
显式信号(Explicit signaling):一笔交易的任一输入的 nSequence 小于 (0xffffffff - 1),即视为该交易选择加入、允许被替换。
继承信号(Inherited signaling):一笔交易自己没显式发信号,但只要它的任一祖先交易(父交易链)发了信号且仍未确认,它在本政策下同样可替换。
没有信号的交易,节点与收款人可以照旧处理,维持现状——这是 “opt-in(可选加入)” 的含义。
4.2 替换必须满足的五条(初始实现)
原文给出的初始实现预期用于 Bitcoin Core 0.12.0。一笔新交易(替换交易)要顶掉内存池里一笔或多笔花费相同输入的交易(原交易),须同时满足:
- 原交易显式或经继承发出了可替换信号;
- 替换交易若包含未确认输入,该输入必须曾出现在某笔原交易里(未确认输入指花费一笔尚在未确认状态的交易的输出);
- 替换交易支付的绝对手续费,至少不低于所有原交易手续费之和;
- 替换交易还须为自身带宽付费,费率不低于节点最低中继费设置。例如最低中继费为 1 satoshi/byte、替换交易共 500 bytes,则其手续费至少要比原交易之和再高 500 satoshis;
- 被替换的原交易加上将被逐出内存池的后代交易,总数不得超过 100 笔。
节点收到信号后是“可以”允许替换,不是必须;替换被拒时,初始实现用 P2P 协议的 reject 消息反馈,轻客户端可据此及中继情况判断替换是否传播成功。
4.3 收款钱包政策
向用户展示未确认交易、或把未确认交易数据提供给自动化系统的钱包,应考虑二选一:对 opt-in full-RBF 交易额外提示可疑,或干脆等它确认后再处理。由于后代交易可经继承信号变得可替换,对祖先未确认期间的后代也要沿用同一处理方式。
4.4 花费钱包政策
不想发信号的钱包:使用最大序列号 (0xffffffff),或在同时要用 locktime 时用 (0xffffffff-1);原文称当时已知钱包都这么做。这类钱包还应避免花费别人发了显式或继承信号的未确认交易。
想做替换的钱包:使用显式信号,并满足 4.2 的替换条件。
五、谁必须动
普通持币人(付款人):想保留事后加费、改交易的能力,就让钱包把输入 nSequence 设为小于 0xffffffff-1 的值;不想被替换,就不要发信号。
收款人:看到带信号的未确认交易,可以选择不把它当作付款、等确认后再交付——信号正是给收款人的风险提示。
钱包开发者:发送端要正确处理显式信号与“不花费带信号的未确认输出”;接收端要把信号状态(包括继承来的)如实呈现给用户或下游系统。
全节点与矿工(策略层):可按本政策在内存池中接受合格的替换。这纯粹是节点各自的 mempool 策略,不是共识义务;原文在部署一节中称,当时全网算力挖矿时都使用 opt-in full-RBF 语义(sequence 小于 0xffffffff-1),并预期随 Bitcoin Core 0.12.0 等软件升级而普及;同时也提醒,要等足够多节点提供中继路径、足够多算力支持替换,替换才可靠。
共识层:无改动。已确认交易不可替换,本 BIP 不碰区块有效性规则。
六、现在算不算数,以及一个常见误读
状态为 Deployed(已部署)。按仓库状态解释:这套信号与替换政策已经进入实际部署的软件与网络实践,读原文时应把它当作现行的策略规范来理解,而不是待议草案。但“已部署”说的是政策可用、节点可实现,不等于每个节点、每个钱包都用完全相同的 mempool 规则——原文从标题起就把它限定为 opt-in 的信号政策:有信号才谈替换,无信号维持原状。
常见误读:“带了 RBF 信号的交易,收款人就一定会被双花骗走钱。”
不对。信号的全部意义在于提前告知:这笔未确认交易可能被替换。原文给收款钱包的政策正是据此设计的——对带信号的未确认交易提高警惕或等确认后再当作付款,这样就消除了付款人利用被允许的替换行骗的空间。风险来自把带信号的未确认交易误当成已确认,而不是信号机制本身。
七、延伸
- 阅读版:https://bips.dev/125
- 官方原文:https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki
- 相关:BIP-68 相对锁定时间、BIP-112 CHECKSEQUENCEVERIFY
- 仓库总目录:https://github.com/bitcoin/bips
