<span id="7ztzv"></span>
<sub id="7ztzv"></sub>

<span id="7ztzv"></span><form id="7ztzv"></form>

<span id="7ztzv"></span>

        <address id="7ztzv"></address>

            原文地址:http://drops.wooyun.org/papers/5390

            前言


            系列將簡單介紹一下IE的相關內容,篇幅和自己的認知有限,其中必然有不足之處,如果有寫得不對的地方歡迎大家指出。

            文章布局:每篇文章最多含有3個部分,這3個部分介紹的是相關內容,但并不一定是同一系列的東西,望見諒。

            第一部分通常是背景介紹

            第二部分是總結性的描述

            第三部分則是詳細介紹或者實踐。

            I.1 Internet Explorer的歷史變遷


            在記憶中,從1999年開始接觸網絡,從那時跟隨著Windows 95一起而來的Internet Explorer 4算起,微軟已經發布了8個不同版本的IE了(如果Spartan姑且算做是Internet Explorer 12的話)。這之中Internet Explorer(以下簡稱IE)都做了哪些變更呢?里程碑可以數一數:

            ·IE1、IE2(1995年):家族中最簡單的“瀏覽器”,只支持靜態的頁面,現在你能用得到的許多功能,它都不支持。現在你用到的許多功能他卻有了雛形。

            enter image description here

            ·IE3 (1996年):對早期版本的改進,支持了ActiveX控件,支持了JavaScript和VBScript(當時稱為Microsoft JScript和Microsoft VBScript,不為啥,就因為商標問題)。而且從這時開始就支持WebBrowser這個被人熟知的ActiveX控件了,這保證了瀏覽器的可重用性。

            enter image description here

            ·IE4(1997年):引入了DHTML功能,支持數據綁定,同時增強了WebBrowser的功能,添加了一些新特性,增加了側邊欄,以及BHO。

            enter image description here

            ·IE5(1999年):隨著Windows 98一起發售,支持持久會話,緊接著誕生了XMLHttpRequest,促使了AJAX的發展(盡管此時AJAX一詞都還沒誕生……),引入了HTA,還有自動填表等功能。IE 5.5版本起還支持了128位的加密。

            enter image description here

            ·IE6(2001年):緊接著Windows XP一起發售,可能是給大家留下印象最深刻的瀏覽器,在2002-2003年中,IE6的市場份額達到了90%,IE全家族的市場份額達到了95%。 同時,這也是最飽受詬病的瀏覽器,因為它的安全問題實在是很嚴重。這一版本中增加的大多是網頁渲染相關的,例如CSS1 、DOM1等的部分支持。

            enter image description here

            ·IE7(2006年)、IE8(2009年):IE6市場份額被火狐搶走之后微軟推出的新版本瀏覽器,這兩個版本大部分都是性能調整和渲染修整以及增強。

            enter image description here

            ·IE9(2011年),穩定版本,性能提升和HTML5支持,多進程支持,這使得網頁假死或者崩潰時不會影響到其他頁面。

            不放截圖了,IE9之后這些版本大家很容易就能搜到。

            ·IE10(2011年)/IE11(2013年),性能較大的增強了,以及渲染以及兼容增強,增加DNT支持,IE10開始性能真的已經和之前有較大的不同了,但是頂著IE的名號,還是承受著IE6帶來的深刻影響。

            ·Spartan(2015年),代號IE12。整合了語音助手,性能提升等,估計微軟此舉也是要丟掉IE的牌子另起爐灶,從程序上看,至少它確實和IE用的不是同一套DLL庫了。

            I.2 IE的構成


            在早期的單進程IE中,IE的結構大致如:

            enter image description here

            enter image description here

            圖:以 IE6 為代表的單進程無 tab 模式

            隨著多進程的引入,IE 的網頁部分結構還是類似這樣,但是界面宿主已經有變化了,看起來像是:

            enter image description here

            請注意上圖中外殼網頁分屬于不同進程。

            在IE7中,一個進程中可以運行一組網頁窗口了,但是新窗口不代表在新進程里面運行。(比如你用Ctrl+N新建窗口,其實它還是在當前進程里面創建的),可以自己安裝一個IE7來試驗,如果沒用過的話看我這個描述應該會很奇怪。開啟了保護模式的進程會運行在低完整性級別下,通過一個代理進程來進行通信。

            簡化的進程模型如下:

            enter image description here

            enter image description here

            enter image description here

            圖:IE7 的進程模式

            在 IE8 中,微軟引入了 IE8 松散耦合進程框架(LCIE),它使用 Jobs 來限制進程權限(吐槽 一下,自己試著用Jobs控制權限,實際應用在IE中的話深知不易,微軟也是下了不少功夫), 這個時候,開啟了保護模式與未開啟保護模式的 IE8 的結構類似于:

            enter image description here

            enter image description here

            可以看到的是這個版本中 IE 的 UI Frame 和一些管理功能所在的進程運行在中完整性級 別上,而保護模式下,Tab 和網頁進程運行在低完整性級別中(禁用保護模式的域下依然是 中完整性級別)。

            如上,HTML 和 ActiveX 控件都在網頁進程里面,還有一個比較特殊的是工具欄,它也 在網頁進程里面。

            采用這種模式的好處都有啥?首先是每個 TAB 都獨立出去了,其中一個崩了也不會影 響其他的;至于把 UI Frame 移動到了代理進程那邊,理由是加快啟動速度。

            而且由于采用了網頁分進程的模式,所以不同完整性級別的網頁、tab 都可以歸屬于同 一個 UI Frame,管理起來也比較方便。 如果你使用過 morden ie,metro ie,你會發現也許它的網頁進程都是 64 位的,這是因為 這個版本中啥插件都不加載。即使現在許多插件都有 64 位版本了,比如 Adobe Flash Player, 但是如果一味的追求 64 位化還是會導致各種插件不兼容。 所以在 IE10、IE11 的 64 位版本中,瀏覽器的 UI Frame 以 64 位運行,而網頁進程為了保 證插件的兼容性,所以依然默認采用了 32 位進程。即使你打開的是 64 位的 ie,最后網頁進 程還是 32 位的。

            所以,也許你會看到有 64 位的 IE 和 32 位 IE 同時存在你電腦里面的樣子:

            enter image description here

            以及,啟動 IE 后出現一個 64 位進程和 n 個 32 位進程的樣子:

            enter image description here

            圖: IE11 64bit Frame 進程和 32bit Content 進程

            相對于 IE7 的模式,可以看出來 IE11 中,即使你手動執行兩次 iexplore http://www.wooyun.org , 出來的也僅僅只有一個 64 位的 UI 進程。

            enter image description here

            圖:IE11 的進程模式

            當然,如果你開啟了增強保護模式,那網頁進程也會變成 64 位的。

            enter image description here

            圖:IE11 啟用增強保護模式

            在 Windows 7 下開啟這個模式,唯一一個用處就是把進程變成了 64 位,但是 Windows 8 下則會引入 AppContainer 這個進程隔離模式,具體的可以參考參考資料(1)。

            限于篇幅,與之相關的內容之后再敘述。

            I.3 重要概念:什么是 Markup Service?


            回到 IE 的核心功能上來,作為網頁的渲染器,超文本標記語言 HTM(Markup)L 想必 是離不開 Markup,那這個 Markup 到底是什么呢?歷史上來說,Markup 其實是給演員看的, 簡單的說就是劇本,通常還會給它畫一道藍色的標記,標明這個東西應該誰怎么演才合適, 在瀏覽器中,Markup通常可以看作是一個個的標簽。關于Markup Service的內容,建議大 家最開始只了解個大概即可。

            enter image description here

            圖:Markup Script,當然,這個是演員用的,圖像來自Google Image

            enter image description here

            圖:IE 可以識別的 Hyper Text Markup Langauge

            例如,一個 HTML 文件可能有如下內容:

            #!html
            <DIV>blast<DIV>off
            

            當瀏覽器解析這個文本時,瀏覽器會對內容做一次標準化(我比較習慣這么稱呼),之 后,DOM 內容看起來像是:

            #!html
            ?<HTML><HEAD><TITLE></TITLE></HEAD><BODY><DIV>blast<DIV>off</DIV></D IV></BODY></HTML>
            

            這個過程你可以自己去網頁 DOM 看:

            enter image description here

            圖:IE11 的文檔標準化

            由于有元素的插入,因此這一項功能可能會引入額外的安全風險,例如我之前發的:

            http://wooyun.org/bugs/wooyun-2010-033834
            

            或者可以說,解析器經過這一輪后,將 HTML 文本轉為了元素。而且為了內容的完整, 有一些原來沒有的元素也加進去了,例如 html、head、title、body 會自動的被解析器構造出 來。

            同時,解析器遇到第二個 div(分塊)的時候,會自動的把第一個 div 給封閉起來(怎 么封閉要取決于瀏覽器的實現)。還有之前加入的必要(但是你沒寫)的標簽,比如 <html><body>,都會自動的被 IE 添上并封閉。

            第二個需要注意的概念是 tree 和 stream(樹、流)的區別,比如:

            #!html
            This <B>is</B> a test
            

            這組“this is a test”和一對 b 標簽的例子,將會被轉化為如下的樹。text 被當為樹葉,element 被作為內節點。

                    ROOT
                      |
              +-------+--------+
              |       |        |
            "this"    B    "a test"
                      |
                     "is"
            

            把文檔轉為tree之后,所有的操作都會變為類似對樹的操作,例如增刪子節點。提供此類操作的API被稱為Tree Service。

            當然,自IE4.0之后,元素的模型操作比簡單的樹更強悍,比如這個例子:

            #!html
            An <B>exmaple <I> of </B> elements </I> cross
            

            B、I的范圍互相交叉,在HTML里面這個很常見,用樹來描述則十分困難。因此,Markup Services對這個內容不再提供類似樹的操作,而是為方便控制內容暴露了一個基于流操作的模型。

            enter image description here

            圖:相互交叉的范圍

            因此,Markup Service 它的作用實際上是用來避免產生這種讓人覺得迷惑的模型層間的。

            當無法用 Tree Service 時,瀏覽器就轉而使用 Markup Service 來控制基于流操作的模型。

            在基于樹的模型中,網頁內容被當作樹的節點來處理,每個元素,或者一塊 Text 都是 一個節點。節點通過這種類似對樹的操作方式來操作,例如從父節點中增刪一個子節點。

            在基于流的模型的內容操作方式中(比如通過 Markup Service 來操作),文檔的內容會 通過使用類似迭代器的對象來操作。 這個就像是在處理上面那個元素交叉的例子一樣,這 些帶有部分重疊的元素通過兩個 Markup Pointer 來區分,每個 Markup Pointer 指定著 Tag 從 哪兒開始,Tag 到哪兒結束。所以,基于流的模型是基于樹的模型的一個超集。

            說了這么多,要引入我們的 Markup Pointer 了。在這之前,舉一個類似的例子,C++中, 比如如果要操作一個 vector,使用迭代器是非常方便的做法:

            enter image description here

            圖:使用迭代器向 vector 插入一個元素

            也如你所見,Markup Pointer也有些許神似迭代器。可以通過創建和操作無效文檔的過程來理解一下。

            注意之前“This is a test”的例子,瀏覽器可能都不會被認為這是一個有效的 HTML 文檔。

            最小的有效HTML文檔至少要有html、head、title和body四個元素,當你提供的內容中沒有這些元素時,解析器會自動建立,然后把它們放到合適的位置上。

            在文檔解析過程中,使用Markup Service即可刪除或者重新排列DOM。例如,你可以整塊刪除html、body元素。你可以把head移動到body里面(但是這么做的話,文檔會被當作是無效文檔)。

            在IE中,提供這個服務的類有很多,最普遍的類即CMarkup,負責“指向元素、區域”的Markup 指針類名字是CMarkupPointer,它們都派生自CBase。

            如果有關注類似的內容的話,之前發的一個CMarkupPointer空指針引用的問題其實就與這相關(http://wooyun.org/bugs/wooyun-2010-079690 )。

            關于 CMarkupPointer,有一些需要注意,也是可能會導致 IE 崩潰或者出其他錯的問題,

            分別是:

            (1) Markup Pointer 剛創建,或者以一個無效對象為構造函數的參數創建的時候是未指 向狀態,也就是說啥都沒指,通常這個值是 0,這個很可能會導致空指針引用;

            (2)Markup Pointer 設置了指針粘滯(當當前指針所在區域發生移動之后,區域內的指 針是否也跟著計算新位置)的時候,如果同時也設置重力(重力分為左右重力, 簡單來說,就是在指針處插入一個內容,操作完之后,指針是應該貼著左邊的內 容還是右邊的內容),且在經過某些操作后發生了歧義,在對 Markup Pointer 指向的部分進行移動、刪除過程后,Markup Pointer 有可能會重新變成未指向狀態。這是因為指針指向的內容不存在或無效了,指針已經從文檔中移除(注意是 remove)了,但是指針自身還沒有被刪除(delete),以后如果重用這個指針又沒做 校驗的話,很可能就會出事兒。

            (3)Markup Pointer 左右移動的時候也有可能移動出錯。

            還有就是一個經驗條例,IE 中代碼很依賴比較上層的有效性檢查,所以一旦中底層代碼接收到了無效數據,IE 就很可能會出現異常。

            還是重提一下關于Markup Service的內容,如果之前沒接觸過的話,最開始只了解個大概即可,之后等了解了更多IE相關的內容時,這一塊的東西才容易和其他部分聯系起來,只是這個屬于基礎性的設施,所以才放在比較前面來介紹,老實說最開始我看這個東西感覺也是相當的頭疼……所以看著比較迷糊的話也不用太在意,有個印象就可以了。

            參考資料


            (1) 騰訊反病毒實驗室:深度解析 AppContainer 工作機制

            (2) Q&A: 64-Bit Internet Explorer

            (3) Windows 8 Metro/Modern Style IE 10

            (4) Enhanced Memory Protections in IE10

            <span id="7ztzv"></span>
            <sub id="7ztzv"></sub>

            <span id="7ztzv"></span><form id="7ztzv"></form>

            <span id="7ztzv"></span>

                  <address id="7ztzv"></address>

                      亚洲欧美在线