每位同学完成一份小论文和同学一样怎么办-谈谈自己对摩尔定律和Intel发展的理解

作者王越美国宾夕法尼亚大学計算机系研究生,中国著名 TeX 开发者非著名 OpenFOAM 开发者。

年被选为资深副总裁1995 年 9 月,她被时任美国国家半导体(National Semiconductor)CEO的 Gil Amelio 忽悠跳槽来到这个企業,做执行副总裁她在这里带领团队完成了 CompactRISC 架构,这个架构事后成为 ARM7 系列的前身很多人早已经把她忘了,也很少有人能够在回忆时将她和 Mac OS X 联系起来但事实上,她是让苹果放弃

月为什么是危机四伏呢?还得从早先的事情说起

20 世纪 80 年代,卖可乐的 John Sculley 成为 Apple 的 CEO随之 Steve Jobs 被轰出Apple。毕竟可乐和计算机不是一回事因此不管是硬件还是 Mac OS,整个公司的开发项目越来越受阻而且由于先天的不足,Mac OS 从诞生之初就不具有一個现代操作系统所应有的特性所以,在 1987 年开发下一代操作系统的计划呼之欲出。具体的规划是把新的系统所需要的功能,写在一堆鉲片上短期可实现的目标,比如增加颜色支持(当时计算机仍是黑 白的)写在蓝色的卡片上;长期的目标,比如多任务功能写在粉銫的卡片上;而在可预见的未来都无法实现的长期的目标,比如加一个纯物件导向的文件系统 就写在红色的卡片上。在这样的思路下Mac OS 嘚开发团队马上就被分成两个组,一个叫蓝组目标是在 1991 年,发布一个关于 Mac OS 的更新版本;另一个叫粉组和蓝组同时工作,计划在 1993 年发咘一个全新的操作系统。

1991 年 5 月 13 日蓝组顺利按时完成开发任务,发布了 Mac OS 7(一般被称为 System 7)而粉组却没做出什么有实际用途的东西来,因此接连跳票而且,由于 Mac OS 7 的发布缺乏人手为了保持正常发布,常常需要从粉组抽调人员参加蓝组的开发再加上 Apple 当时把重心放在了和 IBM 等公司的合作上(Taligent 项目)而不是在粉组上,最终导致了粉组项目夭折而本来 Apple 指望和 IBM 合作的Taligent 项目能开发出一个可用的新系统,但后来 IBM 不跟 Apple 继续玩了因而 Taligent 的果子又吃不到,Apple 相当郁闷这时由于 Mac OS 有先天不足(单任务,没有内存保护)再加上 Apple 以及第三方软件的无限量增加(在这段時期,单 Apple 自己就已经加入了 QuickDraw、PowerTalk、QuickTime 等软件和技术每一个都比 Mac OS 本身来得大),Mac OS 的问题终于大爆发上个世纪 90 年代,Mac OS 给人的印象就是很不稳定、经常崩溃同 Windows 95 留给 PC 用户的印象差不多,甚至更甚

Taligent 项目挂掉后,Apple 自己尝试过十多个不同的内部项目但大多没做多久就夭折了。而这时囸是 Windows NT 走向成熟的关键时期眼看着日子逐渐变得不好过了,Apple 开始重新开始考虑建立下一代操作系统的事情1994年,Mac OS 、Java 等依赖虚拟机的语言就偠比 C 慢许多Python 等动态语言比 C 慢的不是一星半点)、快速开发(我们原先处理一个大文本,先分块一点一点读到内存中,然后把处理完的蔀分写回磁盘清空内存;而现在直接把它全读进来处 理,开发方便执行也快)。而用户必须为这些新功能买不成比例的单64 位就是在這个背景下迅速走入寻常百姓家的——程序占用越来越多的内存,而 32 位的寻址空间已不能满足软件运行的需要了

64位 CPU 是指 CPU 内部的通用寄存器的宽度为 64bit,支持整数的 64bit 宽度的算术与逻辑运算早在 1960 年代,64位架构便已存在于当时的超级电脑且早在 1990 年代,就有以 RISC 为基础的工作站和垺务器2003 年才以 x86-64 和 64 位元 PowerPC 处理器架构(在此之前是 32 位元)的形式引入到个人电脑领域。从 32 位元到 64 位元架构的改变是一个根本的改变因为大哆数操作系统必须进行全面性修改以取得新架构的优点。

苹果向 64 位处理器的迁移花了整整 6 年时间远长于该公司其他技术的迁移——向 Intel 的遷移仅用了一年时间,从经典 Mac OS 到 Mac OS X 也仅用了三年时间总而言之,这场迁移是非常成功的:一方面用户基本无痛苦,老的 32 位程序在目前最噺版的 Mac OS X Lion 中依然可以完全兼容地执行;另一方面对开发者而言,基本只需做微小的调整重新编译程序,而且若干技术如 Universal Binary使他们发布程序非常方便。当然对于某些大量使用过时技术的公司,如 Adobe 和 Microsoft这场迁移则要折腾得多。

这场迁移整整用了四个发行版的时间(10.3 至 10.6)不哃于 Windows 或 Linux,Mac OS X 对 64 位的迁移自下而上再自上而下。先是内核扩展逐渐上升至 Unix 空间,然后上升至用户界面再上升至整个应用程序生态,最后唍成内核的迁移要提醒读者的是,Mac OS X 的 32 位和 64 位内核空间与用户空间的分配和实现和 Windows 存在本质的区别,但在本期介绍中我们尽可能少地紦 Mac OS X 的 64 位迁移和 Windows 进行比较,不拘泥于技术细节对此区别有兴趣的读者,请移步

2003 年,苹果发布了其第一款 64 位计算机工作站 Power Mac G5同期发布的 Mac OS X 10.3 也洇此增加了非常简单的 64 位支持,于是 XNU 内核开始支持 64 位的寄存器和整数计算但对于用户空间而言,程序可见的地址依然是 32 位的程序当然鈳以使用大于 4GB 的内存(Power Mac G5 最高可达 8GB 寻址空间),但这要求程序手动地在两个 32 位内存空间中来回转换

两年后,苹果发布了当时最成功的 Mac OS X 发行蝂 Mac OS X 10.4 Tiger, 除了增加对内核并行多线程的支持它把用户空间可见的地址空间扩展到了 64 位,因此理论上用户程序可以以 64 位方式执行当然,在這个时期几乎系统内的所有程序,哪怕是内核依然是 32 位的。系统中唯一带的 64 位二进制文件是名为 libSystem.dylib 的系统库它是 Mac OS X 上对 C 标准和 POSIX 标准的支歭库,由 libc、libinfo、libkvm、libm 和 libpthread 五部分组成但这仅有的 libSystem.dylib 理论上就能让所有仅使用 C 标准库和 POSIX 标准库的程序以 64 位模式运行。当时用户对 64 位的需求较少,主要限于科学计算或图形处理等需要大数组的领域因此,10.4 能较好地满足这部分用户的需求但如果程序需要调用除 BSD Unix 以外的系统调用,比洳想用 Cocoa 来画图形界面那么该程序仅能以 32 位方式运行了。对于一些需要 64 位寻址空间的科学计算程序比如 Mathematica,就需要采用一些比较麻烦的做法:用一个进程调用 32 位的 Cocoa 画图形界面用另一个进程调用 64 位的 libSystem 来进行运算和 Unix 系统调用,并用 Unix 管道或进程间通信的方式管理两个进程间的输叺/输出

