波場假幣攻擊全過程:BTTBank理財合約遭駭客假BTT攻擊

買賣虛擬貨幣
04月11日凌晨00:17,PeckShield態勢感知平臺監測到TCX1Cay… 開頭的駭客,建立了名為 BTTx, token id 為  1002278 的 TRC10 token,並於凌晨 00:25 至 01:00 之間向多個地址轉入 4,000 萬個 BTTx 代幣,這多個地址對 TXHFhq… 開頭的 BTTBank 理財類合約實施攻擊。BTTBank 專案介紹BTTBank 又名 TronBank BTT, 是屬於 TronBank 旗下的一款專屬於 BitTorrent (BTT) - The token that will enable blockchain mass adoption BTT token 的投資產品,根據官網 TronBank 介紹:TronBank BTT 的智慧合約將為您產生每天 3.6 - 6.6%的投資收益(取決於你購買的產品計劃),自動發放到你的收益餘額中。舉例,購買 4.6% 收益計劃,21 天你即可獲得超過 100% 收益。收益每秒都會計算,你甚至每秒都可以提取收益或重新投資。當您重新投資收益時,投資金額會增加,可以更快的獲得更多收益。

其產品介面如下(由於當前 BTTBank 在維護中,主站無法開啟,援引 TronBank 明星產品 TRX 的投資圖片,詳見 TronBank):

其理財過程大致如下:

1. 使用者根據收益率和投資期限購買相應的理財產品;
2. 投資期限到期之後,使用者提現理財產品到自己的錢包

使用上,和當前的各類 P2P 理財產品類似,使用者的使用門檻僅在於一個 TRON 錢包,但從產品收益率來看,這個資產回報率還是相當可觀的。

攻擊回溯

攻擊事件簡述

去年年底,波場孫老闆發起 12 號提議,即符合波場 TRC10 規範的 Native token 的名字將不再唯一,涉及到 TRC10 token 的轉賬等操作將使用 ID 來代替。這使得波場建立 token 的流程變得簡單易上手,然而卻帶來一個潛在的威脅,一旦合約疏於檢查  token id 的匹配性,就會存在假幣攻擊的可能。簡而言之,本次 BTTBank 遭受攻擊正是因為缺乏  token id 的一致性驗證造成的。

背景知識

TRON 中的 token 分為幾種規範:

· TRX
· TRC20
· TRC10

其中,TRX 為 TRON 的平臺幣,類似於 Ethereum 中的 ETH。

而  TRC20 是與 Ethereum ERC20 相容的 token,實質是一種可程式設計的智慧合約,由使用者透過智慧合約建立 token 之後,其 token 的轉賬、傳送等操作均在智慧合約內部完成,對於一般的小白使用者來說,ERC20/TRC20 使用過於複雜,不便於上手使用。

故此,TRON 中引入了 TRC10 token, 這是一種可以由使用者直接操控的 token,每一個自然使用者支付 1024 TRX 便可建立一個 TRC10 token,同時一個使用者只能建立一個 TRC10 token。每一個 TRC10 token 在建立之後,由系統分配一個唯一 ID(即 token id),這是一個從 1,000,001 開始往後自增的整數,一個 tokenId 標識一個唯一的 token,當前 TRON 平臺上共有 1850+(2019-04-12)個 TRC10。

為了提高 TRC10 的流動性和使用價值,TRON 平臺在  Odyssey 3.2 版本之後,使能了在智慧合約內部轉賬 TRC10 token 的功能,參考 TRC10 Transfer in Smart Contracts, 其示例程式碼如下所示:

上述程式碼簡單解釋如下:

1. transferTokenTest() 介面內部用於轉賬 TRC10 token,介面呼叫方可以透過 address.transferToken(uint256 tokenValue, trcToken tokenId) 往 address 轉賬數量為 tokenValue 的  token id 為 token id 的 TRC10 token;

2. msgTokenValueAndTokenIdTest() 介面表明,呼叫者可以直接在傳送的 message 中加入 token id 和 tokenvalue 欄位,這也說明了 TRC10 是 TRON 平臺上的一等公民,屬於內建型別,與 TRC20 透過函式引數的形式來表徵 token 價值是完全不同的;

3. getTokenBalanceTest() 透過 token id 獲取賬號的餘額。

由此可知,TRC10 token 可以在智慧合約內部透過 token id 完成轉賬,TRC10 token 作為價值承載者,在智慧合約內部即反映在 token id 的差異上。

因此,合約開發者在處理 TRC10 轉賬相關邏輯時,需要特別注意 token Id 的有效性和真實性。

攻擊事件

PeckShield 安全人員在分析 BTTBank 合約時,發現其合約原始碼實現中存在致命漏洞,可導致專案方資金受損。

下圖為駭客攻擊的原過程:

1. 駭客先行建立一個名為 BTTx 的 TRC10 token;
2. 駭客往一批自己控制的賬號中轉入 4,000 萬個 BTTx token;
3. 透過控制的賬號往 BTTBank 合約發起數次攻擊;
4. 最後順序將 BTT 提取到控制的賬號中。

下文從 BTTBank 投資及贖回的過程還原本次 BTT 假幣攻擊的全過程。

投資

投資的核心程式碼如下:

public 介面的 invest( ) 提取 msg.tokenvalue ,並呼叫 private 的 _invest( ) 函式完成投資的過程,_invest( ) 內部計算並儲存使用者這一次的投資數量、時間等資訊到合約的內部資產賬單上。值得注意的是,這裡 invest( ) 只提取了 msg.tokenvalue,這裡並沒有提取 msg.tokenid,也沒有驗證 msg.tokenid是否屬於 BTT Token 的 token id(為 1002000)。

前面我們提到 BTTBank 是一款投資理財類 DApp,使用者存入 BTT token,資產到期之後,再贖回投資的 BTT 和對應的利息,在這裡並沒有檢查是否是真正的 BTT,也就是不論你投資的阿貓阿狗幣,都被認為是 BTT token。

提現

提現的核心程式碼如下:

贖回的過程比較簡單,先從合約的內部投資賬單上計算使用者已經到期的投資金額,並將這一部分投資金額轉回給使用者,注意:msg.sender.transferToken(withdrawalAmount, BTT_ID) 中是固定的 BTT_ID 即 1002000.

至此,使用者投入 BTT,收穫 BTT;而駭客投入 BTTx, 收穫 BTT,一個完美的『狸貓換太子』過程。

防禦策略

PeckShield 安全人員在此提醒廣大開發者,雖然 TRC10/TRC20 都是 token, 但兩者在 TRON 平臺上有著本質的差異性,若要在智慧合約內部轉賬 TRC10,一定要檢查所轉移的 TRC10 對應的 token id 是否為預期值。針對上例,可將投資程式碼增強如下:

另外,PeckShield 安全人員根據上述的程式碼樣式分析 TRON 平臺上其它類 BTTBank 合約時,也發現了相似的問題。在此,PeckShield 安全人員提醒在進行智慧合約開發的時候,雖然複用現有程式碼可能會帶來開發功能上面的便利,但也須注意可能帶來的安全風險。

免責聲明:

  1. 本文版權歸原作者所有,僅代表作者本人觀點,不代表鏈報觀點或立場。
  2. 如發現文章、圖片等侵權行爲,侵權責任將由作者本人承擔。
  3. 鏈報僅提供相關項目信息,不構成任何投資建議

推荐阅读

;