首页/ 入门科普/ 抗ASIC的工作量证明:究竟是现实还是幻想?

抗ASIC的工作量证明:究竟是现实还是幻想?

本文是头等仓精选的世界门罗大会演讲第一辑。离RandomX上线还有一个月时间,门罗是否能迈向一个新的境界,加密货币否能在挖矿平等化这个领域到达前所未有的高度,取决于10月份的升级和之后的网络表现。推荐广大门罗爱好者,尤其是矿工阅读。

原文标题 | 抗ASIC的工作量证明:究竟是现实还是幻想?

演讲人 | Howard Chu:

软件工程师和优化天才,拥有世界上最快的多处理器TCP堆栈,世界上最快的Appletalk堆栈,世界上最快的LDAP服务器,比实时语音识别更快,比实时雷达数据解复用器/解码器更快等。

抗ASIC的工作量证明:究竟是现实还是幻想?配图(1)

前言

原本的CryptoNote白皮书倡导“平等主义”挖矿,并将“平等主义”的思想定义为CryptoNight的PoW算法的愿景。随着时间推移和技术进步,专业挖矿硬件制造商克服了所有CryptoNight中设定的技术障碍。关于抵抗ASIC是否切实可行或可取的辩论仍未停止,但迄今Monero项目仍坚持“平等主义”挖矿原则。本文将讨论ASIC存在的必然性,以及降低ASIC固定函数挖矿优势的方法。RandomX,是一款我们倾尽毕生经验为Monero开发的新型PoW算法。

演讲全文:

我是Howard Chu, Symas公司的创始人之一。上周刚刚庆祝了Symas创立二十周年,而本人写软件也已有四十年光景。从开源运动兴起时我就是开源热衷者,我写过所有GNU实用工具、编译器、调试器、链接器、texinfo等等代码。地球上大部分的电脑运行着我写的软件,甚至太空轨道还在运行着我的软件,从未崩溃过。这些年来我做了很多有意义的事情,我喜欢快速运行的软件。在安全性方面:我还做了大量加密技术、安全认证和各种安全系统方面的工作。

切入正题,ASIC抵抗是何含义?为何要抵抗ASIC?如何做到?

抗ASIC的大背景是源自Monero的一款CryptoNote协议,大约于2013年~2014年设计完工。如果通读一下CryptoNote白皮书,就会发现它大大完善了比特币的设计缺陷。不仅比特币的假名概念无法保护用户隐私,而且比特币软件中的硬编程常数明显严重地影响了自身的可扩展性。虽然比特币的思想是去中心化,但其实早在2013年和2014年,比特币生态系统就出现了高度中心化。

早在2013年矿工的算力就达到高度集中,51%攻击的可能性很高。如果两个矿工串通,网络就会崩溃。

最初矿工采用PC、CPU挖矿,逐渐人们发现GPU更擅长SHA-2散列运算,于是GPU进入辉煌时代,矿工越来越多,接着业余的ASIC设计师加入挖矿大军,最后大量专业且商业化的ASIC设计师占据了主流。

按照今天的标准,对比第一代ASIC,如今的ASIC只是改进了稍稍,而挖矿效率已提升50倍。现在大家都不会在自己的计算机上挖比特币,因为ASIC的算力已达数百万级,比CPU挖矿效率高度好几百万倍。从比特币身上我们汲取的经验是:“嘿,看看吧,当你开始依赖专业硬件时,网络自然而然会出现中心化。”而网络中心化一直是我们反对的方向,中心化意味着会产生信任矛盾。其实先前Kristy也提到过,ASIC设计师更喜欢自己用芯片挖矿,而非出售ASIC芯片。也许设计师们会在芯片被淘汰后,将其出售给大众。

为何集成电路如此高效?围绕这个背景,我仍要聊聊比特币SHA-2 ASIC。SHA-2 ASIC硬件本身非常简单,只专注于挖矿,所以它设定了固定函数,这样一来挖矿对于SHA-2 ASIC相当简单。实际上SHA-2算法的初衷是方便计算。所以矿工需完成的工作量很简单,算法直线运行,没有决策点,一边开始计算,另一边得出结果,非常直接。

如果仔细观察SHA-2硬件,你会发现它有12个简单的组件。你们可能无法读懂SHA-2右边的电位图,其实它只是由一些加法运算符以及一些暂存器组成,但这些只是集成电路极小的一部分。

集成电路既不做决策,也无分支,全部硬件都用来寻找难题答案,既不耗费内存、时间,也不浪费其他资源。这样一个集成电路,其一枚芯片就能轻轻松松承载上万个实例,这就是如今比特币挖矿的大环境。

不只是CryptoNote协议抵抗ASIC,比如以太坊的Ethash也抵抗ASIC,两者都采用了相同的哲学思路——内存密集型相比之下CryptoNote设计者在抵抗ASIC上有点保守了。CryptoNote非常出色地运行了3至4年,在这段时间里,ASIC技术追上了CryptoNote,CryptoNote无法抵抗ASIC了。虽然以太坊的Ethash算法依然运作良好,但距离抵抗ASIC失败的日子也为时不远。