苹果在 Mac OS X 10.4 发布同期的另一项重要决策是。为了帮助开发者和用户顺利迁移苹果正式公布了 。Universal Binary 技术是 Mach-O 二进制文件早就具有的特性呮是在这个场合作为一个商业词汇进行宣传。NeXT 时代 NeXTSTEP 操作系统就支持许多种不同的硬件架构自然可以要求开发者对每个平台发布一个独立嘚版本,但这样的分发模式很麻烦消费者也需要搞清到底购买哪种平台的软 件。因此 NeXT 的 Mach 内核所支持的 Mach-O 二进制文件格式引入了一种叫 fat binary 的特性说白了就是在一个平台架构上分别交叉编译所有平台的二进制格式文件,然后把每个文件都打包成一个文件Universal 技术,买回来的软件直接会解出相应平台程序的二进制文件并执行这是苹果很成功的一步——不像 Windows 系统中要用不同的路径(\Windows\System、\Windows\System32、\Windows\System64)分别存放不同架构的 二进制庫,并且用户还需在 32 位版和 64 位版之间犹豫不决

Mac OS X 10.5 Leopard 经过一系列跳票终于在 2007 年末发布,跳票主要原因是当时苹果投入了大量人力和物力去做 iPhone鉯至于 10.5 跳票了整整一年。10.5 包含了约 300 项新功能而最重要的一项是苹果把对 64 位的支持带入了 Cocoa 层面。因此几乎系统中所有的库都有四个平台嘚版本。在 WWDC 上乔布斯亲自向与会者介绍迁移到 64 位的好处而能使用更大的内存自然是一项重要优势,程序可以申请更大的内存把所有数據一并读入内存中操作,而无须分块后来来回回地在内存和磁盘搬运数 据另外,对 Intel 平台来说x86 架构只有 8 个寄存器,而 x86_64 平台有 16 个寄存器這也就意味着,对该平台来说只要重新编译程序,程序就能自由调度比原先翻倍的寄存器数量而无须快取或在内存中来回查找和读写根据粗略估算, 一般涉及大量数值计算的程序会加快一倍所以他很开心地劝说所有的开发者都迁移到 64 位架构。

历时整整 6 年时间苹果完荿了向 64 位处理器的迁移,同时这也给苹果提供了良好的清理门户的机会——清理过时的技术和 API

同时,苹果做出了一个大胆的举动——Carbon 框架并未出现在这次迁移中Carbon 是 Mac OS X 诞生之初为了帮助 Mac OS 开发者把老程序迁移到新的 Mac OS X 操作系统上所提出的一个兼容 API,这套 API 长得很像经典 Mac OS 的 API但能够嘚到 Mac OS X 平台提供的一切新特性,Adobe、Microsoft 等都是通过 Carbon 把它们经典的 Mac OS 程序移植到 Mac OS X 上的苹果的本意是希望开发者用 Carbon 迁移老程序,用 Cocoa 开发新程序但在 Carbon 誕生之初,其受关注度远大于 Cocoa据 TeXShop 开发者 Dick Koch , 在 Mac OS X 刚诞生的开发者大会上Carbon 讲座的教室挤满了人,而 Cocoa 相关的讲座上听者无几维护两套雷同的 API 開发者,他们的程序将不可能再被编译成 64 位要做到这点,必需先把程序用 Cocoa 重写

后做出了 64 位版,其他大部分程序依然停留在 Carbon 的 32 位模式

蘋果也花了很长时间来重写 Finder、FinalCut、iTunes、QuickTime 等程序或技术,耗费了大量精力当 Adobe 发布 64 位的 Lightroom 2.0 时,苹果还在手忙脚乱地重写 Aperture不过公正地讲,长痛不如短痛砍掉对 Carbon 的支持能够使苹果把更多精力放在该做的事上,也使得 Mac OS X 的结构更简洁并且事实上,64 位的迁移为苹果提供一个砍去老 API 的机遇哪怕对 Cocoa 也是。一方面Cocoa 框架中很多类不是使用类似 Carbon 的 API,就是依赖于用 Carbon 实现(注意和传统观念不同,Carbon 和 Cocoa 在早期 Mac OS X 上是相互依赖的比如菜單 NSMenu 就使用了 ), 这些 API 在 64 位得到了彻底清理QuickTime 相关的 C 接口全被砍去。Cocoa 经过很长时间的发展自然也保留了很多过时的 API 以保证和原先的产品兼嫆,而这次机会给苹果足够的理由彻底推翻原先的设计在 Mac OS X 10.5 中, Objective-C 的运行库 libobjc 更新到 2.0提供了全新的并发、异常处理、自动内存回收、属性(property)等新机制,其中很多新特性只供同时,所有 int 都被改为

作为相反的例子这次清理也有不彻底的地方。比如从老版 Mac OS 中混进来的 甚至具囿 Pascal 风格的 API,由于没有替代品它也得到了 64 位的更新。所以类似 keychain 这样的库成了现在 Mac OS X 程序员的噩梦我每次用到 Keychain 都有痛不欲生的感觉。

为了使應用支持 64 位苹果不遗余力地改写了大量代码,Snow Leopard 中最重要的重写当属 Finder这个程序自 Mac OS X 发布以来就一直是一个 Carbon 程序,并且苹果一直不停地改进咜以展示 Carbon 但自从 10.5 时代苹果下决心砍掉 Carbon 后,该程序被完整地重写新的 Finder 和 Carbon 版的 Finder 看上去并没有太大差别,但 Finder 使用 Cocoa 重写后不仅速度更快,而苴增加了许多 Cocoa 新特性比如加入了更多的 Core Animation 特效来平滑过渡动画。总之虽然苹果在 10.6 期间没有提供太多新功能,但这样大规模的重写为今後代码的可维护性奠定了良好的基础。

经过 6 年时间4 个发行版,苹果终于完成了向 64 位的迁移并随着 Snow Leopard 的发布推出了解决并行编程问题的 Grand Central Dispatch(簡称 GCD)技术,释放了多核系统的潜力

C++ 统一的异常处理模型,都仅限 64

读者应该发现,经过这 4 个发行版Mac OS X 自下而上地对整个系统向 64 位迁移。10.3 内核空间提供了 64 位整数运算的支持10.4 允许程序以 64 位模式运行在用户空间,并且提供了 64 位的 libSystem 使得开发者可以开发 64 位的 Unix 程序而 10.5 中系统所有未废弃的函数库、框架都提供 64 位版本,到了 10.6所有用户空间的程序,包括 Unix 层和图型界面层基本都更新到 64 位。细心的读者不禁会问—那内核是 64 位的吗是的,自下而上支持 64 位后10.6 又从上往下,迁移了整个系统中最后一个也是最重要的部分—内核

内核 64 位化的意义

对于 Windows、Linux,以忣 FreeBSD 等操作系统64位实现的第一步是实现 64 位的内核。然而 Mac OS X 却反其道而行主要原因是,反正 32 位的内核也能以非模拟、非兼容的方式原生地运荇 64 位用户空间程序而内核和与内核动态链接的驱动,很少需要用到 64 位的寻址空间(你什么时候见过内核本身使用 4GB 内存),所以该问题鈳以暂缓

但要记住,用户空间的内存是由内核管理的虚拟内存、内存分页等机制,都是由内核一一实现的一旦在不久的将 来,随着鼡户空间的内存占用越来越多虚拟内存的分页比也会不断膨胀。比方说一个用户程序使用 4GB 的空间,每个分页包含 4KB 的页面那么总共有 1M 個页面。因此假设一个页面 来记录该页的位置,那总共也就需要 64MB 的内核空间来记录这个用户空间程序的虚拟内存不算太多。而在不久嘚将来如果一个 64 位用户程序使用 128GB 的空间,则需要 32M 个页面每个页面 64B 的 PTE 会导致 2GB 的内核地址空间来寻址(暂不考虑大分页)。32 位的内核就显嘚非常紧张

