浏览器基础:进程与线程
跳到导航
跳到搜索
关于
学习 JavaScript 的“事件循环(Event Loop)”机制时,需要结合浏览器的进程、线程相关知识。 关于浏览器的更多知识,参考: # 《浏览器工作原理(各线程介绍)》 # 《深入理解浏览器中的进程与线程》 # 《深入浏览器之页面加载中的计算机网络》 # 《深入浏览器之浏览器中的进程与线程》 # 《浏览器进程/线程模型》
浏览器进程/线程模型[1]
浏览器进程架构有两种方案:单进程多线程和多进程(通过IPC传递消息)。
- 单进程多线程:顾名思义,浏览器在同一个进程运行所有功能模块(包括篇:网络、插件、JavaScript 运行环境、渲染引擎和页面等)
- 其缺点很明显:
- 不稳定:任一线程错误,将导致整个进程崩溃
- 不流畅:同一时刻只有一个浏览器模块可用
- 不安全:各线程共享进程数据,更容易导致攻击
- 高占用:进程关闭之前,不会回收由线程占用的资源
- (其实早在 2007 年之前,市面上浏览器都是单进程的)
“多进程”模型
现代浏览器多从用多进程模型,但各家实现细节各有差异。 (以 Chrome 为例)
浏览器主要进程,包括:
- 浏览器进程(Browser Process):控制应用程序的“chrome”部分,包括地址栏、书签、后退和前进按钮。还处理网络浏览器中不可见的特权部分,如网络请求和文件访问。
- 简单来说:主要负责界面显示、用户交互、子进程管理,同时提供存储等功能。
- 渲染进程(Renderer Process):控制显示网站的选项卡内的任何内容。
- 浏览器会为每个 Tab 标签创建一个渲染进程。
- 出于安全考虑,渲染进程都是运行在沙箱模式下。
- GPU进程(GPU Process):处理应用程序的 GPU 任务,并将它们绘制在同一个表面上。
- 插件进程(Plugin Process):控制网站使用的任何插件。
- 每个插件都有一个插件进程。
也有说法,当前 Chrome 架构(面向服务的架构)将“网络进程”、“utility进程”从“浏览器进程”中独立了出来[2] ,但此处不重要。
浏览器:内核、引擎[3]
浏览器相关的术语:浏览器内核、浏览器引擎、排版引擎、Js引擎、Blink、v8、webkit……,这都是啥?
浏览器内核(浏览器引擎):指“广义上的渲染引擎”(渲染引擎 + JS 引擎)
- 渲染引擎(排版引擎):负责解析(HTML、CSS、JavaScript 和 DOM),并渲染页面。
- 如:WebKit、Geck、Blink
- JS 引擎(JS 虚拟机):负责解释、执行 JavaScript 代码
- 如:SpiderMonkey、JavaScriptCore(WebKit 内置)、V8
浏览器 | 渲染引擎 | JS 引擎 |
---|---|---|
IE | Trident(MSHTML) | JScript/Chakra |
Edge | EdgeHTML | Chakra |
Chrome | Blink | V8 |
Firefox | Gecko | SpiderMonkey |
Safari | WebKit | JavaScriptCore |
Opera | Presto | Carakan |
“排版引擎”(Blink)和“Javascript引擎”(V8)都是运行在“渲染进程”(Renderer Process)中,通过“Event Loop”进协调[4]。
渲染进程
浏览器的“渲染进程(Renderer Process)”是多线程的,页面的渲染、JS 执行等都在这个进程内进行,其执行机制就是“Event Loop:事件循环”。
“渲染进程”中包括以下线程:
- GUI 渲染线程:负责渲染浏览器界面(解析 HTML、CSS;构建 DOM 树、RenderObject 树;布局、绘制)。
- 当界面需要重绘(Repaint)或由于某种操作引发回流(reflow)时,该线程就会执行。
- JS 引擎线程:负责解析处理 JavaScript 任务(包括:“执行栈”、“任务队列”),运行代码。
- 一个 Tab 页中只有一个“JS 引擎线程”。
- 事件触发线程:负责检测“事件触发”状态。
- 当事件发条件被触发时,该线程会:把对应事件添加到“事件队列”(宏任务)中,以等待“JS 引擎”执行;
- 定时触发器线程:负责检测“定时器”状态。
- 当计时完毕后,该线程会:把对应事件添加到“事件队列”(宏任务)中,以等待“JS 引擎”执行;
- setInterval 与 setTimeout 所在线程。
- 异步http请求线程:负责检测 HTTP 请求状态。
- 当请求状态变更时,该线程会:把对应事件添加到“事件队列”(宏任务)中,以等待“JS 引擎”执行;
- 在 XMLHttpRequest/Fetch 连接后,由浏览器创建的线程。
“GUI渲染线程”与“JS 引擎线程”互斥: JS 堵塞的原因所在,其目的是:防止渲染出现不可预期的结果(毕竟 JS 是可以操作 DOM 的)。
参考
- ↑ 参考:
- Chrome:《Inside look at modern web browser (part 1)》:描述了Chrome的多进程架构,及不同进程的区别
- Chrome:《Inside look at modern web browser (part 2)》:为展示网站页面,每个进程和线程如何进行通信
- Chrome:《Inside look at modern web browser (part 3)》:渲染进程(Renderer Process)的内部工作
- Chrome:《Inside look at modern web browser (part 4)》:用户输入时合成器(Compositor)是如何实现平滑交互的
- ↑ 参考:
- ↑ 参考:
- ↑ 参考:《Event Loop 和 JS 引擎、渲染引擎的关系》