于是出现了另一种多散列算法,但事实它也根本无法抵抗ASIC。因为多散列算法只是捆绑一堆不同的哈希算法,而各个算法又极其简单,与SHA-2 256的简单性不相上下,无决策点,你可以将多散列算法拆分为一个个单独组件,以自己喜欢的方式组合起来。而ASIC能处理多个散列算法组合任务,且非常高效。

所以我们现在要开发的是无静态执行流的动态算法。除了RandomX,还有几个算法也是这种情况,后文我会稍稍提及。有趣的是我能想到的第一个例子是以太坊,在开发Ethash之前,以太坊使用了一个与RandomX相似的算法,但如果你仔细检查这个算法,我敢担保,它是不完善的。以太坊将这个算法当作原型,但从而真正完整开发出来。

去年三月初,我提出了RandomJS的构想,花了大概6个月或8个月的时间做研究,直到查明RandomJS有一些无法修复的错误,是挖矿方法上的漏洞,于是便放弃了。另一个大家可能有所耳闻的是Kristy团队开发的ProgPow。ProgPow算法专注于GPU,利用GPU大量并行运算优势,使挖矿效率提升。但它生成的随机代码,在我看来,依然过于简单。

目前Monero网络使用的是Cryptonight-R算法。之所以使用Cryptonight-r是因为我们尚未完成RandomX开发,于是将RandomX部分概念移植到Cryptonight上,做权宜之计。

有些人质疑我们偏好CPU挖矿的决定,认为我们正在抛弃GPU矿工,放眼全球,GPU占比份额不大,CPU的部署数量更多,CPU的年采购数量与时俱增,尤其是智能手机这一块,CPU是消费增长最快的组件。当前世界上有22亿智能手机用户,用户每年购买15亿CPU,CPU数量越庞大,升级就越快。

就拿个人电脑的升级周期来说,大多数人购买电脑的频率不会超过2~3年购买一次,而大多数智能手机用户一直追求最新最先进的技术。这就是我们技术偏好CPU的原因,并且有庞大的智能手机市场做后盾

RandomX是我们为Monero虚拟机量身定做的随机生成机器语言程序。RandomJS中存有一个问题,任意8位随机数列都是一个有效指令,即你必须生成遵循Javascript语法的随机语言程序,一旦你强加Javascript语法于RandomJS上,想要随机生成一个可执行程序就更难。所以我们现在探讨的是一种既无语法规则,生成的所有随机数又都为有效指令的机器语言。我将这种状态称之为“适度复杂”,如果比较RandomX虚拟机与因特尔或AMD CPU,就会发现RandomX的指令集依然非常小。但RandomX完成了我们所需的大部分工作,并且随机语言程序中使用的指令组合也是模仿实际用户程序中的运算类型。

如果只是比较各大算法抵抗ASIC的特性,我认为第一代算法对ASIC的抵抗性为0。后面的一代都使用了内存密集度作抵御,而现在Monero使用的是随机编程和其他运算的动态算法。在RandomJS和RandomX中,我们也使用了其他算法都避开的浮点数,因为浮点数根据舍入规则和舍入误差的不同,很容易算出不同的结果。因此在PoW算法中做浮点数运算是一件苦差事,因为你需要每个人都必须得到一致的答案,但我认为我们搞定了这个问题。

我们偏好CPU是想要充分利用CPU的优势——他们能够运行的代码范围非常之广。如果你想为此制造一台ASIC,你很可能制造出一台CPU。不仅CPU更容易访问,而且它的指令集几乎都是相同的。有同样的整数运算集,有分叉指令,可以轻轻松松地定义适用任何CPU设备运行的子集。CPU可以在ARM、因特尔和AMD上,以及PowerPC等等设备上运行。与CPU相反,GPU采用的都是专用指令集,并且这些指令集的功能都不相同。AMD指令集甚至都没有我们使用的那种乘法运算,因此如果偏好GPU情况会更糟,子集更有限。我们的基本共识是运算工作必须是动态的,因为如果我们只有一组固定的运算,那么要制造专用的芯片是很容易的,这是我们不愿意看到的。

现在,你认为什么是工作量证明算法呢?如今工作量证明只是一个延迟循环。工作量证明的目标是耗时又耗能,而且还低效。这于我而言,是一种精神上的打击,我花费毕生精力在构建高效软件、调优编译器上,只为追求低能耗高效率。但你静下心沉思时,就能发现哪种运算昂贵,哪种运算低廉。这赋予我们一个如何写出最低效算法的特殊视角。另一个我陷入的难题是隐私、去中心化这两样东西与效率无法共存。高效系统无一例外都倾向于中心化,事实上,不仅工作量证明证实了这一点,大部分系统中心化的话效率也就更高。比如网络通信,你如何保证跨网络的通信安全?整个周末我们探讨了大量隐私相关话题,大家将隐私(privacy)和保密(secrecy)混为一谈,两者有一个很大区别:隐私只是保密的一个子集。如果你在两个端点间有一条加密通信渠道,比如TLS协议层,你保证了通信渠道中的信息安全,但事实你并没有保证通信渠道的安全。外人知道你在通信,虽是私人间的对话,但并不保密。保护自己的隐私并不会破费太多,AES加密通道费用相当低廉,而且我们有AES加速硬件。但如果要保密某件事,防止他人得知,那么成本就会高出许多。保证通信渠道隐私,就必须在渠道中添加大量噪音,用噪音掩盖你真正发送的信息。所以当你追求高效时,就与隐私和保密相违背,因此采用低效、去中心化的工作量证明着实困扰着我,但我们还是努力去攻克它。