另外,上一期我们也提到 64 位的 Intel 架构提供了比 32 位多一倍的寄存器因此,用户空间程序对 64 位内核的系统调用也会更快根据苹果的数据,系统调用的响应速度比原先快了 250%而用户空间和内核空间的数据交换也快了 70%,因此64位内核要比 32 位内核更快。

内核完成 64 位迁移

雖然在 Mac OS X 10.6 中苹果提供了 64 位模式运行的内核,但在大部分苹果计算机上。 其原因是虽然 64 位程序和 32 位程序可以在计算机上同时运行,但 64 位嘚程序只可以加载 64 位的库或插件32位程序只能加载 32 位的库或插件。因此如果默认使用 64 位模式启动,则诸多第三方的 32 位驱动或内核模块将無法使用当然,用户可以通过修改 com.apple.Boot.plist、nvram或开机按住 6 和 4 ,不过苹果并不推荐这样的方式直到 Mac OS X 10.7 时,第三方内核扩展已趋完善大部分的 Mac 才默认使用 64 位内核模式启动。

苹果用了整整 6 年的时间完成 64 位的迁移在 2009 年 WWDC 的一个讲座上,Bertrand Serlet 告诉开发者我们这个 64 位技术的讲座,只针对 Mac OS X而 iPhone、iPad 等 iOS 设备,由于使用 ARM 平台在可预见的未来可能并不会支持 64 位技术。

不过两年之后的 2011 年 10 月 27 日ARM v8 发布,ARM 正式宣布支持 64 位未来会不会出现基於 ARM 的 Mac,或是 64 位的 iPad除了苹果,谁知道呢

很长一段时间以来,处理器靠更快的运行时钟来获得更高的效率软件开发者无需改动或重新编譯他们的代码,就能 得到摩尔定律许诺他们的好处因为处理器顺序地执行计算机指令,新一代的处理器就自动会跑得比原先更快后来烸每达到一个技术极限时,总有一些聪明的方法 绕过这些极限比如超纯量、指令管线化、快取等,不是悄无声息地把多条互相独立的指囹同时运行就是隐藏掉数据读写的延时。

到了 21 世纪能想的办法基本都想尽了——现代处理器已经足够并行了,也采取了各项优化来不斷提升各种预测器的准确率而时钟频率却是不能无限提高的——提高时钟 频率会极大地增加处理器的产热,使得服务器机房或笔记本的散热成为一个头痛的问题同时对于便携设备而言,高频也意味着短得多的电池时间因此摩尔定律正 在经受重大的考验。

因此大约在 21 世紀头十年过掉一半时“多核”处理器,终于开始跃入普通消费者的视线“多核”顾名思义,就是把原先单核的半导体线路复制多份排於同一裸片上每个核相 互独立,又能彼此通信多核处理器的出现,有效缓解了计算机处理器生产商的设计和制造压力从而达到忽悠消费者买更新款产品这一不可告人的目的。

但这一次技术革新并不如之前那么顺利,因为程序并不会自动在多核系统上跑得更快甚至囿很多程序每一步都有前后依赖,不能高效地并行运行即使能够高效并行的程序,也需要大规模改写才能充分利用多核所带来的优势

傳统的并发编程模式,就是学习使用线程和锁这听起来很简单,几句话能说明白:

  • 把每个任务独立成一个线程;
  • 不允许两个线程同时改動某个变量因此得把变量“锁”起来;
  • 手动管理线程的先后并发顺序和并发数量,让它们均匀地占满系统资源;
  • 最好系统中只有这个程序在运行否则你精心设计好的线程管理算法往往不能达到原来该有的效果;
  • 最后祈祷程序在用户那儿不出问题。

但是实际操作起来多線程程序的编写要比单线程难上不止一个数量级。一方面调用大量内存和数据反 复的加解锁本身效率就非常低下;另一个重要原因在于,由于多线程程序可能以任意的次序交错执行程序再也无法像顺序执行时那样产生确定的结果。多线程程序 看似容易编写但难分析、難调试,更容易出错即使是最熟练的开发者,在茫茫线程和锁之间也会迷失方向。且程序的错误在很多时候甚至是不可重现的所 以,程序员使用线程和锁机制编写并行程序的代价是很高的

GCD 就是在这种背景下被苹果提出来的。2008年最初提出但未公布细节时很多人怀疑咜是 FreeBSD 的 ULE 调度器在 Mac OS X 上的实现。 是 FreeBSD 当时最新的内核调度器用来替换掉老一代的 4BSD 调度器,当时使 FreeBSD 上跑多线程程序的效率获得了重大的性能提高远高于同期 Linux 和 。 但当时我就认为 GCD 依赖 FreeBSD 这项技术的可能性不大因为 Mac OS X 中管理进程和线程主要用的是 Mach 而不是 BSD。不过后来证实我只猜对了一半GCD 的实现,实际上是依赖于 FreeBSD 的另一项技术 kqueue 是一个由 FreeBSD 4 时代引入的新功能,内核级别地支持消息通信管理GCD 的队列,其实就是用 kqueue 实现的

在 GCD Φ,开发者不再管理和创建线程而是将要实现的运算抽象成一个个任务,一起扔给操作系统转而让操作系统管理,这在计算机科学中被称为。

在 GCD 中开发者使用很简单的方式就能描述清应用程序所需执行的任务,以及任务之间的相互关联每一个任务在代码中被描述荿块(block),然后开发者把一个 一个块显式地按顺序扔到队列(queue)中使用块和队列两个抽象的表述,开发者无须创建线程也无须管理线程,更无须考虑数据的加解锁换之而来的, 是更简短可读的代码剩下的事,全都扔给操作系统去完成

在操作系统那边,GCD 在程序运行時管理着一定数量的线程,线程的数量是自动分配的取决于用户计算机的配置和用户程序运行时的负载。多核工作站每个程序配到的線程自然就会 比单核手机或双核笔记本来得多。而且这个线程的数量是会动态变化的当程序非常忙时,线程数会相应增多而当程序閑置时,系统会自动减少其线程数量然 后,GCD 会一一从队列中读入需要执行的块然后扔到线程上并发执行。

相信读者已经看出 GCD 和传统线程-锁机制的区别来了传统的方式按劳分配,强调程序自由独立地管理妄想通过“无形的手”把系统资源平均分配,走的是资本主义市場经济的道路 而 GCD 按需分配,真正实现了社会主义计划经济管理模式因此在政治上 GCD 就是一个代表先进生产力的计算机技术(我被自己雷叻,但事实就是这样)

GCD 是一个自底向上的技术,它实际上由以下 6 个部分组成

  1. 编译器层面,LLVM 为 C、Objective-C 和 C++ 提供了块语法这个内容等下会介绍。
  2. 运行库方面有一个高效分配管理线程的运行库 libdispatch。

GCD 还有一些工程上的优势首先,程序的响应速度会更快GCD 让程序员更方便地写多线程程序,因此写一个多线程程序来实现前后台简单多了极大改善了 Mac OS X 上应用程序的生态环境。而且 GCD 的代码块队列开销很小比传统线程轻量嘚多。统计表明传统的 Mac OS X 上使用的 POSIX 线程需要数百个计算机汇编指令,而一个代码块队列才用 256 字节的长度,把块加入队列只需要 15 个计算機汇编指令,因此开成百上千个也不费什么事

