用酒吧蹦迪的例子,解释为什么比特币需要闪电网络

来源:橙皮书

上周在Reddit热度最高的帖子之一,它用很通俗的例子解释了为什么比特币需要闪电网络,以及比特币支付是怎么逐渐进步的。

用酒吧蹦迪的例子,解释为什么比特币需要闪电网络

从川普发推到孙哥道歉,最近圈子里出现很多”吸引眼球”的事件,但他们会对整个生态真的产生什么重大影响么?

我觉得未必,把时间维度拉长,技术的进步才是关键的影响因素。

今天的文章是上周在Reddit热度最高的帖子之一,它用很通俗的例子解释了为什么比特币需要闪电网络,以及比特币支付是怎么逐渐进步的。

文章很长,建议先码后看,enjoy~

1

初代:中本聪残破的nSequence 通道

中本聪虽然把产品做出来了,但中本聪的版本(包括支付通道)完成的实在太糟糕。我们不得不自己动手修复它,顺带增加了RBF(译者注:replace‑by-fee,允许用支付更高交易手续费的方式,来替换未经确认的同一笔交易)作为附带功能。

最开始的规则是如果A交易的输入与B交易相同,且A的nSequence更大,那么内存池会将会用A替换B。

0xFFFFFFFF是nSequence能够取到的最大值,这会导致该笔交易被标记为”最终交易”,且不能在内存池中被替换掉。

nLockTime和nSequence正是”nSequence通道”有着如此奇怪规则的原因。nLockTime只能在nSequence小于0xFFFFFFFF时才能起作用。如果nSequence是0xFFFFFFFF,nLocktime就不会起作用。

举一个简单的例子:

1.你去一个酒吧,对酒保说你会在酒吧关门的时候结账。因为我们是在比特币宇宙,时间是以区块高度的形式被测量的,所以酒吧关门的时间是未来的某个区块高度。

2.当你喝第一杯酒时,你会从你的资金里拿出一笔钱,进行一笔交易付给酒保。这笔交易有一个起始为0的nSequence和一个nLocktime(相当于酒吧的关门时间)。你创建这笔交易然后酒保给你酒。

3.如果你想多喝几杯,你需要重新创建类似的交易,把要多付的钱加到给酒保的交易中(所以随着酒钱的增加,交易的输出也不断变大),但是这笔交易的nSequence要比原来的那个增加1。

4.不管怎样,最终你可能还是会因为两个原因离开酒吧:

(1) 酒吧关门了,nLockTime标记的关门时间一到,酒保就可以广播最新的交易,然后让保安不客气把你踢出门。

(2)你不想再喝酒伤肝了,所以你把最新交易的nSequence重签成0xFFFFFFFF,也就是它能到的最大值。这让酒保能够立即拿到他的钱(如果nSequence为0xFFFFFFFF,nLocktine就不再起作用了),所以他就可以让保安客气的把你送出门。

这就是支付通道,它是通过创造一笔”最终”交易来关闭的,这笔交易包含此前的交易。这里当然不存在rounting,因为通道是单向的而且有最大生命周期的限制。但是还是放过中本聪吧,他需要休息,那时他也正忙着发明比特币呢。

还记得我说这种支付通道是残破的么?

这是因为内存池规则不是共识规则,而且不能被验证(在内存池中任何东西都不能在链上验证,每当我听到有人提出”让我们根据内存池的大小确定区块大小吧!”我都要叹气,内存池的状态不能被链上的数据验证)。全节点并不能看到你签名的 所有交易,只有带有最大的nSequence的那笔交易才是真正在链上使用的。

所以你可以像下面这样做:

1.成为吴忌寒的朋友,因为他拥有51%以上的算力。

2.给吴忌寒一些你定的酒作为与你合作的奖励。比如说你定了一百杯酒,你和吴忌寒把酒分了,给他了50杯。

3.当酒吧关门时,吴忌寒让他的矿机挖nSequence为0的那笔交易。就是那笔你只付了一杯酒钱的那笔交易。

4.因为全节点没有办法验证nSequence,它们会接受nSequence=0的版本然后确认,傻傻地把仅付了一杯酒的钱写进区块链。

5.这个酒保被激怒了,从吧台下面拿出一把枪,想把你和吴忌寒打死。

6.吴忌寒用他的魔法力量(其实是矿机的蒸汽)来让子弹减速,结果子弹只是像风吹花瓣一样轻轻接触了你一下。

7.酒保嘴里嘟囔着听不清的话,突然他的衣服被撕开了,他真的变成了一头熊!

8. 你盯着它,心里想着莱昂纳多能从熊的爪子下活下来, 那你也能活下来,况且他只是一个有钱的演员而已,然后你摆好了姿势,嘴里喊着”吃我一招!”

9.有人能继续帮我编下去么?

