安全通告
首頁 > 技術支持 > 安全通告

CVE-2021-1648 windows10 splwow64權限提升分析

發布時間:2021-01-21查看次數:58
分享到

0x00  前言

近日,作者分析了微軟1月補丁日修復的一個漏洞CVE-2021-1648,這是一個可以在splwow64進程空間進行任意地址讀寫的漏洞。由于splwow64是一個普通權限的進程且splwow64在IE瀏覽器的白名單目錄里,因此這個漏洞可以用于提權低權限的IE瀏覽器渲染引擎進程從而繞過IE瀏覽器的沙箱。這篇文章主要介紹一下splwow64的機制和CVE-2021-1648的成因。

環境:Windows10 20H2 2020-12補丁

0x01 splwow64機制

wow64是微軟為了在64bit系統兼容運行32bit程序的一個組件,具體來說,在64bit程序調用32bit的CreateDC Windows會用splwow64.exe處理這個調用,64bit程序與splwow64.exe使用lpc進行通信。

splwow64在splwow64!GDIThunkingVIALPCThread里調用NtCreatePort開啟處理信息的端口,在這里我們可以計算得到調用NtSecureConnectPort與splwow64通信的端口名稱

我們可以從xp sp1代碼\NT\base\ntos\lpc\lpcconn.c中NtSecureConnectPort的注釋中得到一些lpc通信機制的信息,這里摘抄部分注釋如下

1、NtSecureConnectPort通過PortName參數連接server端口,PortName必須與NtCreatePort指定的一致

2、server端通過NtListenPort接收請求,client端在server端接收處理請求、返回NtCompleteConnectPort執行結果前阻塞

3、server在接受請求后返回給client端一個參數PortHandle,PortHandle與名稱無關與client進程有關。client使用PortHandle調用NtRequestWaitReplyPort從server端接收/發送信息

splwow64在splwow64!TLPCMgr::ProcessRequest處理接收的消息,這里過濾了傳入消息的長度,只處理DataSize=0x20長度的消息,

并將某些類型合法消息的[0x30],[0x40],[0x38]作為參數傳遞給Gdi32full!GdiPrinterThunk,這里傳遞的參數都是調用者可控的。

0x02  漏洞分析

CVE-2021-1648出現在0x6d消息的處理過程中,CVE-2021-1648是在CVE-2020-0986補丁的基礎上出現的,CVE-2020-0986的補丁在gdi32full!GdiPrinterThunk里主要加了兩個緩解FindDriverForCookie、FindPrinterHandle和UMPDPointerFromOffset、UMPDStringPointerFromOffset,由于Gdi32full!GdiPrinterThunk傳入的參數可控,這兩個緩解實際上都是可以繞過的。

2.1、FindDriverForCookie、FindPrinterHandle繞過

Gdi32full!FindDriverForCookie的功能是根據傳入的值a1,從一個全局變量gdi32full+EABA0里遍歷得到偏移[7]的位置為a1的地址并返回。

Gdi32full!FindPrinterHandle的功能是根據傳入的參數a1(地址值)、a2、a3,從a1偏移0x40的位置遍歷,返回該地址偏移2*4=a2且3*4=a3的偏移值。

這兩處緩解可以通過0x6a消息調用一次gdi32full!bAddPrinterHandle來繞過,gdi32full!bAddPrinterHandle調用時參數如下,其中第二、三個參數是調用者可控的。

gdi32full!bAddPrinterHandle的功能是把傳入的a2、a3寫入到global_heap偏移2*4、3*4的位置。需要注意的是這里*(QWORD*)(global_heap+0x40)的位置實際上和上文Gdi32full!FindPrinterHandle中*(a1+0x40)相同,

再看一下0x6d消息是如何調用FindPrinterHandle的,這里的參數二、三是我們可控的,這樣在gdi32full!bAddPrinterHandle調用中*(QWORD*)(global_heap+0x40)寫入的內容和gdi32full!FindPrinterHandle中要尋找的內容位置相同且都可控,我們就可以繞過gdi32full!FindPrinterHandle這個檢查。

2.2、UMPDPointerFromOffset、UMPDStringPointerFromOffset繞過

CVE-2020-0986補丁加的另一個緩解是檢查指針是否在32bit的范圍,

這個緩解可以繞過的原因是splwow64.exe與32bit兼容,所以splwow64中堆棧地址都是32bit范圍內的,由于lpc通信過程中server端會開辟內存并拷貝client端傳入的消息,我們構造0x6d畸形請求,

LpcRequest.PtrMsgSend = (UINT64)ClientView.ViewRemoteBase;

即發送消息的地址設置為lpc server端的堆地址即可繞過這一緩解。

splwow64中執行server端開辟內存拷貝的過程在splwow64!TLPCMgr::ProcessRequest

2.3、任意地址讀寫

繞過了上述兩個緩解,splwow64會調用一個src可控、dst可控的memcpy,由于這里memcpy的src和dst沒有檢查范圍,我們可以通過修改src讀dst的內容進行任意地址讀,修改dst為目標地址、修改src為目標內容進行任意地址寫。

0x03  總結

這里介紹了splwow64的一些機制并分析了CVE-2021-1648的成因,重點分析了微軟針對CVE-2020-0986補丁所加的兩個緩解機制的繞過,希望讀者讀完能有所收獲。

0x04  參考鏈接

https://bugs.chromium.org/p/project-zero/issues/detail?id=2096

https://whereisk0shl.top/post/the_story_of_cve_2021_1648

熱門標簽:

防火墻

SD-WAN

超融合

VPN

網閘

入侵防御

入侵檢測

數據安全

堡壘機

漏洞掃描

江西多乐彩今天开奖了 ds视讯网址 贵州快三怎么玩稳赚 七星彩走势图近30期 _澳门百家乐赌场 湖南快乐十分选三前直 1998彩票官方网站-点击登陆 MG招财鞭炮游戏网站 快乐12出号规律 全天幸运飞艇一码计划 安徽快三27日走势图 平码最多几期不出的 江西时时彩人工计划 新疆25选7预测 今天排三p3试机号 北京11选5昨天 _澳门百家乐赌场_Welcome