Javascript 的运行及浏览器多线程

原创 2006年12月28日 10:36:00
Javascript 的运行及浏览器多线程

2006.12     lu_yi_ming(_at_)sina.com



_ 本文目的

  网页HTML结构以及 Javascript 程序越来越复杂了,有必要整理一下思路。

  本文只是想整理一下思路,很多细节不一定准确。


_ 问题详述

  现在一个网页中包含了多个 Iframe(Frame),每个 Iframe 都有 window (本文中 window 特指 DOM 中的 window,MS Windows 中的窗口与 X Window 中的窗口用 WINDOW 来表示),每个 window 都可以有 setInterval,以及 setTimeout,另外 window.document 里面还有很多的 element,每个 element 都可以有 event,而且这些 event 可以一直 bubble 到 body。

  问题 1. 在一个 window 内部,event 与 window.setInterval / window.setTimeout 是否并行?
  问题 2. window 之间的 Javascript 是否并行?
  问题 3. 属于同一个进程的 WINDOW 之间的 Javascript 是否并行?
  问题 4. 如果有并行存在,是一种怎么样的并行? 是浏览器为每一个 window 或 WINDOW 模拟了多线程,还是利用操作系统本身的多线程?
  问题 5. 如果有并行存在,如何解决 Javascript 运行中的互斥、信号?


_ 初步认识

  经过一些简单研究(因为懒,没去读 Firefox 源代码),有以下初步认识。

  对于 IE,用 SPY++ 分析,发现增加页面中的 Iframe 并不能导致线程的增加,也不能导致子 WINDOW 的增加。所以,IE 中的 Iframe 及 window 是 Shell.Explorer (shdocvw.dll 中的 COM 组件) 内部实现的,可能在一个单独的线程中,很可能就在 WINDOW 所属的线程中。进一步,WINDOW 中所有 Iframe 的 window 的内部的 Javascript 都是不并行的。再进一步,结合网络传输,如果一个 Iframe.src 赋值后,Javascript 所在的线程应该会通知另一个线程(本文中简称通讯线程)去向服务器发 HTTP 请求。通讯线程从服务器端接收了一个完整的 HTTP 包后,将把这个数据包交给负责显示的线程(中间环节可能有一个线程负责解析 html),显示线程(或解析线程)边显示边运行页面中的 Javascript,例如 document.write()。并不停的绘制屏幕。而在这个 HTTP 数据包处理过程中,并不会处理其他 Iframe 的 window 的 setInterval 之类的事件。处理完一件事情后,才会在内部的 timer / timeout 队列中选择一个到期的开始运行(调用)。

  所以,如果有一个 Iframe 的 window 的 Javascript 陷入死循环,则此线程内的所有的 Iframe 都将停止响应,并且从服务器端接收来的新数据也将被搁置。

  IE 中的多线程。在 IE 上按 Ctrl-N,或者运行 window.open() ,将会打开一个新的 WINDOW,从 SPY++ 中看,会相应的增加一个新线程,管理这个新的 WINDOW。但是没有增加更多的新线程,说明一个进程内所有的 WINDOW 都共用了通讯线程。也就是通讯进程管理了所有的 TCP Connection。 用 window.open() 返回的对象指针可以访问这个新 WINDWO,并且可以访问其下的 Iframe 的 window 中的各种数据,甚至也可以调用其中的函数,只是需要注意堆栈的不同。经过测试,如果两个线程的 Javascript 同时访问同一个数据,比如同时有 window.setInterval 指定的函数去访问一个 window 中的一个 element 的变量,或者修改属性,则其中的一个函数会返回 Javascript Exception:拒绝访问,说明浏览器在内部实现中注意了互斥。

  基于以上认识,对于 IE ,在一个 WINDOW 的所有 Iframe 的 window 内部应该不存在多线程,也不存在 Javascript 并行。当然也不会有 sleep 之类的函数了。把一个 Javascript 函数阻塞了(如特定的 ActiveX )可能导致整个 WINDOW 暂停相应。

  关于 IE 还有一个发现,window.setInterval 不是用 WM_TIMER 实现的。

  关于 Firefox,在 Windows 上,用 SPY++ 分析,页面中的每一个 Iframe 都是用一个 WINDOW 实现的。但是所有的 WINDOW,包括其他 Tab 打开的 WINDOW,都属于一个线程。但是跨 Tab ,跨浏览器窗口访问同时访问一个数据,也会引发 Javascript Exception:拒绝访问,说明 Firefox 的 Javascript 很可能是在一个 Tab 范围内,是不并行的。有可能是 Firefox 给每个 Tab 单独开了一个线程来运行 Javascript。反正最终行为要与 IE 保持差不多,估计也就这样了。

  在 Linux(FC6)上启动 Firefox,用 gdb attach 进去,发现在新打开网页时会增加不少线程,但网页显示稳定后过一段时间,线程数会减少。这也可能是因为运行 Javascript 的线程任务做完了。


