给 V8 一个提醒:通过显式编译提示加速 JavaScript 启动
快速运行 JavaScript 是响应式网络应用的关键。即使有 V8 的高级优化,在启动时解析和编译关键 JavaScript 仍然会导致性能瓶颈。知道在初始脚本编译期间应编译哪些 JavaScript 函数可以加速网页加载。
快速运行 JavaScript 是响应式网络应用的关键。即使有 V8 的高级优化,在启动时解析和编译关键 JavaScript 仍然会导致性能瓶颈。知道在初始脚本编译期间应编译哪些 JavaScript 函数可以加速网页加载。
V8的最终优化编译器Turbofan以使用节点海洋 (SoN)而闻名,这是少数几个在生产环境中使用的大规模编译器之一。然而,从大约三年前开始,我们逐步放弃节点海洋,采用一种更传统的控制流图 (CFG) 中间表示 (IR),我们将其命名为Turboshaft。目前,Turbofan的整个JavaScript后端已经改用Turboshaft,而WebAssembly的整个管道也采用了Turboshaft。Turbofan的两个部分仍然使用一些节点海洋:一个是内置管道,我们正在慢慢被Turboshaft替换;另一个是JavaScript管道的前端,我们正在用另一个基于控制流图的IR(Maglev)代替。本文将阐述我们为何离开节点海洋的原因。
在 V8 中,我们始终致力于提升 JavaScript 性能。作为此项工作的一个部分,我们最近重新审视了 JetStream2 基准测试套件,以消除性能瓶颈。本篇文章详细介绍了我们进行的一项优化,该优化使 async-fs
基准测试的性能提升了显著的 2.5 倍
,并对整体得分产生了显著影响。这项优化源于基准测试,但类似的模式确实存在于 真实代码中。
你是否曾想过 undefined
、true
和其他核心JavaScript对象是从哪里来的?这些对象是任何用户定义对象的原子,并且必须首先存在。V8将它们称为不可移动的不可变根,它们位于自己的堆——只读堆中。由于它们被频繁使用,快速访问至关重要。而什么比在编译时正确猜测它们的内存地址更快呢?
欢迎来到激动人心的V8世界,在这里速度不仅仅是一种特性,而是一种生活方式。随着我们向2023告别,是时候庆祝V8今年取得的令人印象深刻的成就了。
通过创新的性能优化,V8继续拓展Web不断演变的边界。我们引入了新的中层编译器,并对顶级编译器基础设施、运行时和垃圾回收器进行了多项改进,从而实现了全方位的显著速度提升。
在Chrome M117中,我们引入了一个新的优化编译器:Maglev。Maglev位于现有的Sparkplug和TurboFan编译器之间,扮演快速生成足够优质代码优化编译器的角色。
直到2021年,V8有两个主要的执行层级:Ignition(解释器)和TurboFan(V8的优化编译器,专注于峰值性能)。所有的JavaScript代码都首先被编译为Ignition字节码,并通过解释执行。在执行期间,V8记录程序的行为,包括跟踪对象的形状和类型。执行过程中收集的元数据和字节码会被传递到优化编译器,以生成高性能的、通常基于推测的机器代码,这种机器代码运行速度明显快于解释器。
在 V8 v9.1 中,我们暂时在桌面端禁用了嵌入式内置。虽然嵌入内置显著改善了内存使用,但我们意识到嵌入内置与 JIT 编译代码之间的函数调用可能会带来可观的性能损失。这种成本取决于 CPU 的微架构。在这篇文章中,我们将解释为什么会发生这种情况、性能的表现如何以及我们计划从长期角度解决这个问题的方法。
super
关键字 可用于访问对象父级上的属性和函数。
以前,访问 super 属性(例如 super.x
)是通过运行时调用实现的。从 V8 v9.0 开始,我们在非优化代码中重用了内联缓存 (IC) 系统,并且为 super 属性访问生成了适当的优化代码,而不需要跳转到运行时。
得益于 Chrome 和 Emscripten 的近期工作,现在您可以在 WebAssembly 应用程序中使用高达 4GB 的内存。这比之前 2GB 的限制有了很大的提升。或许您会觉得奇怪为什么会有这种限制——毕竟人们无需特殊工作就可以使用 512MB 或 1GB 的内存!——但事实证明,从 2GB 跳到 4GB 不仅浏览器端需要一些特殊处理,工具链端也有挑战,这些内容将在本文中详细介绍。