下面是知识点:

1.遇到熊人非常糟糕。

2.你不能仅仅因为闪电网络不是链上的,就马上否定它,然后启用所谓的”中本聪版本”。

中本聪版本是一个带有nSequence支付通道的半成品,在这个方案中链上交易代表着多个逻辑上交易款项的和,这几乎和现代版本的链下技术做的一样(先不管现代的链下技术到底是如何工作的)。nSequence(单指这个字段,不是指它现代意义上的意思)早在windows Alpha 0.1.0版本就存在了。

3.矿工完全能够绕过内存池规则。实际上,nSequence能够变成一个可选的功能(RBF)是因为矿工被nSequence系统激励着一直遵守RBF规则罢了。

我的意思是,你给吴忌寒的酒,除了能是你给矿工挖特定版本的交易的手续费,还能是什么其他东西呢?

4.中本聪也会犯错,最初的nSequence的设计就是其中之一。今天,我们不再这样使用nSequence了。

改进中本聪最初的版本是比特币开发的一部分,因为随着时间的发展,我们学到了一些中本聪永远不会不知道的东西中本聪是这项科技的一个里程碑。但是他永远不会是最后一个,也不会是最重要的一个,他会被历史牢记,但也只是作为一个先行者的身份。

2

Spilman通道

Spilman通道是激励兼容-限时型单向通道,实际上就是一种改进版的中本聪通道。

现在,我们知道如果你想在交易通道上作弊,酒保会变成一头熊咬你。而且我们知道你是吴忌寒的好朋友,酒保再也不会接受一个能够让顾客和矿工联合起来骗人的支付通道方案。

好消息来了, Jeremy Spilman提出了一个新方案能够让顾客再也骗不到酒保了。首先,你和酒保进行一个这样的仪式:

1.你拿出一些资金,然后创造一笔注资交易付给一个你和酒保之间的2/2多重签名地址。你现在不会广播这笔交易:你只是进行了签名,得到了交易ID。

2.你再创造另一笔交易用来返还的上面资金。这笔交易有一个nLocktime,它的值是酒吧的关门时间再加上一个区块高度。你给它签名然后把这笔退款交易(但不是上面提到的那笔注资交易)给酒保。

3.酒保给退款交易签名,然后又还给你。现在它就是合法的了,因为你和酒保都签名了。

4.现在你把第一笔交易广播到链上。你和酒保等待这笔交易深度确认,然后你再开始消费。

上面的步骤也许对闪电网络用户来说依稀有些熟悉。这是支付通道的资金创建过程!第一笔付给2/2多重签名地址的交易是用来给通道提供资金的。

然后你开始像这样买酒:

1.第一杯酒,你创建一个花费注资交易(也就是第一笔交易)的输出,把酒品的花费发送给酒保,然后剩余的返还给你。

2.你给这笔交易签名然后把它交给酒保,酒保就给你第一杯酒。

3.为了能再拿一杯酒,你要再创建一笔类似的交易,先新酒的钱加到之前给酒保的钱上,然后再把剩余的钱返回给你。你给这笔交易签名又发给酒保,酒保就再给你一杯。

4. 到最后:

(1)如果酒店关门的时间到了,酒保就给最新的交易签名,将需要的双重签名补全然后向比特币网络广播这笔交易。因为退款交易的是广播的时间是关门时间+1,所以在关门以前它不能使用。

(2)如果你的肝受不了所以你想早走,你只需要告诉酒保关闭通道就好了(酒保可以在任何时候广播最新版本的交易来关闭通道,酒保不这样做是因为希望你能够多待一会,多喝两杯)。

(3)如果你仅仅是在酒吧里闲逛但是从来没有买东西,这样的话当到了关门时间+1的时候你就广播你的退款交易,拿回你全部的资金。

现在,即使你给吴忌寒50杯酒,你也不能让他挖最开始的那笔交易(那笔交易只支付了一杯酒的钱),因为这是一笔2/2的多签名地址但是它只有你自己的签名。

你需要酒保的签名让这笔交易合法,但是他当然不会这么傻,酒保不会给出自己的签名让旧版本的交易合法,自己得到更少的钱。

所以,问题被解决了是吧?解决了吗?让我们来试试吧。你拿到了你的资金,把他们放入一个注资交易中,弄好退款交易,确认注资交易… …

一旦注资交易深度确认完成,酒保意味深长的笑了。他叫来了保安,气势汹汹的盯着你。

“我拒绝给你服务”,酒保说。

“好吧,那我走好了”你面带傻笑,”我会用退款交易拿回我的钱,然后在大众点评上给你个大差评!”

“先别急”酒保说。他的声音让你背脊发冷,就像是他还记得你之前玩弄他的事,”瞧瞧刚才确认的那笔注资交易的交易ID。”

