切换至深色主题
V8引擎实现原理
V8引擎简介
V8 是 Google 的开源高性能 JavaScript 和 WebAssembly 引擎,用 C++ 编写。它用于 Chrome 和 Node.js 等。它实现了ECMAScript和WebAssembly,可以独立运行,也可以嵌入到任何 C++ 应用程序中。
官网:https://www.chromium.org/
GitHub:https://github.com/chromium/chromium 官网:https://v8.dev/
GitHub:https://github.com/v8/v8
chromium源码
https://source.chromium.org/https://source.chromium.org/gnhttps://source.chromium.org/chromiumoshttps://source.chromium.org/chromiumhttps://source.chromium.org/chromium/chromiumhttps://source.chromium.org/chromium/chromium/srchttps://source.chromium.org/chromium/chromium/src/+/main:v8/
https://source.chromium.org/chromium/chromium/src/+/main:third_party/blink/
chromium结构设计:https://www.chromium.org/developers/design-documents/ 多进程架构:https://www.chromium.org/developers/design-documents/multi-process-architecture 过程模型和站点隔离:https://chromium.googlesource.com/chromium/src/+/main/docs/process_model_and_site_isolation.md Blink 的工作原理:https://docs.google.com/document/d/1aitSOucL0VHZa9Z2vbRJSyAIsAz24kX8LFByQ5xQnUg/edit Chrome浏览器引擎 Blink & V8:https://cloud.tencent.com/developer/news/721616
理解 V8 的字节码:https://medium.com/dailyjs/understanding-v8s-bytecode-317d46c94775
sparkplug编译器:https://v8.dev/blog/sparkplug
turbofan:https://v8.js.cn/docs/turbofan/ V8 中的推测优化:https://ponyfoo.com/articles/an-introduction-to-speculative-optimization-in-v8https://benediktmeurer.de/2017/03/01/v8-behind-the-scenes-february-edition Ignition+TurboFan:https://benediktmeurer.de/2016/11/25/v8-behind-the-scenes-november-edition 深入研究 TurboFan JIT:https://v8.js.cn/blog/turbofan-jit/
https://html.spec.whatwg.org/multipage/parsing.html#delay-the-load-event 解析:https://html.spec.whatwg.org/multipage/parsing.htmlhttps://html.spec.whatwg.org/multipage/ HTML解析器:https://html.spec.whatwg.org/
Chrome 中的 GPU 加速合成:https://www.chromium.org/developers/design-documents/gpu-accelerated-compositing-in-chrome/https://www.chromium.org/developers/design-documents/chromium-graphics/ Blink渲染引擎代码:https://chromium.googlesource.com/chromium/src/+/HEAD/third_party/blink/ GPU 架构路线图:https://www.chromium.org/developers/design-documents/gpu-accelerated-compositing-in-chrome/gpu-architecture-roadmap/ 多进程资源加载:https://www.chromium.org/developers/design-documents/multi-process-resource-loading/
渲染引擎:https://www.chromium.org/blink/ 渲染管线:https://docs.google.com/presentation/d/1boPxbgNrTU0ddsc144rcXayGA_WF53k96imRH8Mp34Y/edit#slide=id.ga884fe665f_64_29
V8 的内部分析器:https://v8.js.cn/docs/profile/https://v8.js.cn/docs/build/https://v8.js.cn/docs/build-gn/https://v8.js.cn/docs/source-code/
简介与核心思想
chromium,即Chrome浏览器内核。
简介与核心思想
V8,用C ++编写的Google开源高性能JavaScript和WebAssembly引擎,实现了ECMA-262中指定的ECMAScript。
解析器:负责将JS源代码解析成抽象语法树AST 解释器:负责将AST解析成字节码bytecode,同时解释器也有解释执行bytecode的能力 编译器:负责编译出运行更加高效的机器代码
马蒂亚斯。我在 Google 从事 Chrome DevTools 和 V8 JavaScript 引擎:https://mathiasbynens.be/
JavaScript 引擎架构设计
解析器: 编译器:
JavaScript 引擎的工作原理
---------------------------------------
Duktape
---------------------------------------
简介与核心思想
Duktape - 可嵌入的 Javascript 引擎,专注于便携性和紧凑的占用空间。一个用 C++ 编写的轻量级 JavaScript 解释器,并将其编译为 WebAssembly。 可移植性和减少内存占用。 仅支持 ES5
简介与核心思想
BTW,QuickJS 的作者是 Fabrice Bellard,知名开源项目 FFMPEG 和 QEMU 都出自他手。 QuickJS 是一个基于 C 实现小型且可嵌入的 Javascript 引擎。它支持 ES6(ES2020规范),包括模块、异步生成器、代理和 BigInt。
实现JavaScript引擎的流行项目的列表
V8 — 开源,由 Google 开发,用 C ++ 编写 Rhino — 由 Mozilla 基金会管理,开源,完全用 Java 开发 SpiderMonkey — 是第一个支持 Netscape Navigator 的 JavaScript 引擎,目前正供 Firefox 使用 JavaScriptCore — 开源,以Nitro形式销售,由苹果为Safari开发 KJS — KDE 的引擎,最初由 Harri Porten 为 KDE 项目中的 Konqueror 网页浏览器开发 Chakra (JScript9) — Internet Explorer Chakra (JavaScript) — Microsoft Edge Nashorn, 作为 OpenJDK 的一部分,由 Oracle Java 语言和工具组编写 JerryScript — 物联网的轻量级引擎
Sparkplug 是用于 V8 的新中间层 JavaScript 编译器
Chromium多进程架构
Chromium 分为两个主要部分(不包括其他库):浏览器和渲染器(包括 Blink,Web 引擎)。浏览器是主要进程,代表了所有的 UI 和 I/O。渲染器是(通常)由浏览器驱动的每个选项卡的子进程。它嵌入了 Blink 来进行布局和渲染。
重要通知
Chromium为浏览器选项卡使用单独的进程,以保护整个应用程序免受渲染引擎中的错误和故障的影响,同时还限制每个渲染引擎进程对其他进程和系统其余部分的访问。在某些方面,这给网页浏览带来了内存保护和访问控制给操作系统带来的好处。

