5万亿位数圆周率-新世界纪录
挑战个人计算的极限。。。我们还能走多远?
作者:Alexander J.Yee和Shigeru Kondo
(上次更新时间:2016年9月22日)
对于任何感兴趣的人来说,这是最近一个我回答的堆栈溢出问题.
2011年10月17日:这一记录已提高到10万亿位数。
这是我们的后续行动上一次公告我们计算了5万亿位数的Pi。本文详细介绍了用于计算的一些方法以及计算的硬件和完整时间表。
你们中的一些人知道这会发生。。。只是时间问题。(以及位数)
虽然我们在运行时对这个计算非常保密,但任何关注我的网站或我的XtremeSystems线程2月至5月之间,我们很容易猜到我们正在试图创造一项世界纪录。
三。 |
1415926535 8979323846 2643383279 5028841971 6939937510 : 50 5820974944 5923078164 0628620899 8628034825 3421170679 : 100 |
2962457053 9070959679 6673211870 6342459769 2128529850 : 999,999,999,950 2976735807 0882130902 2460461146 5810642210 6680122702 : 1,000,000,000,000 |
9354516713 6069123212 1286195062 3408400370 1793492657 : 1,999,999,999,950 8386341797 9368318191 5708299469 1313121384 3887908330 : 2,000,000,000,000 |
3840840269 5893047555 2627475826 8598006396 3215856883 : 2,699,999,989,950 9256371619 3901058063 3448436720 6294374587 7597230153 : 2,699,999,990,000 8012497961 5892988915 6174704230 3863302264 3931687863 : 2,699,999,990,050 3126006397 8582637253 6739664083 9716870851 0983536511 : 2,699,999,990,100 |
5628334110 5221005309 8638608325 4364661745 5833914321 : 2,999,999,999,950 9150024270 6285788691 0228572752 8179710957 7137931530 : 3,000,000,000,000 |
5209957313 0955102183 1080456596 1489168093 0578494464 : 3,999,999,999,950 3638467628 3610607856 5071920145 5255995193 8577295739 : 4,000,000,000,000 |
2597691971 6538537682 7963082950 0909387733 3987211875 : 4,999,999,999,950 6399906735 0873400641 7497120374 4023826421 9484283852 : 5,000,000,000,000 |
单击此处访问部分数字。 |
|
计算统计-所有时间均为日本标准时间(JST).
以下是完整的计算统计数据。与所有使用y-cruncher——一个多线程Pi程序,包括屏幕截图和验证。由于计算是在多个会话中完成的,因此没有一个屏幕截图能够从开始到结束捕捉整个计算过程。这里提供的屏幕截图显示了计算的大部分内容。
在近藤茂的桌面上进行了90天的主要计算。这台计算机专门用于此任务。
在计算过程中,通过软件ECC检测并纠正了一个错误。由于错误已被纠正,最终结果不受影响。计算错误被认为是由硬件异常或硬件不稳定引起的。
由于这种计算的规模,需要大量的内存:
- 执行计算大约需要22 TB*的磁盘。
- 还需要3.8 TB的磁盘来存储十进制和十六进制数字的压缩输出。
如果数字存储在未压缩的ascii文本文件中,十进制和十六进制数字的总大小将为8.32 TB。
*本文中使用的所有单位均为二进制:
GB=230字节
TB=240字节
Pi-计算 90天
开始时间:2010年5月4日下午6:19(JST) 完成时间:2010年8月3日上午1:12(JST)
|
Pi-验证 64小时(小学-Bellard的BBP) 66小时(二级-普劳夫BBP)
开始时间:参见详细时间表
完成时间:参见详细时间表 |
计算步骤 |
时间 |
系列汇总: |
73天 |
平方根: |
63.3小时 |
最终乘法: |
41.6小时 |
基本转换: |
8.2天 |
验证基准转换: |
45.6小时 |
总时间*: |
90天 |
验证文件:验证-Pi-5000000000000.txt |
请注意,多核效率%不准确。实际效率约为85%。
|
*总时间还包括将数字输出到磁盘所需的时间,以及从计算错误中恢复所需要的时间。
有关此计算相关事件的详细时间表,请看这里.
目的。。。为什么?
因为是皮。。。因为我们可以!
更严肃地说:
在Fabrice Bellard宣布在“相对便宜”的桌面上实现2.7万亿位数后,很明显,个人计算的极限要高得多。
Shigeru Kondo和我想看看如果我们使用更强大的硬件,我们能做得多好。
我们俩都是硬件狂热者。我们俩(尤其是近藤茂)都有一些功能强大的机器供我们使用。
因此,我们决定看看我们可以在多大程度上利用个人拥有的硬件来推动个人计算的极限。
与Fabrice Bellard注重效率和从少量硬件中获得最大收益的记录不同。我们的计算更侧重于从大量硬件中获得最大的性能和可扩展性。
我们能在一台机器里塞进多少硬件,还能让它更快?
这种规模的计算面临的主要挑战是,软件和硬件都被推到了极限之外。
对于如此长的计算时间和如此多的硬件,失败不仅仅是一种可能性。这是一个给定的。有太多的组件可能会出现故障。
所以问题是:
- 在保持可接受的可靠性水平的同时,硬件可以扩展多少?
- 有可能在软件中建立足够的容错能力来覆盖硬件故障吗?
硬件:Shigeru Kondo的桌面
Shigeru Kondo的计算机具有以下规格:
- 处理器
- 2 x Intel Xeon X5680@3.33 GHz-(12个物理内核,24个超线程)
- 内存
- 96 GB DDR3@1066 MHz-(12 x 8 GB-6通道)-三星(M393B1K70BH1)
- 主板
- 华硕Z8PE-D12
- 硬盘驱动器
- 1 TB SATA II(启动驱动器)-日立(HDS721010CLA332)
3 x 2 TB SATA II(存储Pi输出)-希捷(ST32000542AS)
16 x 2 TB SATA II(计算)-希捷(ST32000641AS)
- Raid控制器
- 2 x LSI MegaRaid SAS 9260-8i
- 操作系统
- Windows Server 2008 R2企业版x64
- 建造人
- 近藤茂
- 图片
- 单击放大。
-
使用两台单独的计算机进行验证。这两台计算机都有其他任务,不专门用于计算。
验证的所有工作都是使用空闲的CPU时间完成的。
单击此处查看参与此计算的计算机的完整列表。
软件:y-cruncher-一个多线程Pi程序/基准
计算软件:
用于主要计算的程序是y-cruncher v0.5.4.9138阿尔法。
请参阅主页:y-cruncher——一个多线程Pi程序
y-cruncher是一个功能强大的多线程程序/基准测试,在计算机爱好者社区中越来越受欢迎。截至本文撰写之时,它还保持着为其他几个著名常数计算的大多数数字的世界纪录。(其中包括:e(电子),2的平方根,黄金比例,Euler-Mascheroni常数,2的自然对数,阿佩里常数、和加泰罗尼亚常数.)
y-cruncher有几个方面与大多数其他类似的Pi-cunching程序不同:
- 它使用最先进的算法实现前所未有的计算速度。其中许多方法和算法都是新开发的,并首次在y-cruncher中进行了测试。因此,它们还没有被其他程序使用。
- y-cruncher可扩展到多核。大多数其他多线程Pi程序无法扩展到多个内核之外,并且无法充分利用多个内核机器,例如用于此Pi计算的12核/24线程计算机。
- y-cruncher支持使用多个硬盘驱动器作为分布式内存存储来进行非常大的计算。
- y-cruncher对硬件错误具有容错性。它能够检测并从硬件异常或不稳定引起的微小计算错误中恢复。这对于非常长的计算非常重要,因为硬件故障的可能性是不可忽略的。
用于计算的准确版本为:
y-cruncher v0.5.4.9138 Alpha(PB)-x64 SSE4.1~ Ushio
这个版本是v0.5.4的早期私有beta。它稍作修改,以显示计算进度的更多细节。(所有公共版本仅显示百分比。)
验证软件:
用于验证的程序是y-cruncher BBP v1.0.119.
请参阅主页:y-cruncher BBP公司
该程序使用BBP公式实现Pi的数字提取算法。其唯一目的是验证主要计算结果。
这两个程序都是我(Alexander J.Yee)编写的,可以从各自的页面下载。
对于使用过y型压榨机并对其工作原理感到好奇:
这个网页是我写的第一篇文章,它揭示了y型压榨机……尽情享受!
贡献的计算机
虽然主要的计算是在一台计算机上完成的。还有其他电脑参与其中。下面是一个完整的列表,详细列出了参与此计算的所有计算机。
计算机/位置 |
所有者 |
主要规格 |
内部存储规范 |
任务 |
主要 (日本) |
近藤茂 |
5月1日之前:
处理器:2 x Intel Xeon X5650@2.66 GHz
内存:96 GB-DDR3 ECC@1066 MHz
主板:华硕Z8PE-D18
操作系统:Windows Server 2008 R2企业版x64
5月1日之后:(用于主要计算)
处理器:2 x Intel Xeon X5680@3.33 GHz
内存:96 GB-DDR3 ECC@1066 MHz
主板:华硕Z8PE-D12
操作系统:Windows Server 2008 R2企业版x64 |
控制器:2 x LSI MegaRaid SAS 9260-8i
1 TB-启动 3 x 2 TB(Raid 0)—存储数字 16 x 2 TB-计算 |
执行主要计算 |
Ushio公司 (伊利诺伊州埃文斯顿) |
亚历山大·叶 |
处理器:Intel Core i7 920@3.5 GHz(OC'ed)
内存:12 GB-DDR3@1333 MHz(OC'ed)
绘图:EVGA GeForce GTX 275
主板:华硕狂暴II基因
操作系统:Windows 7旗舰版x64 |
6月19日前:
1.5 TB希捷-启动 1 TB希捷-其他。保管部 4 x 2 TB Hitachi-代码测试驱动器
6月19日之后:(夏季离线)
1.5 TB希捷-启动 1 TB希捷-其他。保管部 |
运行BBP公式以验证主计算。
这是我当时的主要电脑。这些运行是在主计算过程中使用空闲的CPU时间完成的。 |
Nagisa公司 (加利福尼亚州福斯特市) |
亚历山大·叶 |
3月19日前:
处理器:2 x Intel Xeon X5482@3.2 GHz
内存:64 GB-DDR2 FB-DIMM@800 MHz
绘图:XFX GeForce GTX 9800+
主板:泰恩·坦佩斯特S5397
操作系统:Windows Vista旗舰版x64
3月19日之后:
处理器:2 x Intel Xeon X5482@3.2 GHz
内存:64 GB-DDR2 FB-DIMM@800 MHz
绘图:PNY GeForce GTS 250
主板:泰恩·坦佩斯特S5397
操作系统:Windows 7旗舰版x64 |
3月19日前:
控制器:SuperMicro AOC-SAT2-MV8
64 GB SSD(G.SKILL)-引导 750 GB-希捷-其他。保管部 4 x 1 TB希捷-代码测试驱动器
6月22日前:
控制器:SuperMicro AOC-SAT2-MV8
1.5 TB希捷-启动 750 GB-希捷-其他。保管部 4 x 1 TB希捷-代码测试驱动器
6月22日之后:
控制器:SuperMicro AOC-SAT2-MV8
1.5 TB希捷-启动 4 x 1 TB希捷-代码测试驱动器 6 x 2 TB Hitachi-代码测试驱动器
7月8日之后:
控制器:SuperMicro AOC-SAT2-MV8
64 GB SSD(G.SKILL)-引导
1.5 TB希捷-数据 8 x 2 TB Hitachi-代码测试驱动器 |
全天候待命,以处理主计算过程中可能出现的任何紧急问题。
在整个计算过程中,这台计算机主要用于其他不相关的任务。
这台计算机的主要贡献在于y型压榨机.
它对实际计算本身贡献甚微。
在开发过程中,这是迄今为止我拥有的最重要的计算机,因为它是我拥有的唯一一台可以测试内存密集型代码的机器。 |
请注意,至少有8台其他计算机参与了y型压榨机。但除了几台引人注目的笔记本电脑外,大多数其他机器的规格都不太理想,不值得一提。(他们也没有参与实际计算)
用于计算的公式
主要计算采用以下公式:
Chudnovsky公式:
使用以下两个BBP公式进行验证:
普劳夫公式:
贝拉德公式:
Chudnovsky公式与二进制分割一起用于计算Pi的415241018610个十六进制数字。(+大约40个安全数字)
为了验证十六进制数字的正确性,使用BBP公式直接计算各个位置(包括4152410118610位)的十六进制数字。
两次主要验证运行包括运行两个公式,以计算以4152410118610结尾的32个十六进制数字。这些是在两台不同的计算机上同时完成的-“Ushio”和“Nagisa”。两个计算同时开始。
较快的公式(Bellard)分配给较慢的计算机(Ushio),较慢的公式(Plouffe)分配给较快的计算机(Nagisa)。
因此,两次计算的结束时间大致相同(分别为64小时和66小时)。
使用BBP公式的后续运行仅使用“Ushio”进行。
进行了一次基数转换,将以16为基数的数字转换为以10为基数的。这产生了5000000000000个十进制数字。(+大约50个安全数字)
使用模块散列检查验证基数转换。(请参见验证的充分性)
验证的充分性
验证方法与Fabrice Bellard用于验证其2.7万亿位数记录的方法类似(如果不是完全相同的话)。
与大多数世界记录规模的计算不同,只执行了一次主计算。为了提供足够的冗余以确保计算的数字是正确的,在计算中添加了几个错误检查步骤。
十六进制数字的验证
如前一节所述,十六进制数字是通过直接计算各个位置的数字并与主计算结果进行比较来验证的。这与模块化哈希检查最后乘法足以验证主计算的所有数字。
我们将首先列出一些关于高精度算术的断言。
断言#1:最后一个数字正确->所有数字都正确
这种假设并不总是成立的。我们将回到这一点。
断言#2:浮点(N x N->N位)乘法之前的任何错误都将传播到乘法之后的最后一位。
基于乘法的性质,这个断言显然是正确的。证据将被省略。
断言#3:乘法过程中的任何错误都不会传播到乘法后的最后一位。
根据错误发生的位置,产品的最后数字可能会或可能不会受到产品期间发生的错误的影响。
(如果在逆变换或基于FFT的乘法的最终执行中发生错误,则尤其如此。)
推理:
- 如果断言#1成立,则BBP公式足以验证所有数字。
- Chudnovsky的公式以最后一个浮点(N x N->N位)乘法结束。
根据断言#2,如果最终乘法中没有错误,断言#1将保持不变。
- 这只留下了一个错误的地方。最终乘法本身。但最后的乘法是使用模块化哈希检查.
- 因此,计算中的任何错误都将传播到最后一位,或者模块化哈希检查将失败。
十进制数字的验证
基数转换后,以16为基数和以10为基数都可以使用Pi。
假设以16位为基数的数字是正确的,则以10位为基数进行验证,如下所示:
N=所需的小数位数(5000000000000位)
p=64位素数
计算(使用十进制算法):
计算(使用二进制算术):
如果A=B,那么“概率极高”,转换是正确的。
在这种情况下,“极高概率”意味着:如果转换不正确,A=B的概率约为1/264.
算术算法
y型压榨机以little-endian格式将大整数存储为32位整数字数组。
浮点数存储为带有符号和64位指数的大整数。
以相同的方式存储在磁盘上的大数字,但使用文件句柄而不是指向内存的指针。
所有基本算术都使用32位整数。64位整数仅用于进位处理和索引。
自y型压榨机不使用汇编或内联汇编,由于C/C++中缺少用于进位处理的128位整数类型,因此不可能使用64位字。
尽管如此,这并不是一个主要的缺点,因为y型压榨机实际上,用整数单位做算术只花很少的时间。大部分运行时间都花在执行向量SSE和暂停内存和磁盘访问上。
因此,对于小型计算,瓶颈是SSE浮点单元的吞吐量。
对于大型计算,瓶颈是内存带宽或磁盘带宽,具体取决于硬盘驱动器的数量及其配置。
乘法(Ram中的所有项)
小型产品使用Basecase和Karatsuba乘法算法完成。也实现了3向Toom-Cook,但它被优化器有效地禁用了,因为它从来都不是最佳使用方式。
中型产品使用浮点快速傅里叶变换(浮点FFT)卷积完成。
y型压榨机使用一种改进的FFT,能够实现分裂基数算法的计算复杂性和数值稳定性,同时保持与简单基数算法相同的友好内存访问模式。
FFT变换长度为2k个, 3 * 2k个和5*2k个使用了。变换长度7*2k个没有使用,因为它们只适用于已经由下面的混合NTT算法处理的大型产品。它还不必要地增加了Twiddle Factor表的大小。
FFT是当前程序中优化程度最高的部分,使用矢量SSE2、SSE3和SSE4.1指令。尽管没有手工编码的组件,64位版本的FFT实现了与prime95相当的速度。(众所周知,prime95具有已知最快的x86 FFT,比FFTW快得多)
不支持SSE3或SSE4.1的处理器保持向后兼容性。FFT的未来变体将能够使用256位AVX和FMA指令。
大型产品使用混合数字理论变换(Hybridized Number Theoretic Transforms,Hybrid NTT)完成。
混合NTT是一种目前尚未发表的算法,它最初是在2007年构思的,然后在2008年开发和实施。
它能够实现与浮点FFT相当的速度,而只需要一小部分内存和内存带宽。
(混合NTT的详细信息将超出本文的范围。)
使用的当前实现y型压榨机是多线程的,同时使用整数和浮点指令。这还有一个额外的好处,即从“超线程技术”中获得额外的好处。它支持SSE3、SSE4.1,并有望从AVX和FMA中获得额外的加速。
这里描述的乘法算法已经出现在y型压榨机自v0.1.0(第一个版本)以来。然而,自那以后,他们进行了一些相当重要的修改。(FFT在v0.4.4和v0.5.2之间被完全重写。混合NTT在v0.4.4和0.5.2之间重新调谐。)
乘法(磁盘)
磁盘乘法是无法放入内存的巨大乘法。这些都是专门使用混合NTT完成的。
当(产品尺寸/内存)的比率2)相对较小,则使用三步(或三通)卷积算法。
- 第1步:
- 第2步:
- 第3步:
这是执行内存中无法容纳的磁盘FFT的已知最快方法。
当(产品尺寸/内存)的比率2)由于磁盘容量巨大,由于不连续的磁盘访问导致磁盘查找成为一个巨大的问题。
解决方案是使用5步(或5遍)卷积算法。
- 第1步:
- 第2步:
- 第3步:
- 第4步:
- 第5步:
程序在3步和5步之间切换的阈值是根据编写程序的这一部分时可用的2TB 7200RPM桌面硬盘精心调整的值。也可以使用7步(或更多),但对于我们的ram数量来说,这是不必要的。
由于可用的ram数量巨大(96GB),只有最大的乘法(2万亿x 2万亿位数或更多)使用了5步方法。
实际上,我们有144 GB的ram可供使用(这足以完全消除对5步方法的需要),但由于硬件规格的限制,144 GB ram将以较低的时钟速度运行。(96 GB在1066 MHz下运行,但144 GB在800 MHz下运行。)
关于我们的计算规模(5万亿位数)和硬件配置(16个硬盘驱动器),我们发现144GB的内存接近内存量回报递减点。因此,额外的内存时钟速度比额外的内存量提供了更多的好处。如果我们只使用48GB的内存,我们可以以更快的1333MHz运行内存。但发现48GB内存不够理想。
只运行48GB的ram也将允许我们使用EVGA SR-2主板*,该主板具有超频功能。但是,更快的内存和CPU/内存超频的好处不值得减少总内存以及硬件不稳定的潜在风险,特别是对于这样一个对硬件错误容忍度低的非常长的运行计算。
(由于计算的内存密集性质,这里的内存总量很重要,这似乎比CPU的速度更重要。虽然144 GB的内存正在逐渐减少,但48 GB正好相反。我们估计,使用96 GB内存将CPU时钟锁定到3.33 GHz可能比将CP时钟锁定更快U到4+GHz,只有48 GB内存。)
*请注意,当时人们认为EVGA SR-2主板最多只能支持48GB的ram。但后来发现,尽管EVGA官员表示,主板实际上能够支持高达96GB的ram。
此处描述的磁盘乘法已经存在于y型压榨机自v0.5.2(具有高级交换模式的第一个版本)起。
除法+平方根
除法和平方根都使用直接的一阶牛顿法。没有进行任何特定的优化。
这些是程序中优化程度最低的部分,还有很大的改进空间。
以下列出了未使用的主要改进:
- 多回退步骤的中间产品提取。
- 将倒数乘法和最终乘法结合起来进行除法,以减少冗余。
- 为基于FFT的乘法重用冗余变换。
中使用的除法和平方根的实现y型压榨机自v0.1.0(第一个版本)以来,几乎没有任何改动。
基数转换
使用缩放余数树完成从基数16到基数10的最终基数转换。这与Fabrice Bellard计算2.7万亿位数时使用的算法相同。唯一的区别是没有使用中间产品优化。
基数转换在每次计算结束时自动验证,有两个目的。
- 对于世界纪录的尝试:无需第二次转换即可确保正确性。
- 对于竞争基准:捕捉任何未能传播到最后数字的计算错误。
此验证在数字已写入磁盘后完成。对于基准测试,它不计入计算时间。
将缩放余数树算法添加到y型压榨机在v0.5.3中。在v0.5.3之前,它使用了经典的分治算法。
基数转换验证也添加到y型压榨机在v0.5.3中。
最大限度地提高可扩展性
考虑到使用的硬件数量,可伸缩性是影响性能的最重要因素之一。在本节中,我们将讨论并行/多核以及分布式内存/多硬盘驱动器方面的可扩展性。
多线程处理
随着当前硬件趋向于日益并行的环境,在多个内核上有效扩展的能力是性能的一个主要因素。
因此,y型压榨机广泛使用多线程。
- 二进制拆分-级数求和的二进制分裂算法是平凡的并行算法,因为它递归到独立的工作单元中。
在y型压榨机,此部分算法使用二进制递归线程暂停进行并行处理。在Binary Recursive Thread-Spawning中,递归的每个级别都用一个Thread-limit来调用,它告诉它允许使用多少个线程。然后,这两个递归调用中的每一个都会使用这个线程限制的一半进行调用。递归调用完成后,使用多线程算法进行合并。(使用完整的螺纹极限)
撇开负载平衡问题不谈,这种方法是渐近最优的,因为随着位数的增加,CPU利用率接近100%。
- 基于FFT的乘法-如上所述,乘法也是多线程的。
与二进制分割一样,快速傅里叶变换(FFT)和相关变换也基本上是并行的。在y型压榨机,它们也是以几乎相同的方式使用二进制递归线程暂停来完成的。
与二进制分割一样,该方法是渐近最优的。由于FFT的对称结构,不存在主要的负载平衡问题。任何轻微的负载不平衡通常都是由环境引起的,而不是算法本身。
应该注意的是,二进制递归线程暂停方法是y型压榨机将线程数限制为2的幂。
中已存在多线程y型压榨机从一开始(v0.1.0)。
多硬盘支持
硬盘驱动器是现代计算机中速度最慢的部件之一。磁盘带宽的摩尔定律一直没有赶上CPU计算能力的摩尔定律。因此,磁盘带宽远远落后于CPU。考虑到高精度算术的内存密集性,在磁盘上执行算术受到磁盘速度的极大限制。为了解决这个问题,y型压榨机支持使用多个硬盘驱动器来增加磁盘带宽。
中的多硬盘驱动器功能y型压榨机本质上是一个软件RAID 0。这似乎是硬件RAID的冗余,但与硬件RAID相比,它有两个主要优势:
- 对可使用的驱动器数量没有限制。大多数硬件RAID控制器限制为4或6个驱动器。操作系统支持的软件RAID可以解决这个问题,但通常效率较低。在我们的计算中,我们使用了16个硬盘驱动器,其组合顺序带宽接近2GB/s。
- 通过给予y型压榨机它完全控制每个硬盘驱动器,让程序选择自己的条带参数(除其他外)。
- 它允许程序选择条带大小并动态更改。
- 它允许程序在交错条带化和附加条带化之间进行选择并动态更改。
最后一点很重要。不同的操作更适合不同的RAID模式。例如,加法和减法需要最大的线性速度,因此对于交错带化是最有效的。另一方面,FFT可以进行许多非连续访问,并且最有效的是附加条带化,因为它允许同时访问文件的不同部分。
多硬盘驱动器支持已存在于y型压榨机从一开始(v0.1.0)。
然而,在v0.5.2之前,它只使用了附加条带化。从v0.5.2开始,它使用附加和交错条带化。
最小化带宽消耗
内存访问模式是可伸缩性的一个不太明显的障碍。如果软件受到其他资源(如内存带宽)的限制,那么更多的内核和高CPU利用率意味着什么都没有。
要使内存密集型程序在多个内核上扩展良好,它必须具有较高的(计算工作量/内存访问字节数)比率。
问题是,在高精度算法中,所有常见的运算都有一个非常低的值。加法和减法是最好的例子,因为它们做的工作很少,但它们需要传递包含操作数的所有内存。
加减运算的带宽消耗是一个相对较小的问题,因为它们只占运行时间的很小一部分。一个更大的问题是FFT,FFT因其内存和带宽消耗而臭名昭著。
从我们的实验来看,在基于Intel Core 2 Quad的系统上,单个大型SSE优化基数-4浮点FFT能够饱和内存带宽。
这意味着尝试在这个系统上多线程FFT将产生很少的好处,因为单个线程已经足以占用所有内存带宽。升级硬件只是部分解决方案。但是,即使在最新的基于Intel Nehalem的处理器上,有3个DDR3通道,当运行4个FFT线程时,也没有足够的带宽来保持CPU的运行,更不用说通过HyperThreading运行8个线程了。
为了解决这个问题,我们投入了大量精力来最小化内存访问并提高(计算工作量/内存访问字节数)比率。
- 只要有可能,就要进行加减运算。
- 模块化散列检查(将在下一节中介绍)保持在最低限度。
- 当浮点FFT太大而无法放入CPU缓存时(在所有线程之间划分后),则使用混合NTT*
*最后一点很重要。由于涉及缓存关联性和寄存器不足的复杂性,所有在多线程环境中使浮点FFT在CPU缓存外有效的尝试都被放弃。最终决定,只要浮点FFT不适合缓存,就使用混合NTT。虽然这增加了计算成本,但减少的带宽消耗远远弥补了这一点。
带宽相关的优化已经开始y型压榨机从一开始(v0.1.0)。但自那时以来,它们已经被多次改进和调整。
带宽相关优化的最大改进是在v0.1.0-v0.2.1和v0.4.2-v0.4.3之间。
线程垃圾邮件和负载平衡
由于级数求和的非对称性,并行化二进制拆分过程存在显著的负载平衡问题。
为了解决这个问题,y型压榨机使用以下两种方法:
尺寸-平衡:
在二进制分割的每个递归级别上,都会仔细选择分割,这样每个子递归都会产生大小相等的数字。
这与简单地在两个子递归中平均分割术语形成对比。
在几乎所有的级数求和中,较早的项产生的数字小于较晚的项。(例如:尽管项数相同,但对项1-100求和的结果比对项1000001-1000100求和的结果要小。)
这种大小平衡方法试图通过向子递归提供更多的项来弥补这种差异,子递归是对早期项的汇总。
通过平衡大小,可以确保线程之间的负载更加平衡。它还具有在所有线程之间平衡内存使用的副作用。
为此,y型压榨机在对一系列术语求和后,使用函数近似来估计数字的大小。
这些近似值(其细节将被省略)能够估计递归中每个数字的大小,与实际大小相比,精确度约为+/-一个单词大小。(即使数字长达数十亿字。)
线程扫描:
上述尺寸平衡方法通常能够实现约90%的负载平衡效率。(也就是说,一个子递归很少会比另一个子递归快或慢10%以上。)
但有可能做得更好。这里我们应用了一种我称之为“线程扫描”的方法。
Thread-Spamming的作用与它的名字完全相同。它以提高CPU利用率为目标对线程进行垃圾处理。在程序中的不同位置,允许的线程数是已知的负载不平衡严重程度的两倍甚至四倍。二进制分割就是其中之一。
这个概念很简单。通过将线程数加倍,每个子递归都能够使所有逻辑核本身饱和。这意味着,如果一个子递归在另一个子递归之前完成,则仍在运行的子递归仍能保持处理器繁忙。这最终会提高CPU利用率。
显而易见的问题是,由于线程开销和资源争用,过多的线程可能会适得其反。然而,实验表明,利用这些未使用的CPU周期所获得的加速通常超过了这样的开销。(至少对于共享内存和统一内存环境……)
Size-Balancing和Thread-Spamming均由使用y型压榨机从一开始(v0.1.0)。
错误检测和纠正
对于长时间运行的计算,有必要考虑计算错误的可能性。
即使在稳定和非超频的硬件上,如果长时间处于压力之下,也有不可忽略的硬件错误的可能性。
无论好坏,高度优化的程序往往会对硬件造成极大的压力。y型压榨机也不例外。众所周知,产生的热量比两者都多林帕克和初级95启用“超线程技术”时,在基于Intel Nehalem的处理器上运行。(这正是我们使用的。)
(Linpack公司和初级95是非常受欢迎的压力测试程序。)
因此,从某种意义上说,极端优化带来的性能是一把必须处理的双刃剑。当然,最好首先避免错误,因此在构建将运行的硬件时必须格外小心y型压榨机延长时间。
近藤茂和我都经历过与硬件相关的计算错误,即使是在非超频硬件上。在我们俩之间,CPU利用率达到100%的情况下,每4周就会出现一个错误(来自y型压榨机)在我们的非超频双插槽机器上。这大约是每10个错误1个17操作。对于持续时间远长于此的计算,出现错误的可能性很大。事实确实如此。
计算开始仅仅8天,就发生了硬件错误。幸运的是,错误检测能够捕捉到错误。错误无法恢复,因此终止计算并从上一个检查点重新启动。总损失时间约为1天。
如果没有错误检测,这个错误就会传播到最终结果,并导致错误的数字。
*我们观察到的错误率为1/1017对于非超频硬件,操作似乎异常频繁。无论是巧合、过热,还是仅仅是y-cruncher带来的过度压力,我们还没有找到对此的解释。
错误检测和纠正y型压榨机使用的是一个简单的“自动重复请求”模型。
- 在整个程序中进行冗余检查。
- 如果检测到错误,请重复失败的操作。
- 如果操作无法重复,则回滚到最后一个保存点。
虽然使用了几种不同的错误检测方法,但只有一种方法占主导地位——模块化哈希检查。
模块化哈希检查
Modular Hash Check是一种非常简单(并且众所周知)的冗余检查,它使用数论来验证在模块环下关闭的任何操作的正确性。
我们感兴趣的业务包括:
要验证大整数加法、减法或乘法的正确性,只需取两个操作数在足够大的素数上的模第页.
完成操作后,取结果的模数并应用上述适当的关系。如果它成立,那么极有可能,操作已经正确完成。
y型压榨机使用梅森素数,261-1作为用于冗余检查的所选择的素数。
这样可以确保错误只有1/261-通过模块散列检查的机会为1。(尽管这有点有争议,因为它都是1位的。)
选择这个特殊素数只是为了提高效率,因为计算这个素数的模只需要几个逻辑运算,然后再进行加法。
(其他这种大小的素数需要64位除法,然后是乘法和减法……)
这种方法也适用于浮点数,因为模块化哈希检查可以在舍入或截断之前完成。
特别是,Chudnovsky的Pi公式中的最后一个乘法步骤使用了该方法来验证其正确性。
二进制拆分
在Pi计算中,序列的二进制分割占总运行时的80%以上。因此,这是进行高级冗余检查的最佳位置。
二进制分割过程的早期阶段不涉及舍入,完全由整数加法、减法和乘法组成。模块化散列检查被添加到这些位置。
为了最小化这些散列检查的性能损失,每个数字的模块散列与数字一起存储。每次操作后,哈希都会使用上述关系进行更新。(计算成本可以忽略不计)
这样就避免了每次操作后都需要检查哈希值。相反,哈希只验证一次(当数字大到需要交换时)。
一旦交换开始,就不再进行散列检查。这是因为“模块化哈希检查”需要对每个操作数进行传递—当在磁盘上执行二进制拆分递归时,传递的代价非常昂贵。在这些规模下,程序依赖于其他内部检查。在任何情况下,计算错误(与IO无关)在磁盘级别都很少见,因为CPU负载通常太低,无法产生导致计算错误所需的压力。
二进制拆分中的模块化哈希检查已添加到y型压榨机在v0.5.3中。在v0.5.4的后续版本中添加了自动恢复功能。
基数转换
根据用于转换的Scaled Remaider Tree算法的性质,在算法的(许多地方)插入冗余检查是很容易的,计算开销可以忽略不计(为了简洁起见,将省略其中的细节)。
因此,基数转换是整个程序中检查错误最多的部分。
应该注意的是,这些错误检查虽然数量众多,但尚未证明足以验证整个转换。(无论如何,这似乎还不够……)因此,为确保这一点,在算法中添加了额外的模块化哈希检查步骤。
第一个版本(v0.5.3)中包含基数递归中的冗余检查,该版本转换为缩放余数树算法。v0.5.3中还包括自动恢复功能。
乘法
在四种乘法算法中y型压榨机使用时,只有混合NTT具有冗余检查。
- 基于混合NTT的性质(为了简洁起见,将省略其细节),可以插入冗余检查,开销可以忽略不计。
- Basecase和Karatsuba算法没有插入检查的位置。检查它们的唯一方法是使用完整的模块化哈希检查。(如果已经被更高级别的错误检测覆盖,则这是完全过度的)
- 浮点FFT可以通过检查舍入误差来进行检查,但考虑到对其进行的优化量,这不是微不足道的。
幸运的是,在二进制拆分步骤中,几乎所有未使用混合NTT完成的乘法都已包含在模块化哈希检查中。
所有交换乘法都使用混合NTT。这是程序在二进制拆分中的模块化哈希检查停止后所依赖的错误检测。
混合NTT中的冗余检查已存在于y型压榨机从一开始(v0.1.0)。v0.1.0中还包括自动恢复功能。
一些随机评论
从阅读多个超频论坛和我自己的超频实验来看,计算错误通常是通过二进制拆分中的模块化哈希检查或混合NTT中的检查发现的。很少有错误能够在整个计算中漏掉。(对于v0.5.3,我还没有看到在整个计算过程中出现错误而没有触发任何警告或未通过任何冗余检查的情况。)
从v0.5.3开始,错误检测并不是完全可靠的,因为程序中仍有小部分无法通过冗余检查覆盖。(或者至少不会没有显著的性能成本)但只要错误不太常见,这就足够了。
附带说明:错误检测还可以防止小的软件错误,这是一个很好的奖励。
检查点+可重启性
计算错误和硬件不稳定是一回事。但停电是另一个原因。(除其他外)
当运行一个需要一百天的程序时,预计会有问题。
为了解决这个问题,y型压榨机有一个检查点功能,可以保存进度。这样,如果需要,它可以从中重新启动。
这样,如果计算因任何原因(断电、计算错误、9.0级地震或任何类型的SimCity灾难等)而停止,则可以从检查点(或保存点)重新开始计算。
当然,这取决于交换磁盘在灾难发生后是否正常工作,但如果定期备份交换磁盘,则很容易解决这一问题。
在高级交换模式下,y型压榨机在计算中的不同位置设置检查点。(包括序列总和中的多个检查点)。
这种保存和重新启动计算的能力非常重要,因为它几乎可以保证计算最终会完成。即使在软件错误阻止计算完成的情况下,也可以修复该错误,然后使用修补的二进制文件重新启动。
与错误检测一样,这个特性在计算的8天内就得到了解决。
检查点已添加到y型压榨机在v0.5.4中。这是计算5万亿位数Pi之前添加的最后一个功能。
改进的机会
尽管效率足以执行大型计算,但中的许多算法和实现y型压榨机有足够的改进空间。
用于大型计算的次优缓存使用
经过编写和调整,适合ram中的小型计算,y型压榨机对于非常大的计算来说是次优的。
最值得注意的是y型压榨机对于非常大的计算来说,内存抖动是一个主要问题。
由于时间限制,用于磁盘操作的大多数算法都是从内存中的等价物“强制移植”而来,很少或根本不考虑性能影响。大多数性能损失都是以次优缓存使用的形式出现的。
这种次优的缓存使用导致过多的内存占用,这解释了Shigeru Kondo为什么注意到96GB的ram@1066 MHz比144GB的ram@800 MHz具有更高的性能。
指令集改进
大部分y型压榨机不要完全利用几乎所有最新x86/x64处理器支持的SSE指令。
由于数据依赖性和对齐约束,并不是所有东西都可以很容易地向量化。虽然大部分代码可以矢量化,并不是因为需要对程序进行重大更改。
数学改进
有许多主要优化y型压榨机当前不使用。(因此,没有用于此计算。)
- 中间产品-这种优化大大加快了基本转换和大多数牛顿法迭代。(包括除法和平方根。)
Fabrice Bellard在之前的世界纪录中广泛使用了这种优化。
- GCD因子分解-这种优化大大加快了序列的求和。这也是Fabrice Bellard在上一次世界纪录中使用的。
- 在基于FFT的乘法中重用冗余变换-此优化尝试消除多次使用操作数的乘法运算中的冗余FFT。这是一个棘手的优化,没有被广泛使用,因为它具有高度的情境性,需要突破设计封装的几个层。此外,效益微乎其微,很少超过总加速率的17%。(17%对应于1/6,这是此优化将在许多二进制拆分递归中产生的最大理论速度-包括Pi。)
算法改进
有许多算法和设计考虑因素可能会或可能不会带来任何好处(对于速度和内存)。
这些都没有实现,只是坐在我的想法剪贴簿里。
- 多素数的经典数论变换-这是一个非常流行的算法。它由使用PiFast公司,快速Pi和Fabrice Bellard的塔库斯皮.
对于固定字号和固定数量的素数,经典NTT有一个完美的O(n对数(n))运行时复杂性。这使得它在渐近上优于混合NTT。
由于经典的NTT使用整数除法,所以速度非常慢。因此,它的使用通常仅限于磁盘和低内存环境。
然而,仔细使用因瓦利安乘法或蒙哥马利约简可以使经典NTT高效。
目前,尚不清楚经典NTT是否能够超越混合NTT。
- 运载延迟-随着现代处理器变得越来越矢量化,改进的一个主要障碍是多精度算法中执行导致的依赖性。通过使用小于全尺寸的单词,可以通过延迟结转来打破这些依赖链。这允许以增加内存消耗为代价进行矢量化。
Carry-Delay将大大有利于Basecase和Karatsuba乘法等低端算法。然而,它们不会帮助FFT和混合NTT,因为它们没有太多的拖链。此外,FFT和混合NTT占据了总计算成本的主导地位。因此,预计结转延迟不会带来巨大的整体效益。
- 混合数字理论变换(版本2)-这是混合NTT的改进版本y型压榨机当前使用。
更准确地说,这是2008年开发的完整混合NTT算法的假设实现。
混合NTTy型压榨机目前使用的只是一个高度简化的完整算法版本,它更短且更容易实现。
与现有的混合NTT相比,全混合NTT具有几个理论优势。然而,这是极其复杂的。支持SSE4.1和AVX指令的完全优化实现估计需要超过100000行代码。
由于其极端复杂,2008年实施完全混合NTT的计划被完全取消,取而代之的是y-cruncher目前使用的简化版本。此外,当时完整算法的正确性证明是不完整的。因此,还不确定整个算法是否有效……(由于科琳·李的一些帮助,证明已经完成。)
实际上,高效地实现完整的混合NTT算法是遥不可及的。算法的纯粹复杂性加上缺乏可测试的子步骤,使得它成为一项非常艰巨的任务,在多次尝试之后,我束手无策。
因此,到目前为止,完整的混合数字理论转换仍将只是学术兴趣。
*科琳·李是我高中时最好的朋友之一。在撰写本文时,她是斯坦福大学的本科生。
详细时间线(带屏幕截图)
这里的计算机是通过名称引用的。请参阅计算机列表他们的规格是什么。
日期 |
个人/计算机 |
事件 |
截图 |
二月的某个时候 |
- |
在我宣布5000亿位e,近藤茂联系我说,他希望尝试5万亿位数的圆周率。 |
|
3月-4月 |
- |
我在程序中添加了许多新的开发和改进,以准备进行如此大的计算。在此期间,近藤茂帮助我对这些新功能进行了大量测试。 |
|
2010年5月1日 |
Shigeru Kondo/Main公司 |
Shigeru Kondo完成了1万亿位Pi的计算。总时间:13天
这是最后一次测试,近藤通知我,他接下来将尝试5万亿位数。 |
查看 |
2010年5月2日 |
我/Ushio |
开始计算:32位十六进制数字,以4152410118610结尾。 配方:Bellard的BBP配方 |
|
2010年5月2日 |
我/纳吉萨 |
开始计算:32位十六进制数字,以4152410118610结尾。 公式:普劳夫BBP公式 |
|
2010年5月4日 |
Shigeru Kondo/Main公司 |
开始计算:5000000000000位Pi。 |
查看 |
2010年5月5日 |
我/Ushio |
完成的计算:32位十六进制数字,以4152410118610结尾。 配方:Bellard的BBP配方
总时间:64小时 |
查看 |
2010年5月5日 |
我/纳吉萨 |
完成的计算:32位十六进制数字,以4152410118610结尾。 公式:普劳夫BBP公式
总时间:66小时 |
查看 |
2010年5月7日 |
我/Ushio |
开始计算:50个十六进制数字,以2000000000000结尾。 公式:普劳夫BBP公式 |
|
2010年5月9日 |
我/Ushio |
完成的计算:以2000000000000结尾的50个十六进制数字。 公式:普洛夫BBP公式
总时间:55小时 |
查看 |
2010年5月11日 |
Shigeru Kondo/Main公司 |
第1周进度更新:序列求和已完成13%以上。 |
查看 |
2010年5月12日 |
Shigeru Kondo/Main公司 |
计算错误:程序的内部错误检测检测到计算错误。 我们从17%的检查点重新开始计算。 |
查看 |
2010年5月12日 |
我/纳吉萨 |
我试图在自己的机器上重现错误。但没有检测到错误。 这表明错误可能是由硬件异常引起的。 |
|
2010年5月13日 |
Shigeru Kondo/Main公司 |
计算错误更新:程序传递了部分计算错误。 正如预期的那样,没有检测到错误-确认原始错误是由硬件异常或软件中未知的线程相关错误引起的。
总损失时间:~1天 |
查看 |
2010年5月13日 |
我/Ushio |
开始计算:50个十六进制数字,以400000000000th结尾。 配方:Bellard的BBP配方 |
|
2010年5月16日 |
我/Ushio |
完成的计算:50个十六进制数字,以400000000000th结尾。 配方:Bellard的BBP配方
总时间:68小时 |
查看 |
2010年5月16日 |
我/Ushio |
开始计算:50个十六进制数字,以400000000000th结尾。 公式:普劳夫BBP公式 |
|
2010年5月18日 |
Shigeru Kondo/Main公司 |
第2周进度更新:序列求和已完成22%以上。 |
查看 |
2010年5月20日 |
我/你 |
已完成计算:50个十六进制数字,以400000000000th结尾。 公式:普劳夫BBP公式
总时间:97小时 |
查看 |
2010年5月20日 |
我/Ushio |
开始计算:50个十六进制数字,以300000000000结尾。 公式:Bellard的BBP公式 |
|
2010年5月22日 |
我/Ushio |
完成的计算:50个十六进制数字,以300000000000结尾。 配方:Bellard的BBP配方
总时间:53小时 |
查看 |
2010年5月22日 |
我/Ushio |
开始计算:50个十六进制数字,以300000000000结尾。 公式:普劳夫BBP公式 |
|
2010年5月25日 |
我/Ushio |
完成的计算:50个十六进制数字,以300000000000结尾。 公式:普劳夫BBP公式
总时间:69小时 |
查看 |
2010年5月26日 |
Shigeru Kondo/Main公司 |
第3周进度更新:序列求和已完成36%以上。 |
查看 |
2010年5月31日 |
Shigeru Kondo/Main公司 |
第4周进度更新:序列求和已完成46%以上。 |
|
2010年6月8日 |
Shigeru Kondo/Main公司 |
第5周进度更新:序列求和仍超过46%。 |
查看 |
2010年6月16日 |
Shigeru Kondo/Main公司 |
第6周进度更新:序列求和已完成59%以上。 |
查看 |
2010年6月22日 |
Shigeru Kondo/Main公司 |
第7周进度更新:序列求和仍超过59%。 |
查看 |
2010年6月29日 |
Shigeru Kondo/Main公司 |
第8周进度更新:级数求和已完成76%以上。 |
查看 |
2010年7月7日 |
Shigeru Kondo/Main公司 |
第9周进度更新:序列求和仍超过76%。 |
查看 |
2010年7月11日 |
Shigeru Kondo/Main公司 |
第68天:序列求和完成。开始划分。 |
查看 |
2010年7月16日 |
Shigeru Kondo/Main公司 |
第73天:执行除法的乘法步骤。 |
查看 |
2010年7月19日 |
Shigeru Kondo/Main公司 |
第11周进度更新:执行最终乘法。 |
查看 |
2010年7月22日 |
Shigeru Kondo/Main公司 |
第80天:Pi计算完成。十六进制数字与BBP结果一致!!! |
查看 |
2010年7月28日 |
Shigeru Kondo/Main公司 |
第12周进度更新:基本转换大约完成75%。 |
查看 |
2010年8月1日 |
Shigeru Kondo/Main公司 |
第89天:基本转换已完成。结果与之前的世界纪录相符!!! |
查看 |
2010年8月2日 |
近藤茂/主要 |
第90天:基本转换验证已完成。新的世界纪录是5万亿位数!!! |
查看 |
常见问题
这些并不局限于本文。其中包括一些我过去经常被问到的随机问题。
这个主页y型压榨机有一个与软件本身相关的常见问题解答。
问题:你是数学家吗?
答案:不。
问题:你认为自己数学好吗?
答案:不是真的。。。但我也不认为自己做得不好。
问题:你大学毕业后打算做什么?
答案:我将去伊利诺伊大学香槟分校读研究生。之后,我不知道。。。
问题:你玩什么视频游戏?
答案:我主要玩第一人称射击(FPS)和实时战略(RTS)。具体游戏包括:Left 4 Dead、Team Fortress、Halo、Crisis、Starcraft、魔兽DOTA、帝国时代,以及一些较老的游戏。(虽然我在FPS方面比RTS要好得多……)
问题:你为什么不使用GPU?它们比高端CPU更强大、更便宜。
答案:
- GPU的双精度支持非常差。双精度是必修的.
- 计算几乎完全受内存限制。它不受CPU的限制。因此,GPU的功率将在很大程度上被浪费。
- GPU需要大规模矢量化才能有效。目前,y型压榨机无法扩展到大型SIMD向量。
- GPU没有足够的内存。GPU内存和主内存之间的带宽远远不足以有效地使用主内存来代替GPU内存。
- GP-GPU编程没有通用标准。
问题:一些更高级的视频卡具有大量内存。基于Nvidia Fermi的Quadro卡具有惊人的6GB内存为什么你不能用这些?
答案:昂贵可能是一种轻描淡写的说法。。。对于大型交换计算,6GB的内存肯定是一个瓶颈。64GB或128GB之类的东西会更有用,但我认为这种情况不会很快发生,更不用说价格实惠了。。。
问题:您提到您不能使用GPU,因为双精度支持较差。为什么不能使用单精度?
答案:因为y型压榨机如果精度不够,将失败。在某种程度上,可以强制使用单精度,但对性能和内存的惩罚将是非常恶劣的。
问题:y-cruncher使用GMP或其他开源软件吗?换句话说,整个程序是你自己写的吗?
答案:尽管受到了GMP和其他来源的一些影响,y-cruncher并没有与其他任何东西共享任何源代码。
y-cruncher及其所有底层库的所有源代码都是我自己编写的。
特别感谢
我想特别感谢在这漫长的三个月里为我加油的所有朋友和家人。
特别是,我要特别感谢Kei Simmel,他是我们的翻译,帮助我们管理语言障碍。我不会说日语,近藤茂也不会说英语。。。每当谷歌翻译惨败时,Kei都会提供帮助。
最后,当然是近藤茂本人。没有他的帮助,这个计算是不可能的,因为我缺乏耐心和资源来运行这个计算。
关于我
我是西北大学22岁的大四学生。我实际上是在6月份毕业的(当时正处于长达3个月的计算期)。
所以从技术上讲,我不再是大学生了。然而,我将于8月份开始在伊利诺伊大学香槟分校攻读研究生。
我主修计算机科学和电子工程。我的专业是高性能计算、并行/分布式计算和超大规模集成电路。
然而,我在HPC和并行计算方面的大部分知识都是自学的。
我在加利福尼亚州福斯特城长大,就读于鲍迪奇中学。
毕业后,我搬到了加利福尼亚州的帕洛阿尔托,在那里上学并从帕洛阿尔多高中毕业。
我的爱好包括保龄球、钢琴(一般音乐)、视频游戏和带字幕的日本动漫(即我不看配音……)。
我会说英语、广东话和一点点普通话。
更多关于我.
问题或评论
通过联系我电子邮件。我回复得很好,除非它被学校的垃圾邮件过滤器捕获。
你也可以在上找到我XtremeSystems论坛在用户名下:戳349
返回至: