ETHTaipei x TEM #5
2024/08/21:探討 Web3 安全:從攻擊事件追蹤到重現 Meetup
by Alex
隨著 Web3 安全事件逐年增多,損失金額也呈現上升趨勢,攻擊手法日益複雜,其中不乏涉及多個知名大項目。這些現象顯示,智能合約安全正逐漸成為備受關注的話題。在本次分享會中,Louis 將結合自身經驗,帶領大家使用交易分析工具,介紹常見的合約安全漏洞,並演示如何針對已發生的安全事件進行事後攻擊分析及撰寫 POC,來復現攻擊手法。
過往 Web3 安全事件統計
在開始介紹攻擊之前,我們先來看看鏈上統計的被盜金額數據,這是由 DefiLlama 統計的數量,從下面幾份數據可以看出約莫從 2021 後, 隨著各家 DeFi 如雨後春筍般出現後,就不乏許多厲害的攻擊者對各種 Protocol 展開許多攻擊。
Total Value Hacked
Attack Incident Number
Attack Incident Loss
資料來源: QuillMonitor
安全事件分析專欄/學習資源
與 Web2 世界不同,Web3 世界最大特點在於區塊鏈上的所有交易紀錄都是公開且不可銷毀的。即使是厲害的駭客,也無法抹除鏈上的攻擊痕跡。這意味著,一旦攻擊發生,任何人都可以通過節點的歷史紀錄,完整重現當時的攻擊場景,並且對此進行攻擊重現。也正因如此,才有許多厲害的「鏈上專家」對這些攻擊進行事後分析,加速整體 Web3 安全的迭代。
無論你是白帽駭客、智能合約開發者,或是對於共同保護 Web3 安全充滿熱情的新手,都可以透過以下網站開始學習,這些網站主要分成三大類:
1. Attack Incident Database
這類網站負責收集過往許多大大小小的攻擊事件,總結攻擊發生細節,包含鏈上交易、損失金額以及攻擊復現。
2. Postmortem Analysis
這類網站是專業的 Web3 安全團隊專欄。主要針對近期重大安全事件進行詳細的「驗屍報告」分析,有時也會介紹最新的安全分析工具,讓讀者能夠從專業安全人員的角度,深入理解事件背後的更深層次問題。
3. Real Time Alert
這些是 X 平台上的官方帳號,專門發佈即時安全事件警告,針對正在發生的攻擊進行即時通知。透過這些帳號,你可以獲取第一手的安全事件資訊。
漏洞攻擊分析與 POC 復現
終於進到本次的主角:智能合約常見的攻擊向量(Attack Vector)分析與 POC 復現
常見的交易分析工具:
用過幾個交易分析工具後,我個人還是最喜歡 Phalcon 的介面,因為追蹤交易過程的互動邏輯最直覺且簡潔,後面介紹的例子也都會用 Phalcon 來介紹。但是 Phalcon 支援的鏈沒有像 Tenderly 這麼多,所以有時候也會和 Tenderly 交替使用。
題外話:Phalcon 是最早有意識到模擬攻擊使用的 chainId
不能和真實的主鏈一樣。即便是模擬,但模擬過程中如果有產生簽名,那麼模擬所產生的簽名能被拿到主鏈上進行簽名重放的攻擊,這點 Tenderly 團隊最初並沒意識到這個問題,只有 Phalcon 注意到這點,並且區分主鏈與模擬的 chainId
。這可能跟 Phalcon 本身有強大的 Web3 安全團隊有關。
如何分析一筆複雜的攻擊交易
區分攻擊場景的幾個角色
雖然每個攻擊的細節各不相同,但大致上可以劃分出幾個不同的角色:
Attacker:攻擊者,負責發起攻擊交易的人。
Attack Contract:由攻擊者撰寫的攻擊合約,主要執行攻擊者設計的攻擊流程。這類合約通常不會在鏈上進行驗證,因此我們一般不會直接從這裡分析攻擊手法。
Helper Contract:根據攻擊情境所需,在攻擊過程中額外創建的合約。
Victim Contract:被攻擊的主要合約。通常,攻擊的 Root Cause 能在這裡找到。
External Contract:Victim 合約在運作時與之交互的外部合約。
區分攻擊交易的幾個階段:
Attack Preparation:進行攻擊前的準備工作,例如閃電貸借款、創建 Helper 合約。
Exploit Procedure:與 Victim 合約的交互,主要的攻擊流程會在這個階段發生。
Post Attack Handling:到了這一步,攻擊基本上已經完成,剩下的流程包括歸還閃電貸款及將贓款轉移到指定地址。
常見合約漏洞一:Access Control
這個漏洞主要出現在某些敏感函式沒有設置或正確設置相應的權限控制,導致任何人都能操作合約中的關鍵功能。
範例一: FLIX
Victim Contract: https://etherscan.io/address/0xe58acb560fc33e283ab70c700a0f2eed0e333e0a#code
Root Cause 分析
在 init
函式中,可以看到 owner
會被更改為執行該函式的地址,但函式本身又允許任何人執行。這會導致原本設置只有 owner
能執行的函式形同虛設。因為任何人都能透過 init
函式來更改任意的 owner
,使其能夠執行合約中只能給 owner
執行的函式。
例如合約中的 withdraws
函式,透過 onlyOwner
來限制只有 owner
能執行。
講到這邊為止,大概就能知道大致上怎麼實現這個攻擊了!
攻擊手法:先透過執行 init
將 owner
設為自己,接著成功變成合約的 owner
後,再去呼叫 withdraws
將合約中的餘額給取走,流程如下圖所示。
從這個例子來看,整個攻擊流程相對簡單,關鍵在於敏感函式沒有被限制只能由特定角色執行。儘管如此,這類漏洞在許多攻擊事件中仍然頻繁出現。在 2023 OWASP 常見合約攻擊中,訪問控制(Access Control)漏洞排名第四。
常見合約漏洞二:Arbitrary Call
這個漏洞主要發生在合約允許外部地址任意調用它的某些函式,而沒有適當限制。這意味著攻擊者可以通過特定的 calldata
,調用任意合約中可執行的函式,進而執行未預期的操作或篡改合約的狀態。這類漏洞經常出現在合約的代理模式或是合約間的跨合約調用中,稍有不慎,就可能被攻擊者利用,造成嚴重損失。
範例:RICO
Victim Contract: https://arbiscan.io/address/0x598c6c1cd9459f882530fc9d7da438cb74c6cb3b#code
Root Cause:
在 flash
函式中,可以看出函式本身允許任何人帶入任意的 code
及 data
。意味著合約允許任何人透過這個 flash
函式執行任何可執行的函式。
接著,我們就來看看在這樣的情境底下,我們可以對其合約進行怎樣的攻擊吧!
攻擊手法: 透過 flash
的設計,攻擊者利用 flash
來執行代幣的 transfer
函式,將該合約中所有代幣都直接轉移到攻擊者手上,最後再將贓款全部換成 USDC。
額外補充:因為 flash
函式本身可以執行任意可執行的程式碼,因此除了直接轉走合約中的代幣以外,我們也可以讓合約來執行 ERC20 的 approve
函式,讓合約授權指定地址能夠轉走合約中的代幣,一旦有代幣存入合約中,就能讓先前指定的地址來轉走合約中的錢。想了解這個攻擊情境,可參考 CTF: DamnVulnerableDefi 的題目 Truster。
常見合約漏洞三:Reentrancy
這個漏洞發生在智能合約允許外部合約在一個函式執行過程中反覆調用同一函式,而沒有適當防護措施。攻擊者主要利用合約在尚未更新狀態之前,不斷重入函式,導致資金被多次提取或重複操作。這類攻擊在合約涉及資金轉移的場景中特別危險,因為它可能導致合約中的資金被耗盡。即便這種漏洞已經被廣泛認知,但在許多經典攻擊事件中仍能看到它的影子。
範例:GameToken
Victim Contract: https://etherscan.io/address/0x52d69c67536f55efefe02941868e5e762538dbd6#code
Root Cause:
在 makeBid
函式中,執行了以下幾個步驟:
Check: 檢查
msg.value
是否為合法的出價。Interact: 如果
bidAddress
不為空地址,合約將相應的 ETH 轉移給bidAddress
。Effect: 更新出價者、出價金額及出價截止時間。
這是一個非常典型的容易受到 Reentrancy 攻擊影響的模式。
正如前面提到的,Reentrancy攻擊的關鍵在於:在與外部合約交互之前,合約未先更新相關的變數。這導致雖然合約內的實質狀態已經改變(e.g. bidEther
),但對應的管理變數還未更新。因此,當外部合約重新進入並執行該函式時,檢查條件依舊使用舊的變數狀態,從而使攻擊者能夠不斷重入並觸發攻擊行為。
攻擊行為如下圖所示:
緩解手段
遵守 Check-Effect-Interact 模式: 正如上述所述,這類攻擊之所以能夠成功,是因為在執行外部合約之前,相關變數狀態未能即時更新,導致即使合約狀態已經改變,外部合約在再次執行該函式時仍然能滿足先前的條件。為了有效避免 Reentrancy 攻擊,最關鍵的方法是在執行外部合約之前,先更新相關變數狀態。這就是 Check-Effect-Interact 模式的核心,確保合約在與外部合約交互之前已經更新了變數,使下一次重入時能夠根據最新的變數狀態進行判斷,從而防止攻擊發生。
使用 Reentrancy guard modifier:利用對函式進行上鎖的概念,來判斷函式是否執行到一半或是完全執行完成,只有當函式完全執行完之後,才允許再次執行該函式。透過這種方式,直接阻斷函式再次被重入的可能性。
延伸補充:如果 CEI 模式能夠阻擋 Reentrancy 攻擊,為何還需要使用 Reentrancy guard?
我在現場提問環節時有問到,之前在 X 上有位 OpenZeppelin 的核心開發者提出對於 Reentrancy guard 的看法,他認為 Reentrancy guard 本身是個半吊子且糟糕的解法,並且強調 OpenZeppelin 在自己的 codebase 中不會使用 Reentrancy guard,因為 OpenZeppelin 完全不需要仰賴 Reentrancy guard 防止 Reentrancy 攻擊(這點我並不太認同,因為 OZ 本身的 codebase 屬於合約的基礎建設,不像其他項目方有許多複雜情境考量,會需要極力避免重入的可能性)。
推文底下就有人提問:那為何 Uniswap 仍然在他們的 codebase 中使用 Reentrancy guard。
這位 OZ 核心開發者,表示他對於 Uniswap 本身了解並不深入,所以並沒有回覆太多他對於這件事情的看法。
Martinet 回覆:在遵守 Check-Effect-Interact 模式下,已經能夠很好防範 Reentrancy 攻擊,但考量到實現邏輯變得複雜之後會造成開發者的擔憂,所以在這個情況下加上 Reentrancy guard 能夠降低開發者與審計員的心理負擔,因此以這個角度來看,加上 Reentrancy guard 更多的是出自於心理安慰的考量。
延伸補充:除了上述提到的 Check-Effect-Interact 模式之外,針對協議級別的項目,還需要特別關注協議本身的不變性(Invariants)。
不變性(Invariants)指的是永遠不變的特性,例如像是:
AMM 中常見的 X * Y = K 或 X + Y == K。
流動性挖礦抵押中,用戶應該只能提取他們存入的抵押代幣數量。
也就是說在滿足 Check-Effect-Interact 模式之後,我們應該再多一步確保 Interact 動作之後,協議本身的不變性是否能夠被滿足。
這也說明為何 Uniswap (大概) 從來沒有被駭過,以 Uniswap V2 來說,核心的不變性就是 X * Y = K,正在這樣簡單且明確的不變性,讓他們開發出來的每個函數都是圍繞著這個不變性來服務的,因此能有效去避免運作過程中出現漏洞的可能性。詳細內容請參考這篇,這篇寫得很好值得推薦。
Video(影片處理完成後會更新到這!)
延伸討論
MEV Bot frontrun
by
講者有提到有些攻擊事件的攻擊交易被機器人給搶跑,搶走攻擊獲益,或甚至退還給受害的協議。其實搶跑是非常常見的事件,如同 Dark Forest 文章說述,其實有需多機器人隱藏在黑暗森林中,它們掃描每一筆交易,嘗試剽竊交易內容並替換裡面的資訊來看是否可獲利,如果可以的話就會提供比原本交易更豐厚的手續費來搶先執行自己的交易,也就是搶跑(Frontrun)。
資安緊急應變小組例如 SEAL 911 在嘗試解救被揭露有漏洞合約裡資產時就會透過其他方式來避開黑暗森林:避免直接廣播解救交易到公開的交易池,而是讓出塊者直接收入解救交易,當其他人看到解救交易時,解救交易已經被收入、生效了。
如果你有在使用 AMM,那你可能也會想要避免被搶跑或三明治夾擊,這時候你可以選擇透過 Order Flow Auction(OFA)機制來送出你的交易,你的交易可以獲得 MEV 保護,還有機會能獲得額外反佣。常見的 OFA 像是 Flashbot Protect、MEV Blocker。
Ronin Hack
在八月初 Ronin Network 又再一次被駭客攻擊,這一次是因為它的可升級合約在升級時所準備的 initialize
函式沒有按照預期的方式被呼叫,導致有重要參數沒有被初始化,因此被駭客所利用。
另外靜態分析工具 Slither 也在其資料庫中新增 Ronin 這一次漏洞的模式。
更進階的漏洞
講者也分享了一些更進階、少見的漏洞,讓有興趣的聽眾與讀者可以嘗試分析:
如果你在看完這次演講後有更多的問題想問、有其他技術想了解,請大方地告訴我們!
編輯閒聊分享區
Solidity 的 Error 與 Try/Catch 完整解析
by
Rareskill 的這篇文章完整介紹 Solidity Error 的起源與發生地,包含 require、revert 與 custom error 的不同以及各自實際的錯誤訊息會是什麼。另外還有 Try/Catch 的使用方式以及它不足的地方。對想要妥善處理好各種錯誤、意外的 Solidity 開發者來說非常實用。
Grant
TEM 在進行實驗性的 Grant,贊助一些公共財。如果你有任何公共財想法也歡迎讓我們知道!
待認領的 Grant
社群活動的報名平台 Survey
難度:★
贊助金額:USD $200
進行中的 Grant
Paragraph.xyz 作為文章發表平台的 Survey
不同 Web3 協議的 Governance 機制 Survey
Web2 整合 ENS 的 Survey
區塊鏈技術名詞翻譯計畫
宣傳
TEM Medium 2024 有獎徵稿
TEM Medium 目前正在進行有獎徵稿!詳情請參考這篇文章
2024/09/04 Defi TLDR
下一次的 TLDR 將在 9/4(三)舉辦,地點在 imToken 辦公室~
活動報名連結:https://lu.ma/qevxq2yu
快來把你最近看到的新聞或技術放到這裡和大家分享!