多进程架构
浏览器进程
将运行 UI 并管理选项卡和插件进程的主进程称为“浏览器进程”或“浏览器”。
渲染进程
- 特定于Tab选项卡的进程称为“渲染进程”或“渲染器”。每个渲染进程都有一个全局RenderProcess对象,用于管理与父浏览器进程的通信并维护全局状态。
- 浏览器为每个渲染进程维护一个对应RenderProcessHost,它管理浏览器状态和渲染器的通信。浏览器和渲染器使用Chromium 的 IPC 系统进行通信。
- 渲染器使用 Blink开源布局引擎来解释和布局 HTML。
共享渲染过程
有时有必要或希望在选项卡或窗口之间共享渲染过程。Web 应用程序打开一个新窗口,它希望与它同步通信,例如,在 JavaScript 中使用 window.open。在这种情况下,当我们创建新窗口或选项卡时,我们需要重用打开窗口的进程。如果进程总数太大,或者如果用户已经打开一个导航到该域的进程,我们也有策略将新选项卡分配给现有进程。
过程模型
Chromium 的流程模型决定了如何将文档、工作人员和其他 Web 内容划分为流程。
站点隔离
- 锁定的渲染器进程:渲染器进程可以限制为来自单个网站或来源的文档和工作人员,即使这些文档在 iframe 中也是如此。
- 浏览器强制限制:特权浏览器进程可以监视来自锁定进程的 IPC 消息,以限制它们的操作或对站点数据的访问(例如,使用 ChildProcessSecurityPolicy::CanAccessDataForOrigin)。这可以防止受损的渲染器进程请求跨站点数据、使用授予其他站点的权限等。
- 网络响应限制:Chromium 可以确保锁定的渲染器进程只允许从其指定站点或来源接收敏感数据(例如 HTML、XML、JSON),同时仍然允许跨域子资源请求(例如图像、媒体)作为需要兼容性。这是使用跨域读取阻塞(CORB) 或不透明响应阻塞(ORB) 实现的。
进程间通信(IPC)
Chromium 具有多进程架构,这意味着我们有很多进程相互通信。我们主要的进程间通信原语是命名管道。在 Linux 和 OS X 上,我们使用socketpair(). 为每个渲染器进程分配一个命名管道,用于与浏览器进程通信。管道以异步模式使用,以确保任何一端都不会被阻塞等待另一端。
重要通知
在浏览器中与渲染器的通信是在单独的 I/O 线程中完成。
Blink 渲染引擎
Blink 是 Chromium 使用的开源布局渲染引擎,主要用于解释和布局 HTML。其中,Blink包含一个主线程,多个Worker线程,还有一些其他的线程。
Blink 渲染工作
Blink实现了在浏览器页签中所有的渲染工作。

