新一代即时编译器

对需要长时间运行的应用来说,由于经过充分预热,热点代码会被 HotSpot 的探测机制准确定位捕获,并将其编译为物理硬件可直接执行的机器码,在这类应用中 Java 的运行效率很大程度上是取决于即时编译器所输出的代码质量。

HotSpot 虚拟机中包含有两个即时编译器,分别是编译时间较短但输出代码优化程度较低的客户端编译器(简称为 C1)以及编译耗时长但输出代码优化质量也更高的服务端编译器(简称为 C2),通常它们会在分层编译机制下与解释器互相配合来共同构成 HotSpot 虚拟机的执行子系统的。

自 JDK 10 起,HotSpot 中又加入了一个全新的即时编译器:Graal 编译器,看名字就可以联想到它是来自于前一节提到的 Graal VM。Graal 编译器是作为 C2 编译器替代者的角色登场的。C2 的历史已经非常长了,可以追溯到 Cliff Click 大神读博士期间的作品,这个由 C++写成的编译器尽管目前依然效果拔群,但已经复杂到连 Cliff Click 本人都不愿意继续维护的程度。而 Graal 编译器本身就是由 Java 语言写成,实现时又刻意与 C2 采用了同一种名为“Sea-of-Nodes”的高级中间表示(High IR)形式,使其能够更容易借鉴 C2 的优点。Graal 编译器比 C2 编译器晚了足足二十年面世,有着极其充沛的后发优势,在保持能输出相近质量的编译代码的同时,开发效率和扩展性上都要显著优于 C2 编译器,这决定了 C2 编译器中优秀的代码优化技术可以轻易地移植到 Graal 编译器上,但是反过来 Graal 编译器中行之有效的优化在 C2 编译器里实现起来则异常艰难。这种情况下,Graal 的编译效果短短几年间迅速追平了 C2,甚至某些测试项中开始逐渐反超 C2 编译器。Graal 能够做比 C2 更加复杂的优化,如“部分逃逸分析 (opens new window)”(Partial Escape Analysis),也拥有比 C2 更容易使用“激进预测性优化 (opens new window)”(Aggressive Speculative Optimization)的策略,支持自定义的预测性假设等等。

今天的 Graal 编译器尚且年幼,还未经过足够多的实践验证,所以仍然带着“实验状态”的标签,需要用开关参数去激活,这让笔者不禁联想起 JDK 1.3 时代,HotSpot 虚拟机刚刚横空出世时的场景,同样也是需要用开关激活,也是作为 Classic 虚拟机的替代品的一段历史。

Graal 编译器未来的前途可期,作为 Java 虚拟机执行代码的最新引擎,它的持续改进,会同时为 HotSpot 与 Graal VM 注入更快更强的驱动力。

Kudos to Star
总字数: 851 字  最后更新: