🎉 攢成長值,抽華爲Mate三折疊!廣場第 1️⃣ 2️⃣ 期夏季成長值抽獎大狂歡開啓!
總獎池超 $10,000+,華爲Mate三折疊手機、F1紅牛賽車模型、Gate限量週邊、熱門代幣等你來抽!
立即抽獎 👉 https://www.gate.com/activities/pointprize?now_period=12
如何快速賺成長值?
1️⃣ 進入【廣場】,點擊頭像旁標識進入【社區中心】
2️⃣ 完成發帖、評論、點讚、發言等日常任務,成長值拿不停
100%有獎,抽到賺到,大獎等你抱走,趕緊試試手氣!
截止於 8月9日 24:00 (UTC+8)
詳情: https://www.gate.com/announcements/article/46384
#成长值抽奖12期开启#
Move語言新整數溢出漏洞分析:從引用安全到DoS攻擊
Move語言又一高危漏洞深度剖析
之前我們發現了Aptos Moveevm的一個嚴重漏洞,經過深入研究,我們又發現了一個新的整數溢出漏洞。這次漏洞的觸發過程更加有趣,下面我們將深入分析這個漏洞,同時介紹一些Move語言的背景知識。相信通過本文的講解,你會對Move語言有更深入的理解。
衆所周知,Move語言在執行字節碼之前會驗證代碼單元。驗證過程分爲4個步驟,而這個漏洞就出現在reference_safety步驟中。
reference_safety模塊定義了用於驗證過程主體的引用安全性的轉移函數。其檢查包括驗證沒有懸空引用、對可變引用的訪問是否安全、對全局存儲引用的訪問是否安全等。
引用安全驗證的入口函數會調用analyze_function。在analyze_function中,函數會對每一個基本塊進行驗證。基本塊是指除了入口和出口之外沒有分支指令的代碼序列。
Move語言通過遍歷字節碼、查找所有分支指令以及循環指令序列來確定基本塊。一個典型的Move IR代碼基本塊示例可能包含3個基本塊,分別由BrTrue、Branch和Ret指令確定。
Move中的引用安全
借鑑Rust語言的思想,Move支持兩種類型的引用:不可變引用(&)和可變引用(&mut)。不可變引用用於從結構中讀取數據,可變引用用於修改數據。合理使用引用類型有助於維護安全性並識別讀取模塊。
Move的引用安全模塊會以函數爲單位,掃描函數中基本塊的字節碼指令,驗證所有引用操作是否合法。驗證過程主要涉及AbstractState結構體,它包含borrow graph和locals,用於確保函數中引用的安全性。
驗證過程會比較執行基本塊前後的state,並將結果合並以更新塊狀態,同時將該塊的後置條件傳播到後續塊。這個過程類似於V8 turbofan中的Sea of Nodes思想。
主循環會執行塊代碼,然後嘗試合並pre state和post state。如果狀態發生變化且當前塊存在指向自身的後向邊(表示有循環),則會跳回循環開頭,繼續執行此基本塊,直到post state等於pre state或因錯誤而中止。
漏洞分析
漏洞出現在判斷join結果是否改變的過程中。join_函數用於更新本地變量和borrow關係圖。當函數參數長度加上局部變量長度超過256時,由於local變量是u8類型,在遍歷locals時會發生溢出。
雖然Move有校驗locals個數的過程,但在check bounds模塊只校驗了locals,並未包括參數length。開發人員似乎意識到需要檢查參數和本地值的總和,但代碼實際上只校驗了本地變量的數量。
從整型溢出到DoS攻擊
主循環會掃描代碼塊並調用execute_block函數,之後合並執行前後的state。當代碼中存在循環時,會跳轉到代碼塊開始再次執行。
如果我們構造一個循環代碼塊並利用溢出改變塊的state,使新的locals map與之前不同,那麼再次執行execute_block時,分析basic block中的指令序列會訪問新的locals map。此時如果指令需要訪問的索引在新的map中不存在,就會導致DoS。
在reference safety模塊中,MoveLoc/CopyLoc/FreeRef操作碼可以實現這個目標。以copy_loc函數爲例,它會嘗試通過LocalIndex獲取本地值,如果LocalIndex不存在則會導致panic,從而使整個節點崩潰。
PoC演示
我們可以構造一個包含無條件分支指令的basic block,使其多次調用execute_block和join函數。通過設置適當的參數和本地變量數量,可以在第一次執行後將新的locals map長度縮減爲8。
在第二次執行時,嘗試訪問不存在的offset就會導致panic,從而觸發DoS。
總結
這個漏洞說明即使是經過嚴格靜態校驗的Move語言也存在安全隱患。溢出漏洞可以繞過邊界校驗,突顯了代碼審計的重要性。
作爲Move語言安全研究的領導者,我們建議語言設計者在Move運行時增加更多檢查代碼,以防止意外情況發生。目前Move主要在verify階段進行安全檢查,但運行階段缺乏足夠的安全加固,可能會導致更嚴重的問題。
我們還發現了Move語言的另一個漏洞,將在後續與大家分享。