Blink渲染合成
- 实现了Web平台中的标准,例如HTML标准,包括DOM、CSS等。
- 内置了V8引擎用于运行JavaScript。
- 从网络堆栈中获取资源。
- 构建DOM树。
- 计算样式和布局。
- 内置了Chrome Compositor和绘制图形的能力。
渲染管线
渲染管线(Rendering pipeline)定义了从HTML字符到在屏幕上显示像素的过程。

JavaScript加载与执行过程
一个JavaScript脚本运行要经历加载、分析、解释执行、优化和反优化几个过程,其中Ignition负责将抽象语法树转化成字节码以节省存储空间,TurboFan则根据对象类型信息将部分函数的字节码编译成机器码加速执行。编译后的函数运行过程中发现对象类型变化了则回退到字节码解释阶段执行。

V8 的工作原理
当 V8 编译 JavaScript 代码时,解析器(parser)将生成一个抽象语法树。语法树是 JavaScript 代码的句法结构的树形表示形式。解释器 Ignition 根据语法树生成字节码。TurboFan 是 V8 的优化编译器,TurboFan 将字节码生成优化的机器代码。

编译管道
![]() | ![]() |
![]() | ![]() |
![]() | ![]() |
![]() | |
![]() | |
![]() |
Ignition解释器
Ignition 是一个字节码解释器,是一个带有累加器寄存器的寄存器,它的工作是以尽可能少的延迟开始执行 JavaScript,真正实现减少 V8 的内存开销。
核心优势
使用 Ignition,V8 将 JavaScript 函数编译为简洁的字节码,其大小是等效基线机器代码的 50% 到 25% 之间。然后,该字节码由高性能解释器执行,该解释器在真实网站上产生的执行速度接近于 V8 现有基线编译器生成的代码的执行速度。

启用了 Ignition 的 V8 编译管道
字节码
- 字节码是机器代码的抽象。
- 每个字节码指定其输入和输出作为寄存器操作数。
- 每个字节码都会消耗输入并将输出推送到隐式堆栈上。
- 特殊的累加器寄存器是许多字节码的隐式输入和输出寄存器。
重要通知
由于许多 JavaScript 表达式涉及从左到右求值的操作链,因此这些操作的临时结果通常可以在整个表达式求值过程中保留在累加器中,从而最大限度地减少加载和存储到显式寄存器的操作的需要。
字节码减少的实现原理
随着字节码的生成,它会经过一系列内联优化阶段。这些阶段对字节码流进行简单分析,用更快的序列替换常见模式,删除一些冗余操作,并尽量减少不必要的寄存器加载和传输次数。因此,进一步减小了字节码的大小并提高了性能。
Sparkplug非优化JS编译器
Sparkplug是一个新的非优化 JavaScript 编译器,它位于 Ignition 解释器和 TurboFan 优化编译器之间,旨在快速编译,非常快,以至于我们几乎可以随时编译,这使我们能够比 TurboFan 代码更积极地对 Sparkplug 代码进行分层。
重要通知
Sparkplug可以取代 V8 的基线编译器,以更少的内存开销执行代码,并为更简单的脚本执行管道铺平了道路。

Sparkplug核心优化技巧
- Sparkplug编译的函数已经被编译为字节码,字节码编译器已经完成了大部分艰苦的工作,比如变量解析、判断括号是否真的是箭头函数、去糖化解构语句等等。
- Sparkplug 在字节码上的单次线性传递中直接编译为机器码,发出与该字节码执行相匹配的代码。
V8 JavaScript 堆栈框架
- 在 V8 中,我们有 JavaScript 帧的约定,即参数(包括接收者)在调用函数之前以相反的顺序压入堆栈,堆栈上的前几个槽是:当前正在调用的函数;调用它的上下文;以及传递的参数数量。这是我们的“标准” JS 框架布局
- 这个 JS 调用约定在优化帧和解释帧之间共享,它允许我们在调试器的性能面板中分析代码时以最小的开销遍历堆栈。

