隨著近代軟體需求,目前多數個人電腦均使用 64 位元作業系統,由 AMD 於 1999 年開發擴充 x86 指令級架構而來,稱之為 AMD64,市場上則有 x86-64、x64 等說法,Intel 則是在 Prescott E0 版處理器正式開放使用(絕大部分相容),歷經 IA-32e、EM64T 等名稱,近期則定調為 Intel 64 技術。x86-64 火熱的程度以及向後相容 x86 的特色,甚至將 Intel 與 HP 主導的 IA64 指令集踢出伺服器市場,去年推出的 Itanium 9700 系列處理器即為最後一代。
近日 Intel 處理器的 64 位元運作模式卻爆出重大瑕疵,導致位處使用者模式的程式指令能夠跳過部分安全機制,取得位於核心模式記憶體區域的資料,從而獲得更高的控制權限。也就是說,你可能在瀏覽網頁之餘,不知不覺就把帳號密碼洩漏出去,更糟的是有可能會造成資金實質損失。而這部分無法透過更新微碼修補,需要作業系統以軟體方式避開,Linux 核心已有初步的補丁推出,目前大部分 Windows 採用的 NT 核心已於去年 11 月和 12 月推送修正後的 build 給 fast-ring Windows Insider Program 參與使用者,而同樣運作在 Intel 處理器的 macOS 也已經在 10.13.2 版本修正。
該漏洞利用現代處理器預測機制與作業系統的記憶體位址轉譯機制加速手法,進行惡意存取,但在了解這個漏洞之前,需要先行解說目前電腦作業的「使用者模式」以及「核心模式」。一般而言,當使用者執行 1 個程式的時候,作業系統會指派虛擬記憶體定址空間,這個程式就只能在這個記憶體範圍執行,避免程式當機影響其它的程式運作,或是導致整台電腦不正常。(1 個程式可能有數個行程,每個行程都有自己的虛擬記憶體定址空間,這裡筆者簡化為 1 對 1 關係。)
而處理器此時運作在使用者模式,將虛擬記憶體定址對照分頁表轉譯成真實的記憶體位址,以便進行讀寫操作作業。題外話,使用者模式、虛擬記憶體位址、分頁表也是多工作業的基礎之一,作業系統可將目前沒有活動的程式程序所占用的實體記憶體釋放,將資料移入位於硬碟當中的分頁檔案。
當運作在使用者模式的程式需要存取硬碟,或是連結上網的時候,便會切換成核心模式,由作業系統代勞這些本該由作業系統負責的工作,執行完畢再切回使用者模式並轉交資料。由於效能方面的因素,程式的虛擬記憶體定址空間之內包含核心模式記憶體的映射,以便加快這 2 種模式的切換速度,而近代處理器也會設計有 TLB(Translation Lookaside Buffer、轉譯後備緩衝區)等加速轉譯機制。
▲使用者模式與核心模式的互動關係。
目前處理器都會具備一些投機∕機會演算法,用來預測下一步執行動作,不必依序等待需求出現,就先行載入一些指令或是資料,以便盡量填滿執行管線增加效率。不過 Intel 64 處理器在這部份似乎出了些邏輯差錯,允許使用者模式直接存取核心模式記憶體資料,照理來說這個指令應該會被安全機制擋下並傳回 page fault 資訊。最新消息為 1 位 Vrije Universiteit Amsterdam 的博士生,已經證實能夠利用此漏洞在使用者模式之下讀取核心記憶體資訊。
▲brainsmoke 已於推特發表成功讀取核心記憶體資訊。
目前各大作業系統核心針對此問題,所採用的解決方式為 KPTI(Kernel Page Table Isolation),將核心模式與使用者模式的記憶體空間完全分開,但是把這 2 種模式的分頁表隔離將導致處理器需要切換不同的記憶體空間,TLB 等快取轉譯機制效能下降,預計頻繁進出核心模式∕使用者模式的程式最容易受到影響,使用 PostgreSQL SELECT 1在修補前後的 Linux 作業系統進行測試,最好的狀況將下降 17% 的效能,最糟達 23%,資訊來源 The Register 其它測試更可達 30%。
另一個 x86 市場處理器鉅頭 AMD,則因為架構設計差異的關係,不受此漏洞影響。與我們關係最大的 Microsoft 還沒有正式的公開說明,尚未表示修補程式是否會根據所採用的處理器不同,而決定啟用 KPTI 原理機制,但預計很快就會正式推出更新檔。
引言圖片採用創用 CC 姓名標示-相同方式分享 3.0 未在地化版本,作者為 Eric Gaba
資料來源
'Kernel memory leaking' Intel processor design flaw forces Linux, Windows redesign
參考資料
KAISER: hiding the kernel from user space