其次,线程模式是一种静态的模式一旦程序被执行,其运行模式就被固定下来了但用戶的计算机配置各不相同, 运行时别的程序有可能耗用大量的计算资源这些都会影响该程序的运行效率。而动态分配系统资源则能很好哋解决这个问题苹果自然也是不遗余力地忽悠开发者 使用 GCD,因为各个软件共享多核运算的资源如果 GCD 被更多的开发者采用,整个苹果平囼的生态也就更健康

而最重要的,还是 GCD 采用的线程池模式极大简化了多线程编程也降低了出错的可能性。著名 FreeBSD 开发者 Robert Watson 还发布了一个他修改过的 Apache,声称只需原先 1/3 至 1/2 的代码量就实现了原先的多线程模块,并比原先的效率更好

当然,老王卖瓜自卖自夸,没有实际的例孓是不能让读者信服的。下面我们就来简单讲解 GCD 的技术

首先是块状语法,是一个对 C、C++ 和 Objective-C 语言的扩展用来描述一个任务,用^引导的大括号括起来比如最简单的:


    

则 x 就变成了一个块。如果执行:

那么程序会打印 hello world 出来当然,blcok 像函数一样可以跟参数,比如:

这里 MyBlock 是一个帶参数的代码块

读者看到这里不禁要问,块到底有什么好处它和 C 的函数指针有什么不同?我们依然用上面的例子来说明问题虽然后媔我们把 spec 变量改为 0,但事实上在 MyBlock 创立时已经生成了一个闭包,因此它最后输出的结果仍是 16,不受 spec 值改动的影响这对于搞函数式编程嘚人来说再熟悉不过了,因此很多开发者亲切地称呼块语法的 C 扩展为“带 lambda 的C”

有了闭包功能的 C 顿时牛起来——你可以把函数和数据包装茬一起——这就是块的真正功能。因为只要一个闭包包含了代码和数据它的数据就不会被别的闭包轻易改动,所以在它执行时你根本鈈用为数据上锁解锁。

有了一系列的代码块后接下来的事是把代码块扔到队列里。比如最简单的:

来创建一个轻量级的队列然后

那这個代码块就被扔进 queue 这个队列中了。你可以手动依次添加任意多个项目比如“带着老婆”、“出了城”、“吃着火锅”、“唱着歌”、“突然就被麻匪劫了”等。当然在更多的场合 你会更倾向于使用自动事件源,每当一个事件触发时(比如定时器到点、网络传来包裹或鍺用户点击了按钮),相应的代码块被自动添加到队列中


一旦队列不是空的,GCD 就开始分配任务到线程中拿上面的例子来说,“老婆”、“城”等变量可是封在闭包里的所以在运行时,不用考虑它们被某个别的闭包改掉(当然也有方法来实 现这个功能)总体而言,这個模式比线程-锁模型简单太多——它的执行是并行的但思维却是传统的异步思维,对没有学习过系统多线程编程的开发者来说依 然能佷容易地掌握。

读者可能要问如果闭包之间有复杂的依赖关系,需要申明某两个操作必须同步或异步怎么办比如“出了城”必须 在“吃着火锅”之前。在 GCD 中可以使用 dispatch_async 和 dispatch_sync 来描述这样的依赖关系,而在 Cocoa 层面NSOperation 中的队列依赖关系甚至可以被描述成有向图。

GCD 一经推出就得到了廣泛的应用苹果自家的软件 Final Cut Pro X、Mail 等软件,都采用 GCD 来实现任务并发和调度因此 Mac OS X 10.6 成为了有史以来最快的发行版。从 iOS 4 开始iPhone 和 iPad 也加入了 GCD 的支持。更别提原来使用 Cocoa 的 NSOperation 相关接口的程序无需改动即享受 GCD 的优惠。

GCD 在 Mac OS X 10.6 发布后又以 libdispatch 为名,作为一个独立的开源项目发布 所需的外围代码,洳编译器的块支持、运行库的块支持、内核的支持也都能在 LLVM 和 XNU 等开源项目代码中找到,所以很快被别的操作系统采用作为 Mac OS X 的近亲, FreeBSD 在┅个月后即完整移植了整套 GCD 技术并最终在 FreeBSD 9.0 和

另外,GCD 也成为拯救动态语言的重要法宝由于受 GIL(全局解释锁)的限制,动态语言虽然有操莋系统原生线程但不能在多核处理器上并行执行。而 GCD 成功绕开了这个限制如加入 GCD 支持的 Ruby 。 因此在苹果生态圈以外,GCD 也会得到越来越哆的应用

随着 CPU 与 GPU 合并成技术发展的趋势,苹果开发出了 OpenCL 框架能够进行高速并行处理的能力使 OpenCL 成为了业界标准,被广泛应用

最近几年,GPU 的发展吸引了很多来自科学计算界人士的目光GPU 有稳定的市场推动力——公众喜闻乐见的电子游戏产生了源源不断的升级 GPU 的需求——因此比 CPU 的更新步伐更快。从技术上讲GPU 本身就是多核架构,高端显卡往往有即使低端的集成 GPU 也有二三十个核心,所以能够通过并行来高效處理成千上万的线程同时,对于科学技算中的浮点计算GPU 往往通过硬件加速使其效率比传统 CPU 更高,因为图形渲染等工作基本都是浮点计算

早期的 GPU 只能执行固定的程序,而不开放给程序员编程随着时代的发展,图像处理有时需要对着色器进行编程以实现一些特效因此需要程序员可以使用 GPU 的汇编语言写简单的着色程序。这自然对程序员要求过高所以一些高阶的。比如微软和 NVIDIA 共同开发的 就能为顶点和潒素编写专门的着色程序。这类技术虽然面向图形渲染工作者却吸引了一小簇科学计算研究者的兴趣。以计算流体力学为例它是用纳維斯托克斯方 程【注:把牛顿第二定律和质量守恒应用到流体后,所得到的偏微分方程】来求解流体力学问题的一种算法广泛用于天气預报、F1 方程式赛车设计等工程领域。同时对于电影制片特效,计算流体力学也是最基本的用来模拟流体流动特放的算法皮克斯动画工莋室的《寻找尼莫》中的海洋流动 和水花等,都是使用纳维斯托克斯方程来模拟的

首先,对于一个几何空间进行网格化每个网格中的鋶体,都可以列出纳维斯托克斯方程把这些方程联立起来进行 求解,即可得到各点的温度、压力、湿度、速度等流体信息整个求解过程可以高度并行,因为每个网格的控制方程是完全一样的;同时也牵涉大量的浮点运算但 Cg 这类语言并非面向普通的计算,其变量都是颜銫、顶点、像素等图形学专用变量来自北卡罗莱那大学教堂山分校的 Mark Harris 突发奇想:可以把流体力学中每个网格的速度、压力等变量,存成 RGBA 顏色后让 Cg 去处理所以他在《GPU Gems》中著名的一章,公布了使用 Cg 来高速实现计算流体力学运算的吸引了大量计算界的目光。然而这种编程模式对科技工作者来说很不友好,因为这要求一个学力学的、学生物的、学化学的学生先要明白复杂的 GPU 渲染原理,了解图形学中材质、頂点、合成、像素、光栅化、光线跟踪等深奥的理论才能编写他们专业相关的 GPU 程序。

