SMBv3 Ghost === <center> ![](https://i.imgur.com/dbFEdBq.png) </center> <font size='4'>**漏洞編號**</font> CVE-2020-0796 <font size='4'>**簡述**</font> 研究人員發現SMBv3存在安全漏洞(CVE-2020-0796),遠端攻擊者可對目標系統之SMBv3服務發送特製請求或架設惡意的SMBv3伺服器誘騙受害者進行連線,導致遠端執行任意程式碼。 A remote code execution vulnerability exists in the way that the Microsoft Server Message Block 3.1.1 (SMBv3) protocol handles certain requests. An attacker who successfully exploited the vulnerability could gain the ability to execute code on the target server or client. To exploit the vulnerability against a server, an unauthenticated attacker could send a specially crafted packet to a targeted SMBv3 server. To exploit the vulnerability against a client, an unauthenticated attacker would need to configure a malicious SMBv3 server and convince a user to connect to it. The security update addresses the vulnerability by correcting how the SMBv3 protocol handles these specially crafted requests. <font size='4'>**影響平台**</font> - Windows 10 Version 1903 (32與64位元) - Windows 10 Version 1909 (32與64位元) - Windows Server, version 1903 - Windows Server, version 1909 ###### tags: `Vul Research` ## 漏洞驗證 ### 環境架設 **使用環境** - Attack:Ubuntu 18.04 - Victim:Windows 10 ~~(1909)~~(1903) ![](https://i.imgur.com/UYyapc8.png) >因為漏洞指定作業系統為1903和1909,所以在架設環境時需要特別嚴謹,最原始的win10 1809版本是不會存在漏洞的 > [name=Ch0pper] **驗證環境** - [方法一] 使用[ollypwn](https://github.com/ollypwn/SMBGhost) 的漏洞掃描腳本--><font color='red'>**易誤報**</font> 判斷方式不嚴謹 ```python if res[68:70] != b"\x11\x03" or res[70:72] != b"\x02\x00": print(f"{ip} Not vulnerable.") else: print(f"{ip} Vulnerable") ``` 檢查SMBv3回應封包檔頭,單純判斷協定 ![](https://i.imgur.com/bwFsE4U.png) - [方法二] 使用[T13nn3s](https://github.com/T13nn3s/CVE-2020-0796)的powershell腳本檢查--><font color='red'>**不易誤報**</font> ```clike if ($WindowsVersion -eq 1903) { Write-Host "[*] CVE-2020-0976 is applicable to your Windows Version." } Elseif ($WindowsVersion -eq 1909) { Write-Host "[*] CVE-2020-0976 is applicable to your Windows Version." } Else { Write-Host "[+] CVE-2020-0976 is not applicable to your Windows Version." -ForegroundColor Green pause return } ...... function CheckIfUpdateIsInstalled { Write-Host "[*] Check if KB4551762 is installed..." $fix = Get-HotFix -Id KB4551762 -ErrorAction SilentlyContinue if ($fix) { Write-Host "[+] *** Windows Update $($fix.HotFixID) is installed on $($fix.InstalledOn). You're not vulnerable ***" Write-Host "[+] No workaround needed, you can still customize the SMBv3 compression if you like." return } Else { Write-Host "[-] Windows Update $($kb) is not installed." } ``` ![](https://i.imgur.com/XLXs6lh.png) ### 漏洞重現 - victim ![](https://i.imgur.com/7RU0lSM.png =500x) - attack - 使用[eerykitty](https://github.com/eerykitty/CVE-2020-0796-PoC)的POC ![](https://i.imgur.com/2zhzsBu.png =400x) <font color='red'>**當執行腳本後會導致藍屏BSOD**</font> ![](https://i.imgur.com/vO6WwDK.png =400x) ## 漏洞分析 ### 原始碼分析 漏洞主要存在於Window驅動的漏洞主要存在於Window驅動的<font color='red'>**srv2.sys**</font> (C:\Windows\System32\drivers\srv2.sys) 中。 在srv2.sys中和smb2解壓縮相關的函式包含: - Smb2GetHonorCompressionAlgOrder - Srv2DecompressMessageAsync - Srv2DecompressData - Smb2ValidateCompressionCapabilities - Smb2SelectCompressionAlgorithm `Srv2ReceiveHandler`再收到封包時會檢查檔頭紀錄的協議,當發現`0x424D53FC`時,代表該封包屬SMB2的協議,因此會會叫`Srv2DecompressMessageAsync`對封包進行解壓縮 ![](https://i.imgur.com/alDUxId.png =520x) `Srv2DecompressMessageAsync`會調用`Srv2DecompressData`去對封包進行解壓縮 ![](https://i.imgur.com/1jg1YSY.png =400x) 接著`Srv2DecompressData`會去申請記憶體空間(`SrvNetAllocateBuffer`)用來存解壓縮後的資料 ![](https://i.imgur.com/De0yyrw.png =460x) <font color='red'>srv2.sys中`Srv2DecompressData()`實現對SMBv3解壓縮資料段的數字檢查不夠嚴謹,未檢查OriginalCompressedSegmentSize和Offset/Length運算後的合法性,導致`unsigned int`溢位。</font> 溢位的數字會被後面利用還申請一記憶體空間,進而發生非預期的狀況導致解壓縮的payload會覆蓋到申請的記憶體以外的區塊。 ### SMB2協議 根據微軟MS-SMB2協議文件檔案,SMB Compression Transform Header的結構如下 ![](https://i.imgur.com/r5QxJcu.png) - ProtocolId(4bytes) - 用來識別協議類別和版本 - 固定為**0x424D53FC**(0xFC,'S','M','B') - OriginalCompressedSegmentSize(4bytes): - 未壓縮前的資料段大小 - 單位:Byte - CompressionAlgorithm(2bytes): - 必須記錄SMB2所使用的其中一個壓縮演算法 ![](https://i.imgur.com/UH3y4Q6.png =500x) - Flags(2bytes): - 必須設定以下其中一個值 ![](https://i.imgur.com/Xh6yfHe.png =500x) - Offset/Length(4bytes): - 如果Flag設定為SMB2_COMPRESSION_FLAG_CHAINED(0x0001),解釋為長度(Length) - 代表壓縮後的payload長度,單位為Byte - 除上述之外,皆解釋為偏移量(Offset) - 代表壓縮的資料相對於結構的偏移量 - from the end of this structure to the start of compressed data segment 解壓縮所需要的大小需參考檔頭中的**OriginalCompressedSegmentSize**和**Offset/Length** 根據文件可知協議內的檔頭架構 ``` typedef struct _COMPRESSION_TRANSFORM_HEADER { ULONG ProtocolId; ULONG OriginalCompressedSegmentSize; USHORT CompressionAlgorithm; USHORT Flags; ULONG Length; }COMPRESSION_TRANSFORM_HEADER, *PCOMPRESSION_TRANSFORM_HEADER; ``` ### 小結 因為協議本身使用**系統權限**,可以碰觸到**作業系統的記憶體分布** 因此可以利用此漏洞完成: - 本地提權LPE - 系統權限 - [danigargu-CVE-2020-0796](https://github.com/danigargu/CVE-2020-0796/) - [f1tz-CVE-2020-0796-LPE-EXP](https://github.com/f1tz/CVE-2020-0796-LPE-EXP) - 藍屏BOSD - 只要蓋掉原本作業系統放在記憶體中的資訊,導致後續利用發生錯誤 - [eerykitty-CVE-2020-0796-PoC](https://github.com/eerykitty/CVE-2020-0796-PoC) - 遠端代碼控制RCE - 難度較高,需要先leak出記憶體資訊再透過heap spray、ROP等技術構造payload 網路上目前較被認證且公開的script為<font color='blue'>**提權**</font>和<font color='blue'>**藍屏**</font> ## PoC研究 ### 本地提權LPE 目前已公開用來執行本地提權的PoC主要包含以下幾個重要流程 - 首先驗證process初始的SMB server對話建立(session) - 驗證process獲得自身token數據結構中privilege成員在內核中的地址(tokenAddr) - 驗證process通過session發送"畸形"壓縮數據(evilData)給SMB server觸發漏洞 - 其中evilData包含:tokenAddr、極限數據、stackoverflow的數據 - SMB server收到evilData後觸發漏洞,並修改tokenAddr地址處的極限數據,從而提升驗證process的權限 - 驗證proess獲取極限後對winlogon進行控制,來創建system使用者的shell ### 藍屏BOSD ### 遠端代碼控制RCE ## 研究進度紀錄 ```mermaid gantt title Research Progress section 漏洞驗證 環境架設 :a1, 2020-05-11, 2020-05-18 漏洞重現 :after a1 , 2020-06-04 section 漏洞分析 原始碼分析 :2020-05-28 , 2020-06-08 SMB2協議 : 2020-06-01 , 2020-06-04 section PoC研究 本地提權LPE :2020-06-08 , 1d 藍屏BOSD : 2020-06-08, 1d 遠端代碼控制 : 2020-06-08, 1d ``` <font size='2'> | Date | Progress | BottleNeck Detail | TODO | Solution | | :--: | :--: | :---- | :--| :--- | | 2020-05-11 | 環境架設 |使用[ollypwn](https://github.com/ollypwn/SMBGhost) 的漏洞掃描腳本,回傳無漏洞![](https://i.imgur.com/0HoZBqj.png)|重新檢查版本和SMBv3版本功能是否啟動 |2020-05-19<br>作業系統為win10 1809版本<br>須更新至1903 / 1909的版本![](https://i.imgur.com/bwFsE4U.png) |2020-05-21|漏洞重現|使用Github公認exp無法製造藍屏|先研究漏洞成因在匯去檢查exp有沒有要修改的部分|2020/6/2<br>BGuy學長提供1903版本,藍屏<br>歡呼~| |2020-05-28|靜態分析|取出1909版本的srv2.sys反組譯結果和1903有差異,無法像網路上文章那樣清楚|1.嘗試安裝1903(x)<br>2.檢查symbol path(o)|2020/6/2<br>BGuy學長提供1903版本給我了<br>感動| </font> ## 參考資料 [1] https://mp.weixin.qq.com/s/kWKzbjz8CHTaNgRBhqJHpg [2] https://xz.aliyun.com/t/7440 [3] https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-smb2/1d435f21-9a21-4f4c-828e-624a176cf2a0