“它咋啦?”你面无惧色的问道,说着你打开了你的笔记本电脑,然后找到了一个可靠的区块链浏览器。

接下来的看到的东西把你吓坏了。

“啥玩意?交易ID变了?!你他妈改了我的签名??怎么可能?我把我唯一一份私钥藏在了一个密封的信封里,然后把它放在一个神秘戈壁滩的保险柜里,一群骁勇的游牧民族守护它,他们以自己儿女的鲜血起誓,要誓死捍卫这份秘密!”

“难道你不知道?”酒保笑了。”签名仅仅是非常大的数字。签名中的一个标记可以被改变,从正变到负,或者从负变到正,但是签名仍然是合法的。即使不知道私钥,任何人都可以这么做。但是比特币在生成交易ID时在其中包含了签名,所以这一点小改变也让交易ID改变。有人想把签名从交易主体中分离出去,他们说这样签名延展性(signature malleability)就不再会影响到交易ID了,但是我打赌我可以让我的好哥们吴忌寒拖延这个’Sepsig'(分离签名)计划好长时间。

吴忌寒是个好人,只要我给他51杯啤酒,他就愿意挖那笔改动了的交易”他笑得更开心了”恐怕你的退款交易不会起作用了,因为它想花的那个交易ID根本不存在。

好吧,让我们来谈谈吧。你把你注资交易里99%的资金给我,作为交换,我会给你在链上的那笔交易签名。如果拒绝,那你一毛不剩。但是我和所有的HODLer都会因为流通又减少了一些欢呼雀跃。接受这笔交易你可以剩1%的钱。如果你拒绝我,我也分毫不会损失,好好考虑一下吧!”他的眼睛发着贪婪的光。

学到什么吗?

(1)报复行为很糟糕。

(2 )交易延展性更糟糕。这就是我们为什么要在隔离见证里修复这个bug的原因。MtGox宣称他们就是被这种漏洞攻击了,有人一直搞乱他们交易的签名,导致他们资金去向被重复提款,但是修复交易延展性更主要的是为了支持支付通道。

(3) 把签名包括进去取哈希,最终决定交易ID的设计是一个错误。中本聪犯了许多这样的错误。我们必须重申”中本聪并不是一个有着无限智慧的天龙人”。

3

CLTV保护型Spilman通道

使用CLTV做退款分支(branch)。

这和Spilman通道的区别是退款交易被退款分支给代替了。这种方案只有在2015年后OP_CHECKLOCKTIMEVERIFY(CLTV)被启用才成为可能。

就像我们在Spilman通道里讨论的那样,交易延展性导致任何在链下被预注册的交易都可以在注资交易未被确认的时候通过改动注资交易的签名使预注册的交易无效化。

这可以通过简单地在比特币脚本中把一些特殊的要求加到特定分支中来避免。现在,退款分支可以为支付通道创造一个最大的生命周期,通过我们之前对OP_CHECKLOCKTIMEVERIFY的介绍,我们知道这只有在有一个预注册的nLockTime的时候才是可行的。

通过CLTV,我们可以在你要支付的脚本中加入很多分支判断使它能够避免上面的问题。

为了设定好注资交易,你现在不必再向一个2/2地址付钱了,你现在要向一个脚本支付资金,这个脚本基本就相当于一个一开始是2/2但经过一段时间就变成单签名的地址。这样就不再需要预注册的交易了。

你可以稍后使用任何已确认注资交易的交易ID来创建你的退款交易。既然注资交易已经被确认,所以也就不可能再更改交易ID了。

4

Todd微支付网络

闪电网络最直接的前辈就是由Peter Todd引入的hub-spoke模式。

在这种模式中,付款人和收款人并不直接联系,付款人和收款人都连接上一个中心hub。

这就使得任何的付款人可以向任何的收款人使用在hub上的同一个支付通道付费。相似的,它也允许任何的收款人从任何的付款人那里使用同一个通道收款。

还记得之前的Spilman的例子吗?当你向酒保打开一个通道后,你必须等待注资交易确认。这可能会花费一个小时的时间。再想象一下你需要和所有你要付款的人开通通道。这并不具备可拓展性。

所以hub-spoke模式有一个清算中心,用来将资金从付款人转移到收款人。”Moonbeam”项目采取了这个模式。当然,这个模式hub会知道谁是付款者和收款者,所以hub有审查交易的能力。当然,通常hub更有效率的审查方式是不再维护它想审查的付款人和收款人的通道就好了(因为如果hub不处理这笔交易那通道里的资金只能被锁在里面毫无用处)。

拥有监控支付的能力意味着hub可以贩卖私人交易数据来牟利。在今天,这种对隐私的破坏是不能容忍的。