GPU 生产厂商洞察到了 GPU 高速并行浮点数运算的潜力所鉯 GPGPU(General Purposed Graphics Processing Unit)概念终于浮出水面。一方面 GPU 设计一代比一代可编程化另一方面各公司也在加紧研制新一代 GPU 编程语言。新一代的语言对比 Cg去掉了對于渲染相关的知识要求,独立于图形学之外是纯粹的普通语言,比如变量不再是像素、顶点、面等类型而是 C/C++ 语言开发者喜闻乐见的浮点数组、整形数组等。这一时期为代表的语言主要是 CUDA(Compute Unified Device Architecture)。CUDA 是 NVIDIA 在 2007 年公布的一项面对科学计算工作者的 通过该技术,使用者可利用 NVIDIA 的 GeForce 8 鉯后的 GPU 和较新的 Quadro GPU 进行高性能编程用户先编写一个特殊的 C++ 代码文件,扩展名为 cu文件中需要申明创建的变量、GPU 计算核心(kernel)以及使用给定嘚编程接口来实现变量在 CPU 和 GPU 中的传送。然后通过 NVIDIA 自家的编译器编译这个代码链接到 NVIDIA 自家的库上,即可把该运算核心编译为 GPU 汇编语句扔到特定型号的 GPU 上高度执行其他厂家也紧随其后,比如 AMD

对科学工作者来说CUDA 比 Cg 友好太多。使用 CUDA 加速流体力学运算相关的论文和同学一样怎么辦更是雨后春笋般涌现然而不久后,我发现它存在许多问题

首先,对初学者来说CUDA 编程模式很容易学混。因为一个 GPU 数组和一个 CPU 数组在 CUDA Φ的表述都是同样的C指针但对于 GPU 数组和 CPU 数组,CUDA 的处理模式完全不同CPU 数组使用常规的 malloc 来初始化,而 GPU 数组得使用 CUDA 提供的 malloc所以程序写着写著,就忘了一个变量到底是给 CPU 用的还是给 GPU 用的这无疑增加了学习难度。同时CUDA 对 C/C++ 语言进行了一系列扩展,这不但意味着写的程序不再具囿 C/C++ 那样良好的可移植性而且这种计算核心和传统 C 程序混写的编程语言很不美观。

其次CUDA 这类语言的实现各自为政。如果你写了一个 CUDA 程序就意味着这个代码只能运行在 NVIDIA 的显卡上。如果想使用 ATI 的显卡呢没门,请用 ATI Stream SDK 重写

再次,CUDA 是在编译时就静态产生 GPU 代码的所以只能产生特定的 GPU 代码。如果你发布了一个 CUDA 程序它仅对某几种 NVIDIA 显卡进行特定的代码优化。如果 NVIDIA 自家出了一种新显卡很抱歉,哪怕新显卡可能兼容咾显卡的汇编指令而你的程序恰巧可以在新显卡上跑起来你也无法发挥新显卡的所有特性。必须用针对新显卡 的编译器重新编译源代码才能够保证程序在新显卡上高效执行。

最后CUDA 这类语言仅能产生高效的 GPU 代码,而无法产生 CPU 代码即:写完的代码只能跑在 GPU 上,在 CPU 上只能“模拟执行”仅供调试用。所以在一台不具备给定 GPU 的机器上无法高效运行 CUDA 程序。同样如果你有一个性能很强的工作站,那么你的 CPU 亳無用处——CUDA 不可能分配一部分任务给 CPU 完成

另外还有未来计算机架构的不确定性。当时GPU 越来越一般化,可以跑多种数值计算程序而 CPU 随著多核成为主流也越来越像 GPU。所以很多厂家在考虑 CPU 和 GPU 合并的可能性

当时轰动一时的热门事件,是 CPU 厂商 AMD 买下了 GPU 厂商 ATI来开发下一代处理器 AMD Fusion,把 GPU 和 CPU 合并到一起Intel 自然不甘示弱,做出了 Nehalem 平台在该平台上,CPU 和集成 GPU 处于同一个包装中外界一度猜测这样可使合并后的 CPU 具有图形处理笁能,从而用户购置计算机就不用再考虑配一块 GPU 了

更强大的是,当时 Intel 还公布了 Larrabee 计划让 GPU 支援 x86 指令,使得一个常规的 x86 平台的程序不需要修妀和重新编译便可在 GPU 上运行

虽然事实和这些预期有稍许出入,但当时的技术趋势是:在将来可能出现一种新的合并 GPU/CPU 的技术能够并行高速地运行一般的计算机程序,而面对这样新的可能的平台我们如何准备?

OpenCL 则是苹果为这个新局面画下的蓝图这项技术初期全称为 Open Computing Library(如果留意苹果早期宣传广告的话),后改名为 Open Computing Language这项技术从本质上来说,和 CUDA 并没有太多的两样但由于苹果在借鉴他人技术并把他人技术改嘚更棒这一点上是出了名的,所以 OpenCL 很好地解决了以上所有问题

下面简单介绍一下这个框架。OpenCL 技术的结构十分清晰对程序员来说,它是┅个 Mac OS X 的 Framework定义了两套标准,一套是一个 C 语言的编程界面(API)使得开发者创建、拷贝、回收 GPU 使用的对象,同时也包含检测处理器、为该处悝器编译并调用核心程序(kernel)相关的接口;另一套是 OpenCL 核心程序语言的定义是一套基于 C99

例如我们有两个大数组,1024 维的 a 和 1024 维的 b(当然1024不算夶,OpenCL 往往用来处理十万、百万数量级的任务)我们把两个数组对应的元素加和,结果是一个 1024 维的数组cC 程序员很容易能写出下面的程序:


    

OpenCL 的核心程序,则是取每个独立的可并行的循环分支即上面程序中的 c[i]=a[i]+b[i]。所以核心程序大概是下面这样:


    

其中get_global_id () 函数可以返回当前函数是铨局中的第几个元素。把该程序保存为 add.cl就是一个 OpenCL 的核心程序,为 C99 语言的一个子集

使用 OpenCL 的 API 就能调用这个核心程序。每个 OpenCL 程序基本上是模式化地照搬下面流程:

4. 运行核心(把内存对象作为核心程序函数的输入参数执行这个核心程序会并发为 1024 个线程,每个线程执行一次相应嘚加法运算);

让我们逐条来看前面那些问题是如何被解决的

首先,OpenCL Framework 由 C API 和 OpenCL 语言组成泾渭分明,所有的 GPU 变量在 C API 中都是内存对象的形式絀现,有别于 C 自建的数组因此,你永远不会搞混两者同理,OpenCL 核心程序是独立在 C 源程序之外的不仅美观,也能保证你的 C 程序能被所有 C 編译器编译因为调用 OpenCL 库和调用其他 C 的函数库没有任何不同。

Group 旗下的三大业界标准

再次,CUDA 是在编译时就静态产生 GPU 代码的所以只能产生特定的 GPU 代码。而 OpenCL 的核心程序(kernel)是在运行时被编译成 GPU 指令的由于 kernel 所用的 OpenCL 语言,仅是 C99 的一个子集所以负责编译这个程序的是 OpenCL 运行库自带嘚 LLVM-Clang。这样做的好处是明显的举例来说,如果用户有一堆 OpenCL 的程序比如苹果最新的 Final Cut Pro X 就在, 如果某一天硬件厂商发布了一个全新的 GPU 架构那麼用户安装显卡后,只要下载或更新相关的驱动程序和运行库即可而不需要再求软件厂商发布一个新版本的 Final Cut Pro X。因为 OpenCL 在运行时会根据显鉲厂商提供的驱动和新运行库自动优化程序到特定架构上。所以程序兼容性问题也被圆满解决。

最后由于 OpenCL 是个开放标准,也支持 CPU 和其怹任何计算设备比如数字信号处理芯片(DSPs)和各种专门的处理器架构。所以只要有相关的驱动和运行库OpenCL 程序可以高效地并行运行在任哬架构的运算设备上。由于 OpenCL 和 GCD 的编程模式是一样的因此当 OpenCL 程序在 CPU 上执行时,是跑在 GCD 队列上的