V8 JavaScript 堆栈框架
V8 解释器栈帧
Ignition 是一个基于寄存器的解释器,这意味着有一些虚拟寄存器(不要与机器寄存器混淆!)存储解释器的当前状态——这包括 JavaScript 函数局部变量(var/let/const 声明)和临时价值观。这些寄存器存储在解释器的堆栈帧中,还有一个指向正在执行的字节码数组的指针,以及当前字节码在该数组中的偏移量。

V8 解释器栈帧
V8 Sparkplug 堆栈框架
V8存储了从 Sparkplug 代码地址范围到相应字节码偏移量的双向映射;一个相对简单的编码映射,因为 Sparkplug 代码是直接从字节码的线性遍历中发出的。每当堆栈帧访问想知道 Sparkplug 帧的“字节码偏移量”时,我们都会在此映射中查找当前正在执行的指令并返回相应的字节码偏移量。同样,每当我们想从解释器到 Sparkplug 进行 OSR 时,我们都可以在映射中查找当前字节码偏移量,并跳转到相应的 Sparkplug 指令。

V8 Sparkplug 堆栈框架
重要通知
Sparkplug 是一个从 Ignition 字节码到 CPU 字节码的“转换器”,将你的函数从在“模拟器”中运行转移到“本机”运行。
Turbofan优化编译器
TurboFan是基于 JavaScript 执行期间收集的信息生成高性能机器代码的优化编译器,其将尖端的中间表示与多层翻译和优化管道相结合,以生成比以前使用 CrankShaft JIT 可能产生的更高质量的机器代码,实现了流体代码运动、控制流优化和精确的数值范围分析。
Turbofan工作原理
Turbofan工作原理,即将JavaScript 代码转换为高度优化机器代码的过程实现机制。

TurboFan的核心任务
- 拓宽快速通道。
拓宽快速路径对于确保 JavaScript 引擎用于优化代码的资源真正获得回报至关重要。
- 改善慢路径。
注意事项
TurboFan 编译比 Crankshaft 更昂贵。
减少代码内存开销
- 重用 TurboFan 管道的实际代码生成部分来构建Ignition 解释器。
- 改善页面加载时间并有助于减轻解析开销,因为 TurboFan 优化编译器在开始优化时不再需要重新解析函数源,而是可以直接从解释器的字节码进行优化。
TurboFan整体架构
TurboFan JIT 通过许多高级技术实现了更积极的优化。JavaScript 以最不优化的形式进入编译器管道,并经过翻译和优化以逐步降低形式,直到生成机器代码为止。设计的核心是代码的更加宽松的 sea-of-nodes 内部表示(IR),从而可以更有效地重新排序和优化。

TurboFan 代码生成架构
新架构打开了一个全新的 JavaScript 可能优化世界。推动优化内置函数,并最终能够将它们内联到 TurboFan 优化代码中。
TurboFan 代码生成架构示例
GPU 加速合成实现原理
GPU硬件合成的优势
- 在GPU上合成页面层可以实现更好的效率在绘图和涉及大量像素的合成操作,硬件是专为这些类型的工作负载设计。
- 对于GPU上已有的内容,不需要昂贵的回读(如加速视频、Canvas2D或WebGL)。
- CPU和GPU之间的并行性,可同时运行创建高效的图形管道。
GPU 架构路线图
- 在渲染器中强制合成模式
- 浏览器合成器
- 浏览器和渲染器中的线程合成
- 在渲染器和浏览器中执行侧绘制
- 混合加速光栅化,尽可能使层光栅化
V8内部分析器
Chrome DevTools 的 CPU Profiler 可帮助你分析代码的瓶颈,但是我们需要更深入、更细致地对代码进行详细的相关性能指数分析,而V8内部分析器提供了强大代码性能分析功能。
源代码构建 V8 的三个步骤
- 生成构建文件
- 编译
- 运行测试
构建 V8 的两个工作流程
- 使用名为的辅助脚本的便利工作流程gm很好地结合了所有三个步骤
- 原始工作流程,您可以在其中手动为每个步骤在较低级别运行单独的命令