另一个值得注意的点是如果这样的网络真的被大规模推广了,但是它只有单向的通道可以使用。但是一个人可能是付款人,也可能是收款人,你需要分别创建一个收款通道和付款通道。更糟糕的是,如果你想把钱从收款通道转移到付款通道,你需要在链上把他们都关闭然后再开通一次。

5

Poon-Dryja闪电网络

Poon-Dryja是双向双参与者通道。

Poon-Dryja通道的机制有两个重要的改变:双向且没有时间限制。

最初的中本聪版本和Spilman变体都是单向的:这里存在不同的两方,付款者和收款者,如果收款者想要退款,或者收款人想要买一个付款人的东西,他们也不能使用同一个通道。

Poon-Dryjam机制可以使通道变成双向的,你不只是一个付款人或者收款人,只要你的对手方在线,你可以任意的收款和付款。

更进一步讲,不像是Spilman变体,通道没有时间限制。你可以让通道维持到你想要的任何时候。

这两种特性,合在一起形成了一种大多数人都没有意识到的强大的拓展性。在单向的支付通道中,你需要为收钱和付钱单独开设一条通道。你需要定期的在链上执行操作来”逆转”支付通道的方向。其次,因为Spilman通道有一个固定的生命周期,你必须周期性的关闭和重开通道。

有了双向、无限生命周期的通道,可能你一生只需要进行两笔链上交易,一次在你开通通道时,一次在你死后遗产分配时。这就是这种通道的强大之处。

我不会在去解释Poon-Dryja双向通道的交易结构,它很复杂,而且你还可以在其他地方找到简单易懂的图示来搞明白它的机制。

下面我们来讲一下Poon-Dryja通道的一些人们常常忽视的缺点(因为这些缺点被完美的解决了)。

你必须存储这个通道所有的撤销密钥。通道的每一次更新你都需要存储一个撤销密钥,也就是说仅仅对一个通道来讲,你需要在你的一生中存储上百万的密钥,大小会到几兆。

RustyReddit解决了这个问题,我们可以从一个种子密钥开始生成所有的密钥。每一个密钥都是那个种子密钥不断重复的取SHA256。

比如,我告诉你我的第一个撤销密钥是SHA256(SHA256(seed))。你可以在O(1)中存储它。等到下一次撤销时,我告知你撤销密钥是SHA256(seed)。从SHA256(seed)开始,你自己就可以计算SHA256(SHA256(seed))(也就是之前的撤销密钥)。所以你只需要记住最近的撤销密钥就可以了,你可以通过计算得出之前的每一个密钥。当你开通一个通道时,你会在你的种子密钥上执行上百万次SHA256,然后把最终结果作为第一次使用的撤销密钥,每当你需要一个撤销密钥时你只需要去掉一层SHA256。RustyReddit还提出了一种效率很高的储存结构O(log n),shachain。如果出现状况,你能够很快的找到原来的撤销密钥。人们现在不再讨论这个储存问题了,因为它被非常完美的解决了。

我想强调的另一件事是,当闪电网络的论文从老的 hub-spoke模型里被发展出来时,现代的闪电网络吸取了教训,不再区分”hubs”和”spokes”了。

在闪电网络中的任何节点都可以当作其他节点的hub。所以,即使你在执行过程中只付款,或者只转发交易,至少最终你仍然部分是转发节点(”hub”)。这大大的减少了只有几个hub节点导致的隐私问题:转发节点只能得到通过他们的很少的信息,因为付款人和收款人之间的距离太大了,最终的收款人和付款人可以是闪电网络上的任何人。

又到了知识点时间:

(1) 只要我们足够努力我们就可以做到去中心化!

(2) 只要我们都是hub,hub也可以变成一个好东西。

(3) 聪明的人能够解决问题,这也是他们聪明的原因。

6

未来

在闪电网络之后,有Decker-Wattenhofer 双工微支付通道(DMC)。它使用了一种奇妙的”nSequence递减通道”,使用一种新型的nSequence(不是中本聪残破的那一款)相对时间锁语义(relative-timelock semantics)。它使用多个”递减nSequence”结构体,终止于一对Spilman通道中,两个方向各一个。

通道结构实际上可以在其中包含更多通道构造(Decker-Wattenhofer将一对Spilman通道放入一系列”递减nSequence通道”),这引导我们更进一步提出了Burchert-Decker-Wattenhofer通道工厂。

基本上是说,你可以持有多个双参与者通道结构,这些通道结构又被包含在一个更大的多方”通道”里(也就是说在一个”工厂”里持有多个通道)。

继续更进一步,我们还有有Decker-Russell-Osuntokun或者”eltoo”结构。这篇文章已经够长了,我准备以后再讨论它。

比特币链下扩展性比你想象的还要强大的多。

作者:almkglor

翻译:空岛飞行

原文地址:

Technical: A Brief History of Payment Channels: from Satoshi to Lightning Network from Bitcoin