的主要用户之一。如上面提到的 Final Cut Pro X 就是个典范使用 GCD 和 OpenCL 进行大量并行的流媒体处理。在老版本 Final Cut 中每当用户执行一次流媒体操作,都会弹出一个进度条来告诉用户剩余的处理时间洏 Final Cut Pro X 优化后的速度是如此实时,以至于这个进度条被去除了Mac OS X 许多的底层库也使用 OpenCL 重写,如 Core Image本身也是一个 GPU 加速库,使用 OpenCL 后相比原来依然獲得了。

目前看来OpenCL 虽然解决了上面的所有问题且速度飞快,但对普通程序员来说依然是非常底层的技术。而且由于硬件的限制(显卡鈈支持指针运算)很多 C 的标准并未在 OpenCL 中出现,写链表还需要用整数去模拟地址程序员需要手动管理内存,处理底层的核心调用以及数據读写而显卡厂商也大多不愿公开 GPU 的技术细节,因此不像 CPU 程序很容易通过汇编指令分析计算机底层干了什么显卡对于开发者纯粹是个嫼盒,把整个问题分成多少个线程并发也没有一个规律可循有可能不起眼的改动会使 程序运行瞬间变快或变慢数十倍,开发者也不知道其中的原因只能凭经验操作。而且由于不存在良好的调试工具所以很难改正程序的错误。

显卡作为系统最为重要的共享资源之一不潒现代操作系统那样提供内存保护机制,因此一个用户 OpenCL 程序的错误很容易导致整个计算机崩溃所以经常是程序跑一遍后发现操作系统挂叻,重启后发现了一个可能的错误改完后编译运行,操作系统又挂了我用 OpenCL 编写科学计算程序时,大量时间是在重启电脑而不是写程序这些问题仍然阻碍着 OpenCL 被广泛采纳,不过在科学计算界,已经涌现出了越来越多相关的论文和同学一样怎么办和技术相信在不久的将來,情况会有所改观

当写完这篇技术长文时,天色已晚走出教室,和 ENIAC 擦肩而过ENIAC 的出现激励了之后一次次的处理器革命。2009 年发布的 Snow Leopard 可能在整个 Mac OS X 发行版历史中不算最出彩却是对于半导体集成电路革命的一次重大收获。

HFS+ 和 UFS 文件系统同时被引入早期的 Mac OS X随着若干年的发展,HFS+ 提供的功能已超越 UFS使其在 Mac OS X 10.5 之后成为成为唯一正式的 Mac OS X 系统,但因为其背负许多的历史包袱为考虑兼容性,这些陈旧的设计并不能被推翻偅来所以苹果开始秘密研发下一代的文件系统。

在 Unix 系统刚诞生的远古时期文件系统被简单地称为 FS。FS 只包括启动块、超级块(处于硬盘汾区开头用来保存文件系统信息)、inodes(索引节点)及数据FS 文件系统在 Unix 系统刚诞生时还能满足新老客户的需求,但随着科学技术的进步FS 巳不能符合现代文件系统的需求,且会导致抖动等一系列问题当时还是加州大学伯克利分校研究生,后成为著名 BSD 开发者 Marshall 都使用它也成為当今各 BSD 分支(FreeBSD、OpenBSD、NetBSD 及 DragonFlyBSD)的标准文件系统。每个不同的系统无论开源与否,又会在 FFS 文件系统上增加各种扩展这些扩展往往不互相兼容,但神奇的是大家又都使用和原版同样的块大小和数据块宽度。因此在很大程度上这些山寨版 FFS 文件系统又相互兼容,至少在一个操作系统上能对另一操作系统的文件系统执行只读操作因此,FFS 事实上已经成为 Unix 系统的标准文件系统故它有了一个更广泛的称谓——UFS()。

UFS 茬后来的若干年又取得了长足的发展Sun 公司在 Solaris 7 系统中,给 UFS 提供了简单的日志功能日志文件系统指在档案系统发生变化时,先把相关的信息写入一个被称为日志的区域然后再把变化写入主文件系统的文件系统。在文件系 统发生故障(如内核崩溃或突然停电)时日志文件系统更容易保持一致性,并且可以较快恢复Marshall Kirk McKusick 又实现了 BSD 一度引以为豪的 功能,来保证计算机掉电或系统崩溃时通过使元数据按依赖顺序哽新来确保磁盘上总的文件系统保持一致的实现机制。Soft Update 的目标和日志类似但实现代价比日志轻量许多。不过这项功能有所代价主要是需要引入一个后台 FSCK 检查。

分支的文件系统设计了 ACL 访问控制表功能() 先前,Unix 文件系统的访问控制是非常简单的其权限管理分为三个不哃的类别:用户、同组用户以及其他用户,对每个类别Unix 文件系统提供读、写、执行三种权限的管理。这样的许可管理过于粗糙无法指萣某一用户访问的权限,也无法指定更为细致的权限内容(例如准许对一文件实行删 除操作)为解决这个问题,访问控制表被增加到文件系统中使用以存取控制矩阵为基础的存取控制方法。存取控制串列描述每一个文件对象各自的存取控制并 记录可对此物件进行存取嘚所有主体对对象的权限。总之UFS 与时俱进,不断增加新的功能

作为 Mac OS X 的老祖宗 NeXTSTEP,因为基于 BSD所以自然也使用 UFS。而老版的 Mac OS 则使用一个叫做 嘚文件系统HFS 是一个比较古老且不思进取的文件系统,因此在 20 世纪 90 年代末已不能满足当时的需要。在《Mac OS X 背后的故事(一)》中我们提到为了实现 Mac OS 的现代化,Copland 项目被提出Copland 项目的子项目 Sequoia 旨在 HFS 的基础上,加入现代文件系统所必需的新功能如大文件支持、Unicode 文件名支持、长文件名支持、32 位文件映射表支持等。Sequoia 项目即成为后来熟知的 HFS+由 Don Brady 领导,这个团队先花了 6 个月时间把 HFS 项目原本的 Mac 使用的 68K 处理器汇编码改写成 C 代碼然后逐渐。

Mac OS X 10.0 发布后苹果不遗余力地对 HFS+ 进行大规模的扩展和维护,增加了很多 UFS 独有的功能这些新功能使得文件系统更加安全稳定可靠。例如 Mac OS X 10.2.2 中HFS+ 支持日志。日志功能在 Mac OS X 10.2 服务器版中可以简单地设定但在普通桌面版中需要使用命令行进行操作。在 Mac OS X 10.3 中带日志功能的

文件系统除了让用户供稳定地存放文件这一目标以外,还是各项操作系统功能的基础Mac OS X 每个大发行版都要增加数百项新功能,许多新功能严重依赖于文件系统的实现Mac OS X 10.3 提供了 ,因此用户主目录被保存在一个 HFS+ 文件系统加密镜像中Mac OS X 10.4 提供了,能让用户对整个磁盘系统进行快速搜寻、隨打即显这项功能要求文件系统提供任意长度文件元数据(metadata)的支持。因此苹果发布了一个测试版本的 BootCamp 来让用户安装 Mac OS X、Windows 双系统,并在 Mac OS X 10.5 囸式集成进系统

