本文由半导体产业纵横(ID:ICVIEWS)编译自chipsandcheese
不是x86需要消亡,而是RISC与CISC的辩论应该终结。
现代CPU的真实面貌
以下是两个由不同公司开发、运行不同指令集的无关联CPU的微架构框图。这两个CPU核心都不简单,但它们有很多共同之处。
AMD的Zen 4架构(根据AMD的图表绘制了此图,并通过微基准测试推断出一些细节。)
Arm的Cortex X2架构(主要根据微基准测试结果推断出架构细节。)
Cortex X2和Zen 4都使用超标量、推测性、乱序执行以及寄存器重命名。在核心之外,Cortex X2和Zen 4都使用复杂的多级缓存层次结构和预取器来避免DRAM访问惩罚。所有这些特性都与最大化性能有关,尤其是在计算性能不断超越DRAM性能的情况下。它们与所使用的指令集无关。
获取和解码指令的复杂性并不是x86独有的问题。没有现代高性能的x86或ARM/MIPS/Loongarch/RISC-V CPU会像20世纪70年代的MOS 6502那样直接使用指令位来控制执行硬件。相反,它们都将指令解码为乱序执行引擎和其功能单元所理解的内部格式。
RISC架构的解码成本也很高,即使它们使用的是固定长度的指令。与英特尔和AMD一样,Arm通过使用微型运算缓存,以解码后的内部格式保存最近使用过的指令,从而降低解码成本。一些Arm内核更进一步,在L1指令缓存中以更长的中间格式存储指令。这就将一些解码阶段移到了指令缓存填充阶段,使其脱离了较热的取指+解码阶段。许多Arm内核将这种 “预编码 ”技术与微操作缓存相结合。解码是昂贵的,大家都会采取措施来降低解码成本。
一些观察到的LASX向量扩展指令编码来自MIPS的后继者LoongArch。
有人对x86指令集扩展和指令数量增加表示担忧,但这两者都不是x86独有的特性。ARM也经历了众多的修订和扩展。x86-64有SSE、AVX(2)和AVX-512向量扩展,而64位ARM(aarch64)则有ASIMD、SVE和SVE2向量扩展。MIPS也有类似的情况,它有MSA SIMD扩展。MIPS没有像ARM和x86那样获得更多的扩展,那是因为已经没有人再使用它了。LoongArch源自64位MIPS,但使用了不兼容的指令编码。Loongson已经用LSX和LASX向量扩展对LoongArch进行了扩展。
ISA还会收到与向量无关的更新。aarch64得到了加速原子内存操作和加快memcpy/memset例程的更新。x86也会不时收到类似的更新,尽管是在不同的领域。这是因为更多的晶体管预算让工程师能够在硬件中做更多的事情,而为特定工作负载添加更多指令是加速它们的好方法。
有人指出x86的mpsadbw指令“至少进行了19次加法,但CPU 仅在两个时钟周期内完成”。作者应该通过查看其用例来思考为什么存在这样的指令。视频编解码器通过表示大多数帧与前一帧的不同之处来高效利用带宽和磁盘空间,而不是存储整个帧。计算绝对差值和(SAD)是观察块变化程度的好方法,并且是视频编码的重要组成部分。ARM也有类似的向量指令。
有人认为增加更多指令(如mpsadbw)会使寄存器重命名和指令调度更加复杂。这听起来很有道理,但并不符合实际情况。尽管 mpsadbw 执行了更多的底层操作,但它只需要两个寄存器输入和一个目标寄存器。因此,重命名器只需要从寄存器别名表中读取两个值来确定从哪里获取输入,并分配一个空闲寄存器来存储结果。
我们可以使用类似RISC的指令(不包括mpsadbw的选择部分)来执行向量SAD计算。每条简单的RISC指令都需要与“复杂”的msadbw指令相同程度的寄存器重命名。每个输入都需要在寄存器别名表中进行查找,并且需要分配一个空闲寄存器来保存每个结果。
仅涵盖绝对差值和的部分,甚至都不是全部,因为已经有太多的重叠箭头了。
复杂指令实际上降低了寄存器重命名和调度成本。处理等效的一系列简单指令将需要更多的寄存器重命名和调度工作。一个假设的纯RISC内核将需要使用更高的时钟频率或更宽的重命名器来达到可比的性能。这两者都不容易实现。如上所示,同一个寄存器可能会在很短的时间内被多次重命名,因此更宽的重命名器必须应对更长的潜在依赖链。除了更宽的重命名器之外,纯RISC设计还需要更大的寄存器文件、调度器和其他后端缓冲区来减轻需要跟踪更多指令的影响。
变化已经到来
当然,ARM CPU的设计人员深知有效利用获取/解码/重命名带宽的重要性。他们还了解节约使用寄存器文件和调度器条目等后端资源的重要性。这就是为什么现在的ARM拥有大量复杂的指令,可以在引擎盖下执行许多底层操作。矢量指令可能是最突出的例子,但也很容易找到其他例子。Aarch64长期以来一直支持通过移位索引寄存器生成的地址从内存加载值,并将其添加到基寄存器。这在引擎盖下是一连串三个相关操作,但它简化了数组寻址。
另一方面,简单指令通常构成执行程序指令流的大多数。这尤其适用于难以并行化的程序,如文件压缩或网页浏览。因此,今天的CPU必须擅长快速执行简单操作。同时,它们也受益于拥有复杂指令来加速特定工作负载。
Arm Cortex X2优化手册中的一页显示了内核进行复杂运算的情况(例如,RSUBHN2可以进行16次8位减法运算,选择每个运算结果中最重要的一半,并进行四舍五入,整个过程需要两个周期)。
考虑到这一现实,今天的指令集已经发生了变化。“CISC”和“RISC”这两个标签只反映了指令集的遥远起源。它们反映的是三十多年前几乎不相关的哲学争论,现在则完全无关紧要。是时候让CISC与RISC的争论永远消失了。
问题的真正所在
当我们津津乐道于不同的CPU及其性能时,很容易忘记这些性能的用途:运行软件。如果CPU不能运行你所需的软件,那它就是一块小砖头。x86-64 CPU保留了真实模式,这样操作系统就能以同样的方式启动。如今,你可以创建一个单一的操作系统安装硬盘,它既可以在现代的Zen 4系统上运行,也可以在15年前的Phenom 统上运行(只要确保使用MBR启动即可),还可以在两者之间的任何系统上运行。15 年前的Phenom系统可以运行Windows 10或Ubuntu 22.04等最新操作系统。当然,这是有限制的,你无法在Northwood奔腾4上运行Windows 10。但真正的模式支持是同一操作系统启动代码能在众多CPU上运行的原因之一。这是PC 兼容性生态系统的一部分,它赋予x86 CPU无与伦比的兼容性和使用寿命。
其他生态系统则呈现出鲜明对比。即使来自同一制造商且发布时间仅相隔几年,不同的手机也需要定制化的镜像。操作系统更新涉及为每台设备构建和验证操作系统镜像,这给手机制造商带来了巨大的负担。因此,基于ARM的智能手机在硬件性能还远未过时之前就已经不再受支持,变成了电子垃圾。如果用户解锁引导加载程序并使用像LineageOS这样的社区支持镜像,他们有时可以让设备再更新几年,但这远非理想之选。
LineageOS 项目拥有超过 1000个存储库,因为每台设备的镜像构建都需要单独处理。
英特尔和AMD正确地认识到,在兼容性上投入额外努力是值得的。这样做简化了软件分发,并让用户能够更长时间地使用他们昂贵的硬件。
当然,兼容性不可能永远保持。ISA必须发展。AMD和英特尔可能希望通过减少支持实模式所需的验证工作来节省一些资金。英特尔已经计划放弃实模式。随着需求的变化,任何 ISA 都必须接受更新。但是,应该尽量减少兼容性的破坏,以避免让用户陷入没有明确好处的升级循环。
结论
CISC与RISC的争论似乎每隔几年就会重新燃起,往往伴随着x86应该消亡的声音。这场争论在20世纪90年代初最为激烈。例如,Alpha的EV5是1994年推出的一款四宽核心,运行频率为266 MHz。而英特尔1994年最好的CPU是双宽的120 MHz Pentium。但很快,英特尔就展示了他们自己也能开发出高性能设计,而我们也知道在这个十年结束时发生了什么。
2000年代,英特尔公司试图将x86推向边缘。Itanium的设计遵循了Hackaday的作者所坚信的原则。它使用一套128 架构寄存器来避免寄存器重命名,使用简单、固定长度的指令。它放弃了失序执行,将调度责任转移给了编译器。所有这些想法都失败了,因为晶体管预算的增加使得分支预测和更大的失序执行结构成为可能。硬件失序执行可以适应不断变化的程序行为,并自然生成更优化的指令调度。由于失序执行是高性能所必需的,因此,Itanium的存在没有什么意义。
来自英特尔的Hot Chips演示
到了2010年代末,Marvell的ThunderX3和高通的Centriq服务器CPU试图在服务器市场站稳脚跟。两者都使用了aarch64,但在十年末都宣告终止,几乎没有取得什么成果。这并不是说aarch64是一个糟糕的指令集架构,或者说ThunderX3/Centriq因此而注定失败。相反,一个CPU需要将高性能与强大的软件生态系统结合起来才能获得支持。
如今,aarch64拥有更强大的软件生态系统和性能更佳的CPU内核。Ampere Altra芯片已部署在谷歌、微软和甲骨文的公有云产品中。亚马逊也在其云中使用Arm的Neoverse内核。aarch64已具备与x86正面竞争并挑战英特尔/AMD双头垄断地位的实力,这是一件好事。但是,Arm、RISC-V和MIPS/LoongArch必须通过其硬件设计和软件生态系统的优势来取得成功。所有这些指令集在关键领域都足够优秀。
展望未来,希望我们能就各种CPU设计的优势进行更有成效、更深入的研究讨论。当然,ISA可以成为讨论的一部分,因为各种ISA扩展可能对性能产生显著影响。同时也应该讨论许可和版权费问题,因为这两者经常扼杀各种有前景的技术。但是,像“在MIPS、ARM或RISC-V等RISC架构中,指令的实现全靠硬件”这样完全错误的观点必须被摒弃。现在已经不是1980年了。
*声明:本文系原作者创作。文章内容系其个人观点,我方转载仅为分享与讨论,不代表我方赞成或认同,如有异议,请联系后台。