作者:ACce1er4t0r@知道創宇404區塊鏈安全研究團隊
時間:2020年7月22日
在7月15號,v2ex上突然出現了一個這樣標題的帖子:三行代碼就賺走 4000w RMB,還能這么玩?
帖子內容里,攻擊者僅僅只用了短短的幾行代碼,就成功的獲利千萬RMB,那么他是怎么做到的呢?
讓我們來回顧一下這次事件。
事件回顧
2020年1月16日,開源項目Ravencoin接到這么一則pull request

代碼中,提交者將原本定義模糊的報錯細分,讓人們能夠更直觀的了解究竟出了什么錯誤,看起來是在優化項目,但是,事實真是這樣么?
2020年6月29日,Solus Explorer開發團隊一位程序員在修bug后同步數據時發現了一個suspected transactions with unbalanced VOUTs被Explorer標記出,之后他檢查RVN時發現RVN大約被增發了約275,000,000,并發現了大量可疑地reissue asset Transaction,這些交易不僅僅有Asset Amount,而且獲得了RVN。在他發現這一事件后,馬上和他的團隊一起將事件報告給Ravencoin團隊。
2020年7月3日,Ravencoin團隊向社區發布緊急更新
2020年7月4日,13:26:27 (UTC),Ravencoin團隊對區塊強制更新了新協議,并確認總增發量為 301,804,400 RVN,即為3.01億RVN.
2020年7月5月,Ravencoin團隊宣布緊急事件結束
2020年7月8日,Ravencoin團隊公布事件

事件原理
在解釋原理前,我們不妨先重新看看WindowsCryptoDev提交的代碼

這是一段Ravencoin中用于驗證的邏輯代碼。
簡單來說,提交者改變了CheckTransaction對Asset驗證的判斷,將原本isAsset && txout.nValue != 0的條件更改為下面的條件:
isAsset && nType == TX_TRANSFER_ASSET && txout.nValue != 0isAsset && nType == TX_NEW_ASSET && txout.nValue != 0
這段代碼本身利用了開源社區PR的風格(在開源社區中,如果開發者發現提交的PR無關實際邏輯,則不會過度關注代碼影響),看似只是細化了交易過程中返回的報錯,使得正常使用功能的交易者更容易定位到錯誤,實則,通過忽略else語句,導致一個通用的限制條件被細化到了nType的兩種常見情況下。
而代碼中nTypt可能的值有如下:
enum txnouttype
{
TX_NONSTANDARD = 0,
// 'standard' transaction types:
TX_PUBKEY = 1,
TX_PUBKEYHASH = 2,
TX_SCRIPTHASH = 3,
TX_MULTISIG = 4,
TX_NULL_DATA = 5, //!< unspendable OP_RETURN script that carries data
TX_WITNESS_V0_SCRIPTHASH = 6,
TX_WITNESS_V0_KEYHASH = 7,
/** RVN START */
TX_NEW_ASSET = 8,
TX_REISSUE_ASSET = 9,
TX_TRANSFER_ASSET = 10,
TX_RESTRICTED_ASSET_DATA = 11, //!< unspendable OP_RAVEN_ASSET script that carries data
/** RVN END */
};
由于代碼的改變,當nType == TX_REISSUE_ASSET時,txout.nValue可以不為0。
通過對比正常的交易和存在問題的交易,我們也能驗證這一觀點。

在正常的Reissue操作中,我們需要向 Address 的錯誤信息)

而攻擊者修改了判斷條件,導致了在CheckTransaction時并不會檢測TX_REISSUE_ASSET,所以能夠在Address的Amount不為0的情況下通過判斷,最終實現增發RVN。
看完代碼后,我們點開這位叫做WindowsCryptoDev的用戶的GitHub主頁

這是個在2020年1月15日新建的賬號,為了偽造身份,起了個WindowsCryptoDev的id,并且同天建了個叫Windows的repo,最后的活動便是在1月16號向Ravencoin提交PR。
而對于這個PR,項目團隊的反饋也能印證我們的猜測。

整個攻擊流程如下:
- 2020年1月15日,攻擊者偽造身份
- 1月16日,攻擊者提交pull request
- 1月16日,當天pull request被合并
- 5月9日,攻擊者開始通過持續制造非法Reissue Asset操作增發RVN,并通過多個平臺轉賣換為其他虛擬貨幣
- 6月29日,
Solus Explorer開發團隊一位程序員發現問題并上報 - 7月3日,
Ravencoin團隊向社區發布緊急更新,攻擊者停止增發RVN - 7月4日,13:26:27 (UTC),
Ravencoin團隊對區塊強制更新了新協議 - 7月5月,
Ravencoin團隊宣布緊急事件結束 - 7月8日,
Ravencoin團隊公布事件
至此,事件結束,最終,攻擊者增發了近3億的RVN。
總結
隨著互聯網時代的發展,開源文化逐漸從小眾文化慢慢走向人們的視野中,人們漸漸開始認為開源社區給項目帶來源源不斷的活力,開源使得人人都可以提交請求、人人都可以提出想法,可以一定層度上提高代碼的質量、增加社區的活躍度,形成一種正反饋,這使開源社區活力無限。
但也因此,無數不懷好意的目光也隨之投向了開源社區,或是因為攻擊者蓄謀已久,抑或是因為貢獻者無心之舉,一些存在問題的代碼被加入到開源項目中,他們有的直接被曝光被發現被修復,也有的甚至還隱藏在核心代碼中深遠著影響著各種依賴開源項目生存著的軟件、硬件安全。
開源有利亦有弊,攻擊者也在滲透著越來越多開發過程中的不同維度,在經歷了這次事件之后,你還能隨意的接受開源項目中的PR嗎?
REF
[1] 三行代碼就賺走 4000w RMB,還能這么玩?
[2] commit
https://github.com/RavenProject/Ravencoin/commit/d23f862a6afc17092ae31b67d96bc2738fe917d2
[3] Solus Explorer - Address: Illegal Supply
https://rvn.cryptoscope.io/address/?address=Illegal%20Supply
[4] Ravencoin — Emergency Update
https://medium.com/@tronblack/ravencoin-emergency-update-dece62255fd9/https://medium.com/@tronblack/ravencoin-emergency-update-dece62255fd9
[5] Ravencoin — Emergency Ended
https://medium.com/@tronblack/ravencoin-emergency-ended-3f3181a0f6d2/https://medium.com/@tronblack/ravencoin-emergency-ended-3f3181a0f6d2
[6] The anatomy of Ravencoin exploit finding
https://medium.com/@cryproscope/the-anatomy-of-ravencoin-exploit-finding-8fa4fe7547a9/https://medium.com/@cryproscope/the-anatomy-of-ravencoin-exploit-finding-8fa4fe7547a9
[7] RavencoinVulnerability — WTF Happened?
https://medium.com/@tronblack/ravencoin-post-vulnerability-fix-fb3a4bd70b7b/https://medium.com/@tronblack/ravencoin-post-vulnerability-fix-fb3a4bd70b7b
本文由 Seebug Paper 發布,如需轉載請注明來源。本文地址:http://www.bjnorthway.com/1275/