哪怕在 Mac OS X 系统运行,BootCamp 也可以实时调整系统主分区的大小来空出磁盘空间给 Windows,因此HFS+ 又需要支持动态分区大小调整。在 Mac OS X 10.5 中集成了 它是苹果公司所推出备份的工具程序,于 2006 年 8 月 7 日在苹果计算机全球研发者大会(WWDC)中首次公开成为当天观众欢呼声最高的功能。Time Machine 对于修改过的文件会在备份盘上保存一个新拷贝而对于不变的内容,仅在备份盘上存一个指向先前文件的硬链接因此每一次快照只保存改动的文件,而别的文件 只保存占用空间很少的硬链接但 Unix 一般只支持文件的硬链接而不支持目录的硬链接。因此 HFS+ 在这点上走得比 Unix 文件系统更远提供了对于目录的硬链接支持。在 Mac OS X 10.6 中HFS+ 甚至支持文件系统压缩,使得安装后占用比 Mac OS X 10.5 少得多的空间Mac OS X 10.7 提出了 , 能加密整个磁盘洏不是一个用户目录这些功能我们在为读者介绍每个发行版时亦会提到,但总之读者看到HFS+ 的功能随着 Mac OS X 的商业需求不断被扩展。“我在莋了这么多工作后回想才发现我们为 HFS+ 增加了那么多新功能,”苹果前文件系统开发者 Don

由于 HFS+ 经过后来若干年的发展提供的功能已不逊于 UFS,甚至更多更好故至 Mac OS X 10.5 砍掉了安装至 UFS 的支持。HFS+ 成为唯一正式的 Mac OS X 系统

HFS+ 自发布以来,几乎每个发行版都有令人欣喜的改动它也逐渐成为一個非常完善的文件系统。但 HFS+ 立足于 HFS 设计HFS 已有 27 年的历史,HFS+ 亦有 14 年历史这个文件系统有太多的历史包袱,为考虑兼容性这些陈旧的设计並不能被推翻重来。

HFS+ 基于B-树实现当查找B-树中未使用的节点时,HFS+ 只能每次处理 16 位原因是老 Mac 使用的 Motorola 的 68K 芯片原生支持 16 位的数据操作。但不管昰 PowerPC 还是 Intel寄存器都支持 256 位宽的寄存器。

HFS+ 的元数据(metadata)都以大字节序保存原因是 Motorola 的 68k 和后来 Mac 使用的 PowerPC 都使用大字节序。但经过 Intel 迁移后当今的 Mac 嘟使用 Intel 芯片,而 Intel 芯片是使用小字节序的因此每当数据读取或存入时,还要经过小字节序和大字节序的转换远古时期磁盘很慢,计算机處理器的速度也很低因此进行一次磁盘操 作会占用较多的时间,但当今的磁盘、处理器处理一次文件系统操作的时间远小于一秒,因此所有主流磁盘文件系统的时间分辨率都是一至数百纳秒级别的

HFS+ 的元数据有全局锁,同一时间只有一个进程可以访问更新文件系统在單核处理器连手机平板都较少见到的当今,这种设计显得很幼稚

HFS+ 亦没有稀疏文件的支持。例如我们在 SQL 中建立了一个数据库SQL 分配了 10GB 的文件给这个数据库,并且在文件头和文件尾写上一些字节的数据而由于我们还没有给这个数据库添加新的数据,所以这 10GB 的文件除了头尾外其他字节都为0现代的文件系统基本都支持稀疏文件,也就是说当处理这个数据库操作时,事实上往磁盘写入的数据只有那文件头和文件尾的 若干字节而 HFS+ 则需要把那些 0 也写上,因此会完整写入 10GB 的数据耗费长得多的时间。

此外HFS+ 不具备元数据校验功能、快照功能、写入時复制功能、、等很多现代磁盘系统所具备的功能,也这些功能的加入并不容易。

其中最要命的是HFS+ 不像一些先进的文件系统,支持写叺时复制事务模型也没有快照和克隆。这使得用户数据时时处于风险之中例如由于因为断电、内核崩溃等原因,文件系统上写 到一半嘚数据小则导致个别文件损坏,大则导致整个文件系统崩溃在生产领域,这样不可靠的文件系统很有可能带来致命的灾难。

正是由於上述这些原因连我们介绍过的短视的 Linus Torvalds 都认为 HFS+ 是个垃圾文件系统。苹果自然受不了这种侮辱因此,干掉 HFS+ 势在必行用什么取代 HFS+ 呢?苹果开始秘密研发下一代的文件系统

由于各种缺点,干掉 HFS+ 势在必行然而用什么取代 HFS+ 呢?苹果开始秘密研发下一代的文件系统——ZFS然而茬诸多因素的干扰下,Mac OS X 的 ZFS 支持却只是昙花一现未来文件系统之路将走向何方?

文件系统的新时代——ZFS

为了代替 HFS+。但这时 Sun 公司的工作让蘋果的员工们为之一振

2004 年,Sun 公司发表了其杰出的这是一个 128 位的文件系统,本为 Solaris 操作系统开发于 2005 年 10 月 31 日并入了 。后成为一个使用 CDDL 协议條款授权的开源项目

ZFS 是一个具有高存储容量、文件系统与卷管理概念整合、崭新的磁碟逻辑结构的轻量级文件系统,同时也是一个便捷嘚存储池管理系统

ZFS 的一个重大特点就是拥有大容量。ZFS 是一个 128 位的文件系统这意味着它能存储 1800 亿亿(18.4×1018)倍于当前 64 位文件系统的数据。ZFS 嘚设计如此超前以至于这个极限就当前现实而言可能永远无法遇到项目领导 Bonwick 曾说:“要填满一个 128 位的文件系统,将耗尽地球上所有存储設备除非你拥有煮沸整个海洋的能量。”假设每秒钟创建 1000 个新文件达到 ZFS 文件数的极限需要约 9000 年。

此外ZFS 的一个重要指导思想是不单单詓做一个文件系统,而是实现一套完整的卷管理方案不同于传统文件系统需要驻留于单独设备或者需要一个卷管理系统去使用一个以 上嘚设备,ZFS 建立在虚拟的被称为“zpools”的存储池之上每个存储池由若干虚拟设备组成。这些虚拟设备可以是原始磁碟也可能是一 RAID1 镜像设备,或是非标准 RAID 等级的多磁碟组于是 zpool 上的文件系统可以使用这些虚拟设备的总存储容量。

有了卷管理方案后ZFS 走得更远,加入了快照和克隆等实用的文件系统功能当 ZFS 写新数据时,包含旧数据的块被保留磁盘只写入修改过的那部分数据块。所以快照的建立非常快只存储兩个快照间的数据差异,因此快照也是空间优化的克隆 指两个独立的文件系统共享一些列的块。当任何一个克隆版本的文件系统被改变時只创建改动的数据块,因此非常快速也占用少得多的空间。

而 ZFS 最大的贡献在于它是第一个支持写入时复制功能(COWcopy on write)的文件系统。所有文件系统中的块都包括 256 位的校验值含有活动数据的块从来不被覆盖;而是分配一个新块,并把修改过的数据写在新块上所有与该塊相关的元数据块都被重新读、分配和重写。因此当 一个数据写入时发生了任何意外错误,原先的数据依然可以被访问且文件系统知噵哪个操作出了错误而没有完成。ZFS 的快照和克隆正是因此项技术而得以实现

ZFS 对于用户而言,界面友好先前 ,FreeBSD 因此还建了一套给逻辑卷管理做深层次的抽象。而 ZFS 文件系统自带卷管理方案几乎所有烦琐复杂的操作都能,我用传统的卷管理工具已有近十个年头第一次使鼡 ZFS 时,完全被其易用性震撼所以我毫不犹豫地把手头所有的服务器迁移到了 ZFS。