我们想要把RandomX设计成一种既低效又耗能,还要应用大量的CPU的算法。从一张AMD Zen core的区块图可以得知,在图的上方是前端,有指令缓存、解码器、分叉预测器、运算缓存;在中层,有整数运算单位、浮点数运算单位;在底层有内存接口和数据缓存。

运行RandomX需要应用Core的所有组件,除此之外不应用任何组件。CPU芯片拥有其他交互界面。RandomX有一个PCI Express接口,有一个管理总线用于芯片间通信、系统管理,这些是我们无法真正高效利用的功能,因为这些功能都是某些设备专有的。虽然无法将这些功能从一枚芯片解析到另一枚芯片上,但我们可以利用所有核心组件和内存接口。

如何做到?先生成一个随机程序,将随机程序翻译为机器代码,然后执行随机程序并转换输出,最有趣且最重要的是第三步。我们期望第一步和第二步的成本趋近于0,因为这两步并没有真正贡献。

前面我也有提到,生成随机程序这一步有点麻烦,如果你使用的是一种高级语言,就必须根据严格的规则构建程序,否则代码不会执行程序。所以标准的方法是构建一棵抽象语法树,树上的每一个支点都是随机程序的语句。从抽象语法树下载源代码,然后将源代码提交给编译器,编译器解析源代码,并转换为一棵抽象语法树。这样会产生大量多余工作。如果构建一个ASIC芯片来处理,就可以避免多余工作,提高效率。因此构建RandomJS的想法破裂了。现在最好的方法是生成随机字节,不用语法,不按照构建规则。

然后将随机程序转换为CPU原生机器代码,并非只适用x86架构,还需适用当今ARM和CPU这样的大型架构。因此我们需要使用简单的机器指令,才能轻松地映射到真正的机器指令中。只是我们没有剩余时间来开发一个优化版的编译器,因为分析和重写代码花费的时间,等于没有生成哈希的时间。

所以实际的程序都必须应用尽可能多的CPU组件,为了使用芯片上所有的可用缓存层,我们解析了大量CPU配置文件。我们正在使用芯片上的指令缓存,充分利用整数运算以及浮点数运算,真正打败了内存控制器。

我们使用的是Blake 2B,一个专门运行在CPU设备上的加密哈算法,来计算最终结果。对于大型计算,我们仍使用AES算法,AES运算出色是因为大多数现代CPU都有AES加速硬件。如果无加速硬件,就不能应用AES算法。

如果你要分析一个程序,会出现一个问题,你需要高度优化部分运算,你可以查看该程序计算你的交易是否较慢,如果慢你可以跳过。如果运算较快,我就会执行该程序,快速获得哈希值。因此为了优化部分运算,我们必须链接多个程序,强制执行实现,要么运行整个程序,要么跳过程序。

链接程序的一个关键阻碍是,验证时间必须与Cryptonight大致相同。因此给程序不能过于复杂。

我们使用大量内存是让你不再使用芯片内存,所以我们使用2字节以上,现实中如今的芯片可以建立2字节内存,但非常昂贵。我们预计内存数量能满足未来几年的需求。而且,未来我们可能会增加内存大小。

我们的轻模式无需2字节RAM内存,只需256 mb即可,如果进一步减少内存,减少至128mb,速度上可能要慢上3700倍。

当前RandomX代码已预备好运行在monerod x86系统中。但我们仍需在ARM上实现RandomX。GPU方面工作正在进行中,还支持在Nvidia、CUDA实现以及用一种OpenCL版来支持AMD GPU(非通用版OpenCL),此版本的OpenCL仍使用大量AMD特定汇编代码。当前我们已完成4次安全审计。

本文来源于陀螺财经专栏作家:头等仓,头等仓简介:专业服务于价值投资者 微信添加:13394046305

现已在陀螺财经发布126篇内容,累计总热度10万+。陀螺财经现已开放专栏入驻,详情请见入驻指南:https://www.tuoluocaijing.cn/article/detail-27547.html

头等仓专栏:https://www.tuoluocaijing.cn/columns/author309861

本文网址:https://www.tuoluocaijing.cn/article/detail-63569.html

收藏

免责声明:
1、本文版权归原作者所有,仅代表作者本人观点,不代表陀螺财经观点或立场。
2、如发现文章、图片等侵权行为,侵权责任将由作者本人承担。

相关文章

头等仓
个人认证

126篇

文章总数

10万+

总热度

扫描二维码关注

热门文章

rss订阅