摘要:重入攻擊本質上與編程里的遞歸調用類似,當合約將以太幣發送到未知地址時就可能會發生,威脅以太坊智能合約的安全性。知道創宇區塊鏈安全實驗室?從轉賬方法、fallback函數、漏洞代碼、源碼分析四個方面入手,深入分析攻擊原因,詳解?The?DAO事件。
前言
智能合約的概念于1995年由NickSzabo首次提出,它是一種旨在以信息化方式傳播、驗證或執行合同的計算機協議,它允許在沒有第三方的情況下進行可信交易,這些交易可追蹤且不可逆轉。
然而智能合約也并非是安全的,其中?重入(Re-Entrance)攻擊?漏洞是以太坊中的攻擊方式之一,早在2016年就因為TheDAO事件而造成了以太坊的硬分叉。
漏洞概述
在以太坊中,智能合約能夠調用其他外部合約的代碼,由于智能合約可以調用外部合約或者發送以太幣,這些操作需要合約提交外部的調用,所以這些合約外部的調用就可以被攻擊者利用造成攻擊劫持,使得被攻擊合約在任意位置重新執行,繞過原代碼中的限制條件,從而發生重入攻擊。重入攻擊本質上與編程里的遞歸調用類似,所以當合約將以太幣發送到未知地址時就可能會發生。
藍色光標:與騰訊在作為元宇宙入口的虛擬人業務有較深入合作:11月16日消息,藍色光標在互動平臺表示,公司與騰訊在游戲、動漫、閱文等層面有深入合作;同時,在作為元宇宙入口的虛擬人業務,也有較深入合作。[2021/11/16 21:54:34]
簡單的來說,發生重入攻擊漏洞的條件有2個:
調用了外部的合約且該合約是不安全的
外部合約的函數調用早于狀態變量的修改
下面給出一個簡單的代碼片段示例:
上述代碼片段就是最簡單的提款操作,接下來會給大家詳細分析重入攻擊造成的原因。
漏洞分析
在正式的分析重入攻擊之前,我們先來介紹幾個重點知識。
轉賬方法
由于重入攻擊會發送在轉賬操作時,而Solidity中常用的轉賬方法為
.transfer(),.send()和.gas().call.vale()(),下面對這3種轉賬方法進行說明:
.transfer():只會發送2300gas進行調用,當發送失敗時會通過throw來進行回滾操作,從而防止了重入攻擊。
現場 | 觀點:區塊鏈技術需要深入場景才能形成產業:金色財經現場報道,10月15日,華山論劍2020網絡安全大會于西安召開,在大會的區塊鏈安全與應用創新分論壇圓桌討論環節,
基石基金管理合伙人秦少博分享表示,區塊鏈創新型的業務需要承擔比較大的沉默成本,在區塊鏈領域創業需要考量自身能力。區塊鏈技術需要深入場景才能形成產業,過去5年由幣引發的熱潮已經越發理智。把區塊鏈作為技術、生產力討論更合適。不宜與太大的市場概念結合。
中國移動研究院安全技術研究所所長何申分享表示,從通信行業看待區塊鏈,會從系統工程高度去看,當區塊鏈從節點成網形成共識,需要考慮節點的安全。此外,可信是一種保障預期方案,區塊鏈是一種方案,兩種方案的協同,是通信領域的重點。對于區塊鏈透明性帶來的隱私問題可以通過隱私技術解決,但可能在公鏈場景里比較難實現。[2020/10/15]
.send():只會發送2300gas進行調用,當發送失敗時會返回布爾值false,從而防止了重入攻擊。
.gas().call.vale()():在調用時會發送所有的gas,當發送失敗時會返回布爾值false,不能有效的防止重入攻擊。fallback函數
動態 | 北大光華成立金融科技聯合實驗室 向區塊鏈等五大領域深入研究:10月12日,北京大學光華管理學院與度小滿金融宣布合作成立金融科技聯合實驗室,并在北京大學為實驗室揭牌。聯合實驗室主任劉曉蕾表示實驗室將圍繞數字化資產配置、超大規模關聯網絡、在線機器人、監管科技、區塊鏈技術等五大領域深入研究,積極探索前沿技術在金融場景中的應用,同時推動跨學科人才的培養和輸出。[2018/10/12]
接著我們來講解下fallback回退函數。
回退函數(fallbackfunction):回退函數是每個合約中有且僅有一個沒有名字的函數,并且該函數無參數,無返回值,如下所示:
function()publicpayable{???
???...
}
回退函數在以下幾種情況中被執行:
調用合約時沒有匹配到任何一個函數;
沒有傳數據;
智能合約收到以太幣。
漏洞代碼
德國證券交易所正深入研究是否推出比特幣期貨等相關產品:據ccn援引彭博社消息,德意志交易所(Deutsche Boerse)正在深入研究是否提供比特幣期貨和其他加密貨幣的相關產品。在一次行業盛會上,該公司的客戶,產品和核心市場負責人Jeffrey Tessler稱:“德意志交易所在推進比特幣之前,希望確保理解比特幣之下的交易,這不是最容易的一件事。我們正在深入地了解之中,希望了解波動性,想要確保客戶協調,及監管機構的協調。”Tessler表示,盡管CEM和CBOE在一個交易日期間比特幣期貨交易量多達6.7億美元,但目前沒有任何一家主要的歐洲交易所列出比特幣或其他加密貨幣的衍生產品。據悉,德意志交易所已經參與了區塊鏈實驗,他們今年3月份與流動性管理公司HQLAx合作,利用R3的Corda平臺開發基于區塊鏈的證券借貸平臺。[2018/5/24]
下面的代碼就是存在重入攻擊的,實現的是一個類似于公共錢包的合約,所有的用戶都可以使用deposit()存款到Reentrance合約中,也可以從Reentrance合約中使用withdraw()進行提款,當然了所有人也可以使用balanceof()查詢自己或者其他人在該合約中的余額。
迅雷CEO陳磊:區塊鏈一定要深入到老百姓當中:迅雷CEO陳磊在接受媒體采訪時表示,“區塊鏈一定要深入到老百姓當中。區塊鏈的發展還在一個相對早期的階段,所以一旦你掌握了區塊鏈的一些正在改進中的技術,那么就能取得領先,但是這些技術必須要和現實場景結合才能有意義。我們希望看到,迅雷生態鏈上能有大量推動實體經濟發展和C端用戶參與的應用,這是區塊鏈發展的核心動力。”[2018/5/20]
首先使用一個賬戶(0x5B38Da6a701c568545dCfcB03FcB875f56beddC4)扮演受害者,將該合約在RemixIDE?點擊Deploy按鈕進行部署。
在部署合約成功后在VALUE設置框中填寫5,將單位改成ether,點擊deposit存入5個以太幣。
點擊wallet查看該合約的余額,發現余額為5ether,說明我們的存款成功。
而下面的代碼則是針對上面存在漏洞的合約進行的攻擊:
使用另外一個賬戶(0xAb8483F64d9C6d1EcF9b849Ae677dD3315835cb2)扮演攻擊者,復制存在漏洞的合約地址到Deploy的設置框內,點擊Deploy部署上面的攻擊合約。
部署成功后先調用wallet()函數查看攻擊合約的余額為0。
攻擊者先存款1ether到漏洞合約中,這里設置VALUE為1ether,之后點擊攻擊合約的deposit進行存款。
再次調用合約的wallet函數查看漏洞合約的余額,發現已經變成了6ether。
攻擊者(0xAb8483F64d9C6d1EcF9b849Ae677dD3315835cb2)調用攻擊合約的attack函數模擬攻擊,之后調用被攻擊合約的wallet函數去查看合約的余額,發現已經歸零,此時回到攻擊合約查看余額,發現被攻擊合約中的6ether已經全部提款到了攻擊者合約中,這就造成了重入攻擊。
源碼分析
上面講解了如何進行重入攻擊已經漏洞原因,這里梳理了漏洞源碼和攻擊的步驟,列出了關鍵代碼。
相關案例
2016年6月17日,TheDAO項目遭到了重入攻擊,導致了300多萬個以太幣被從TheDAO資產池中分離出來,而攻擊者利用TheDAO智能合約中的splitDAO()函數重復利用自己的DAO資產進行重入攻擊,不斷的從TheDAO項目的資產池中將DAO資產分離出來并轉移到自己的賬戶中。
下列代碼為splitDAO()函數中的部分代碼,源代碼在TokenCreation.sol中,它會將代幣從theparentDAO轉移到thechildDAO中。平衡數組uintfundsToBeMoved=(balances*p.splitData.splitBalance)?/p.splitData.totalSupply決定了要轉移的代幣數量。
下面的代碼則是進行提款獎勵操作,每次攻擊者調用這項功能時p.splitData都是一樣的,并且p.splitData.totalSupply與balances的值由于函數順序問題,發生在了轉賬操作之后,并沒有被更新。
paidOut=reward更新狀態變量放在了問題代碼payOut函數調用之后。
對_recipient發出.call.value調用,轉賬_amount個Wei,.call.value調用默認會使用當前剩余的所有gas。
解決辦法
通過上面對重入攻擊的分析,我們可以發現重入攻擊漏洞的重點在于使用了fallback等函數回調自己造成遞歸調用進行循環轉賬操作,所以針對重入攻擊漏洞的解決辦法有以下幾種。
使用其他轉賬函數
在進行以太幣轉賬發送給外部地址時使用Solidity內置的transfer()函數,因為transfer()轉賬時只會發送2300gas進行調用,這將不足以調用另一份合約,使用transfer()重寫原合約的withdraw()如下:
先修改狀態變量
這種方式就是確保狀態變量的修改要早于轉賬操作,即Solidity官方推薦的檢查-生效-交互模式(checks-effects-interactions)。
使用互斥鎖
互斥鎖就是添加一個在代碼執行過程中鎖定合約的狀態變量以防止重入攻擊。
使用?OpenZeppelin官方庫
OpenZeppelin官方庫中有一個專門針對重入攻擊的安全合約:
https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/security/ReentrancyGuard.sol
參考文獻
1.以太坊的幾次硬分叉:
https://zhuanlan.zhihu.com/p/111446792
2.以太坊智能合約安全漏洞(1):重入攻擊:
https://blog.csdn.net/henrynote/article/details/82119116
3.?區塊鏈的那些事—THEDAO攻擊事件源碼分析:
https://blog.csdn.net/Fly_hps/article/details/83095036
一:大部分投資者,包括新人和很多老司機,獲取投資信息的重要渠道,就是聽朋友、群友的介紹。“聽說這只股票過幾天有利好消息;”“聽說那個幣有莊家要拉盤;”“聽說黃金走勢開始向下,可以做空了;”人們總.
1900/1/1 0:00:00以太坊區塊鏈瀏覽器和分析平臺Etherscan已啟用NFT跟蹤工具作為其交易跟蹤工具包的一部分.
1900/1/1 0:00:00尊敬的歐易OKEx用戶:2020年12月1日至2021年2月28日,OKB啟動了新一季度的回購銷毀.
1900/1/1 0:00:00大家好,我是來自CKcoin平臺首席分析師老崔說幣,也是你們的朋友老崔說幣lcsb18888,老崔說幣公眾號同步專注數字貨幣行情分析,爭取為廣大幣友傳遞最有價值的幣市信息.
1900/1/1 0:00:00尊敬的用戶, WBF于2021年5月26日12:00-2021年5月30日12:00舉辦的”10000USDT助力金為您的信仰充值“活動獎勵已經發放,請獲獎用戶及時查看資產.
1900/1/1 0:00:00Bitget全球站用戶:為了全球用戶更方便更快捷的進行數字貨幣交易,Bitget已于新加坡時間2021年6月3日在App端上線全球OTC功能.
1900/1/1 0:00:00