由于 ZFS 各种美好加上其开源性质,所有的操作系统都想支歭它Solaris、OpenSolaris 项目一直作为标准实现供其他系统参考。并在 ,作为 FreeBSD 第七版最耀眼的三项功能之一(另一项功能是我们先前提到的 ULE以及 Sun DTrace 的移植工作)。Linux 则麻烦得多,因为 Linux 内核的协议 GPL 是个和很多协议都水火不容的奇葩协议ZFS 分发所采用的 CDDL 和 GPL 会产生冲突,所以一方面 ;另一方面由 Oracle 牵头,专为 Linux 开发 Btrfs事实上就是一个 ZFS 的山寨版,可惜折腾了几年Oracle 自己又把 Sun 收购了,且到我撰写此文时 Btrfs 依然没有正式的稳定版本发布

曇花一现的 ZFS 梦

刚才提到,苹果在招兵买马雇员工开发新一代的文件系统,而 Chris Emura(Apple CoreOS 的文件系统开发经理)及 Don Brady(先前提到此人领导 HFS+ 的开发)兩个富有经验的文件系统开发者却被衣服一样晾在了一边无所事事。2006 年刚刚提到的 Pawe Jakub Dawidek 正在往 FreeBSD 迁移 Sun 的 ZFS,这项工作立刻引起了

苹果一看两人的 ZFS 嘚移植工作大有前途立即跟进。2007 年的苹果全球开发者大会上苹果让 Chris Emura 及 Don Brady 举办了一场小型讲话,介绍 Mac OS X 对 ZFS 的支持这场讲话先前并没有在官方声明中告示,但讲话的报告厅依然挤满了听众随后 ZFS 移植的源码在 Mac OS Forge 公布。在最终版的 Mac OS X 10.5 带有试验性的 ZFS 只读支持以命令行方式提供。用户鈳以挂载 ZFS 的存储池并对池中的文件系统进行读取操作。

苹果一直使移植并使用 Sun 的关键技术除了 Java 以外,Mac OS X 10.5 的 Xcode 套件也加入了 DTrace 的支持并提供叻一个好用的图形界面 Instruments 让开发者更方便地调用 DTrace。ZFS 除了解决 HFS+ 的所有问题提供安全可靠的文件系统基础外,还可以简化苹果许多软件的实现例如前文提到的 Mac OS X 10.5 的 Time 的快照功能的图形界面插件名为 Time Slider,和苹果的 Time Machine 提供了非常相近的功能我在使用后感觉不错。

因此在 WWDC 2008 上Snow Leopard 被提出,其中┅项很重要的卖点就是对 ZFS 的完整的读写支持在 Mac OS X 的服务器版,苹果也将提供一套图形界面工具来方便维护人员管理 ZFS 存储池在当时的 Snow Leopard Server 主页仩,苹果声明 ZFS 将作为一项主推功能

但好景不长,一年后的苹果开发者大会时ZFS 相关的内容被悄悄从任何公开的文档、网站、发布会中撤丅,没有给出任何的理由Mac OS Forge 上的 ZFS 代码和页面也被苹果移除。外界有很多对此的猜测但没有任何猜测得到苹果官方的或是哪怕离职员工的證实。

猜测之二是 ZFS 的关键技术 Copy On Write 有专利问题NetApp 声称他们拥有 COW 的专利因此在起诉 Sun,苹果不想在当中冒风险

猜测之三是 ZFS 和苹果的 XNU 内核有协议冲突。我虽然不学法律但我认为这个说法不完全对,因为 ZFS 和 DTrace 一样是以 CDDL 发布的开源软件,既然 DTrace 可以无后顾之忧地加入到 XNU 中ZFS 也没有理由不鈳以。事实上除了 Linux 这种少数使用 GPL 这类奇葩协议的内核,大多数系统的协议都不和 CDDL 冲突FreeBSD 也好,Mac

但事实上如果把三种猜测并在一起,我們可以看到一个更全局的可能性:对于猜测之二苹果可能并非想使用 CDDL,而是想从 Sun 买下一个私有的协议这样一来,Sun 不但提供更好的技术支持出了问题(比如猜测二中的专利问题)也可以让 Sun 为自己背黑锅。结果 Sun 可能和苹果价格谈不拢加上猜测之一提到的 Sun 大势已去,让苹果觉得还不如自己造个轮子来得方便Sun 公司开发 ZFS 的主力 Jeff Bonwick 虽不能提供详细的信息,但他基本证实了这种说法

无论如何,Mac OS X的 ZFS 支持如昙花一現般消失了。

未来文件系统之路走向何方

MacZFS 提供更新更稳定的移植

不过,砍了 ZFS 后的苹果目标也变得更清晰——和 Sun 的谈判让苹果觉得与其支付高额的协议费还不如雇人自己做个新的,再说了作为比 Sun 大得多的 IT 公司,苹果可以轻而易举地搞个更强大的东西灭了它因为 ZFS 其实也鈈如传说中的那样好。

首先时代在进步。ZFS 之后又有很多新的和文件系统相关的研究,如 Ohad Rodeh 的论文和同学一样怎么办即成为后来 BtrFS 实现的基础,可能比 ZFS 做得更好

其次,ZFS 是十年前开始设计的文件系统但十年中,存储工具已发生了重大的变化ZFS 为传统磁盘设计,但传统磁盘嘚市场空间已不断被 SSD、闪存的吞食尤其是 MacBook Air 中使用的 Flash 存储器便宜好用又小巧,可能将来会在 MacBook Pro 甚至 iMac 中得到更大的推广采用为传统磁盘优化嘚 ZFS 就不显得那么有吸引力。

最后ZFS 和苹果有不同的用户群。ZFS 目标用户是大企业的工作站和服务器在那里,大容量的存储空间、高级的卷管理显得非常重要但苹果面对的基本都是个人用户——先前苹果还卖服务器,但后来 Xserve 都被苹果砍了有几个个人用户需要使用到 ZFS 这些高級的功能呢?更重要的苹果的主要利润将移到 iPhone、iPod、iPad、Apple TV 这些小设备上,ZFS 需要占用大量的内存来实现文件系统操作在这些小设备上,内存佷少ZFS 根本跑不起来。

苹果非常清楚这些问题工程师们现在一定在紧锣密鼓地开发下一代文件系统。在 10.7 及 10.8 中这套文件系统并未浮出水媔,但一些细节值得留意在 10.7 中,苹果发布了 Core Storage但并未声张。这是一套逻辑卷管理工具类似于前文提到的 FreeBSD 的 GEOM。这个版本的 File Vault 2 亦使用 Core Storage 重写鈳以看到虽然苹果在上层不断地淡化文件系统的概念,例如 iCloud 的发布和 iOS 中对于文件这一概念的故意忽略但苹果在底层文件系统上的动作越來越大,想必在将来苹果定会让我们感到重大的惊喜。

原标题:【Google Jeff Dean独自署名论文和同学┅样怎么办】深度学习革命及其对计算机架构和芯片设计的影响讲述AI芯片发展历程与未来

长文介绍了后摩尔定律时代的机器学习研究进展,以及他对未来发展趋势的预测判断

  • 后台回复“ DLRC ” 就可以获取 《深度学习革命及其对计算机架构和芯片设计的影响,讲述AI芯片发展历程与未来》 论文和同学一样怎么办下载链接索引~

专知专业可信的人工智能知识分发,让认知协作更快更好!欢迎注册登录专知 www.zhuanzhi.ai获取5000+AI主題干货知识资料!

欢迎微信扫一扫加入 专知人工智能知识星球群,获取 最新AI专业干货知识教程视频资料和与专家交流咨询

点击“ 阅读原攵”了解使用 专知,查看5000+AI主题知识资料

我要回帖

更多关于 论文和同学一样怎么办 的文章

 

随机推荐