_ 初步结论

  1. 在 IE 的一个 WINDOW 内,Firefox 的一个 Tab 内, Javascript 是单线程运行的。
  2. 如果要在页面上的各 Iframe 之间实现 Javascript 同步,则应该采用 window.setInterval 来实现,而不是把一个 Javascript 挂起。
  3. 在 IE 上跨 WINDOW,或在 Firefox 上跨 Tab 访问数据,则要注意用 try catch 解决线程互斥导致的 Exception。

Python-多线程

-
  • 1970年01月01日 08:00

浏览器多线程和js单线程

0.前言开发过程中遇到js线程和ui渲染线程互斥问题。导致ui无法正常更新等问题。这些问题的根源就是因为浏览器的多线程和js的单线程引起的。看本篇博客之前,应该充分理解消息队列,事件循环,同步异步任务...
  • github_34514750
  • github_34514750
  • 2017-08-02 15:13:11
  • 1463

浏览器UI线程 和 js线程

浏览器中的线程介绍       通常一个浏览器会至少存在三个线程:JS引擎线程(用于处理JS)、GUI渲染线程(用于页面渲染)、浏览器时间触发线程(用于控制交互)。      而因为JS可以操作...
  • u011643473
  • u011643473
  • 2015-01-27 10:55:17
  • 3755

Javascript 的运行及浏览器多线程

Javascript 的运行及浏览器多线程2006.12     lu_yi_ming(_at_)sina.com_ 本文目的  网页HTML结构以及 Javascript 程序越来越复杂了,有必要整...
  • putongren
  • putongren
  • 2006-12-28 10:36:00
  • 1803

关于IE的"多线程"...

最近在CSDN社区的AJAX版有些人问道关于AJAX的多线程的问题...在这里我想说下我的看法...IE的线程模式其实是STA(Single-Threaded Apartment)模式... 也就是说...
  • chaircat
  • chaircat
  • 2006-10-03 14:40:00
  • 829

Javascript是单线程的深入分析

面试的时候发现99%的童鞋不理解为什么JavaScript是单线程的却能让AJAX异步发送和回调请求,还有setTimeout也看起来像是多线程的?还有non-blocking IO, event l...
  • talking12391239
  • talking12391239
  • 2014-03-13 14:02:19
  • 22581

WebBrowser多线程带来的麻烦

我们在做采集软件的时候 有些网站通过直接分析html文本是很麻烦的事情 在利用WinForm编程的情况下 有一种更好的方式当然是分析HtmlDocument 然而,这HtmlD...
  • gold0523
  • gold0523
  • 2014-06-02 17:41:52
  • 6095

利用IE对多帧GIF的onload事件重复执行的原理实现(JavaScript多线程的实现)

注:以下内容基于IE中GIF的onload事件的基础上,故所有测试IE only需要用到的几个图片:先看一个简单的事实: var img=new Image(); img.src="attachme...
  • canduecho
  • canduecho
  • 2008-05-04 16:13:00
  • 846

JavaScript多线程之一~~HTML5中的Web Worker

Web Worker的出现对于JavaScript具有非常重大的意义,个人觉得Web Worker的出现就如同当年AJAX对于JavaScript前端开发的意义一样重大,这是完全不同的开发体验。因为多...
  • zwjabcd
  • zwjabcd
  • 2015-12-17 11:19:39
  • 3566

从浏览器多进程到JS单线程,JS运行机制最全面的梳理

从浏览器多进程到JS单线程,JS运行机制最全面的一次梳理 前言 见解有限,如有描述不当之处,请帮忙及时指出,如有错误,会及时修正。 ----------超长文+多图预警,需要...
  • jason_renyu
  • jason_renyu
  • 2018-01-30 13:13:15
  • 38
收藏助手
不良信息举报
您举报文章:Javascript 的运行及浏览器多线程
举报原因:
原因补充:

(最多只允许输入30个字)