作者:B1tg
本文為作者投稿,Seebug Paper 期待你的分享,凡經采用即有禮品相送! 投稿郵箱:paper@seebug.org

漏洞介紹

2023年8月23號,group-ib[1] 公開了 WinRAR 中存在的 0day 漏洞 CVE-2023-38831,其被在野利用于攻擊交易員。

該漏洞觸發需要用戶打開 zip 壓縮包并點擊其中的誘餌文件,可被用于釣魚攻擊。

影響版本為 winrar < 6.23

分析

漏洞觸發過程主要分成兩個環節:

  1. 點擊誘餌文件時額外的文件被釋放

  2. 點擊文件后程序執行了額外釋放的文件而非用戶點擊文件

文件釋放 bug

zip 文件中包含三種數據結構:ZIPFILERECORD, ZIPDIRENTRY, ZIPENDLOCATOR,這里主要關心 ZIPDIRENTRY,其用于描述壓縮包內目錄的結構,每個文件/目錄都對應一個這樣的數據結構

用戶在 winrar 窗口點擊某個文件后,winrar 會遍歷壓縮包中的 direntry,依次比較direntry->filename 和點擊文件名(click_name),匹配成功的 direntry 對應的文件后續會解壓到臨時目錄下,比較函數為 0047F790,匹配成功該函數返回1,失敗則返回0

比較成立的條件為 entry_name 等于 click_name,或者 entry_name 等于 click_name 加上路徑分隔符。

比較邏輯用偽代碼表示為:

extract_list = []
def compare_click_and_entry(entry_name, click_name):
    click_name_len = len(click_name)
    if entry_name[:click_name_len] == click_name and \
      entry_name[click_name_len] in ("\\", "/", "\x00"):
        return 1
    return 0

for direntry in zip.direntry_list:
    if compare_click_and_entry(direntry.name, click_name):
        extract_list.append(direntry.name)

在poc樣本中[1] ,誘餌文件對應的是 dirEntry[2], 點擊誘餌文件后 click_name = "CLASSIFIED_DOCUMENTS.pdf "

三個等待比較的 entry_name 為: - "CLASSIFIED_DOCUMENTS.pdf /" - "CLASSIFIED_DOCUMENTS.pdf " - "CLASSIFIED_DOCUMENTS.pdf /CLASSIFIED_DOCUMENTS.pdf .cmd"

三個 entry_name 比較結果都為 1,兩個文件將會被釋放到臨時目錄下,第一個 bug 出現了,雖然用戶點擊了一個文件,但是 winrar 額外釋放了一個 .cmd 文件。

這個 bug 和 entry_name 中的空格、子文件的名字無關,只要 click_name 和 entry_name 成功匹配,entry對應的文件就會被釋放,下面進行驗證。

構造如下的文件夾:

壓縮成 zip 后包含7個 dirEntry 結構:

在二進制編輯器中修改 dirEntry[1] 的 filename,由Cir 改成 Dir

保存后打開該壓縮包,可以看到同名的文件夾和文件夾

此時文件中的7個 entry_name 如下: - Bir - Dir - Dir/ - Dir/a1.txt - Dir/a2.txt - Eir - Eir/e1.txt

如果點擊文件 Dir,匹配的 entry_name 如下,對應的文件會被釋放

  • Dir
  • Dir/
  • Dir/a1.txt
  • Dir/a2.txt

雙擊winrar中的文件Dir(右擊查看文件也可以),可以看到臨時目錄下有三個文件被釋放,和分析結果一致。

反常的執行邏輯

poc樣本具有如下結構:

根據上一節的分析,在 winrar 中雙擊樣本的 dirEntry[2]("CLASSIFIED_DOCUMENTS.pdf "),winrar 會在臨時目錄下釋放兩個文件:

  • CLASSIFIED_DOCUMENTS.pdf
  • CLASSIFIED_DOCUMENTS.pdf .cmd

隨后 winrar 會調用函數 ShellExecuteExW 執行文件,傳入的 shExecInfo.lpFile 為: "C:\\Users\\DELL\\AppData\\Local\\Temp\\Rar$DIa21552.1835\\CLASSIFIED_DOCUMENTS.pdf "

BOOL ShellExecuteExW(
  [in, out] SHELLEXECUTEINFOW *pExecInfo
);

實際上 ShellExecuteExW 會運行臨時目錄下的 CLASSIFIED_DOCUMENTS.pdf .cmd 觸發漏洞,整個過程可以描述為:用戶在 winrar 中點擊了一個文檔文件,winrar 卻執行了同名目錄下的腳本而非文檔文件本身。

ShellExecuteExW 函數為什么在路徑末尾有空格的情況下執行了一個 .cmd 文件?

分析發現,ShellExecuteExW 函數會調用 shlwapi!PathFileExistsDefExtAndAttributesW 對路徑進行處理

在 PathFileExistsDefExtAndAttributesW 函數中,當路徑末尾有空格時 PathFindExtensionW 函數會返回NULL,之后會進入函數 sub_7FF741824B4 給路徑添加上通配符.* 進行文件搜索,并對搜索到的文件進行后綴判斷,第一個符合條件的文件名被用作后續執行,在前面的情況下,搜索到的就是文件"C:\\Users\\DELL\\AppData\\Local\\Temp\\Rar$DIa21552.1835\\CLASSIFIED_DOCUMENTS.pdf .cmd"

由于后綴判定按給定列表遍歷,可以判斷出 ShellExecuteExW 的后綴搜索的順序依次為:

  • .pif

  • .com

  • .exe

  • .bat

  • .lnk

  • .cmd

也就是說如果在文件夾下放置多個這些后綴的文件,會按照優先級執行第一個。在構造樣本時不一定要用 .cmd 后綴,上面的選項都能觸發。

目前公布的在野樣本、POC使用的都是類似如下的 direntry 組合觸發漏洞:

  • a.pdf

  • a.pdf /

  • a.pdf /a.pdf .cmd

一些廠商也通過 direntry 中空格加斜杠這樣的特征[3]來檢測此類漏洞。

通過對函數 PathFindExtensionW 進行分析發現,只要路徑中的最后一個 . 后面包含空格,該函數返回值就為空,ShellExecuteExW 就能進入搜索邏輯。

于是可以構造類似如下 direntry 組合的樣本繞過常規檢測

  • top.secret pdf

  • top.secret pdf/

  • top.secret pdf/top.secret pdf.bat

相關鏈接

  1. https://www.group-ib.com/blog/cve-2023-38831-winrar-zero-day/

  2. https://github.com/b1tg/CVE-2023-38831-winrar-exploit

  3. https://isc.sans.edu/diary/Analysis+of+RAR+Exploit+Files+CVE202338831/30164/

  4. https://aleeamini.com/cve-2023-38831-winrar-bug-or-windows-feature/


Paper 本文由 Seebug Paper 發布,如需轉載請注明來源。本文地址:http://www.bjnorthway.com/3036/