DeFi协议Akropolis漏洞详解:黑客复现“经典重入攻击”掳走203万DAI
昨天晚间19时50分,DeFi 协议 Akropolis 遭到了黑客攻击。
区块链安全公司 PeckShield(派盾)安全人员迅速定位到问题在于,Akropolis 项目的 SavingsModule 合约在处理用户存储资产时存在某种缺陷,黑客利用此缺陷连续实施了17次重入攻击,导致其 YCurve 和 sUSD 资金池损失了203万枚 DAI。
技术概要:
本次攻击的原因如下:
1)合约没有对用户存储的 Token 进行白名单校验2)关键的 deposit 函数没有对重入攻击的保护
简单而言:黑客利用 Akropolis 项目存在的存储资产校验缺陷,向合约发起连续多次的重入攻击,致使 Akropolis 合约在没有新资产注入的情况下,凭空增发了大量的 pooltokens,进而再利用这些 pooltokens 从 YCurve 和 sUSD 池子中提取 DAI,最终导致项目合约损失了203万枚 DAI。
攻击过程详解:
攻击流程复现:
我们通过分析黑客实施攻击的交易哈希(0xe1f375a47172b5612d96496a4599247049f07c9a7d518929fbe296b0c281e04d)发现,攻击来自于一个恶意的 ERC20 合约地址(0xe2307837524Db8961C4541f943598654240bd62f)
这个恶意合约实现了一个钩子函数,使得函数在 transferFrom() (function signature: 0x23b872dd)被调用的时候会被执行。
攻击者先是调用 SavingsModule.sol (https://github.com/akropolisio/delphi/blob/release-1.0/contracts/modules/savings/SavingsModule.sol#L217-L277) 中的 deposit() 函数,并将自己编写的位于 0xe230 开头的恶意合约作为要存储的代币地址传入。当其恶意代币的 transferFrom() 函数被调用时,其钩子函数会再次调用 deposit() 函数并存入真实的 DAI 资产。
由于 pooltokens 增发的量通过代币 deposit 前后余额的差值得出。所以第二次 deposit 的真实的 DAI 资产会被计算两次用于铸造 pooltokens。第一次是在恶意合约 0xe230 存储的时候,第二次是在 DAI 存储的时候。也就是说,如果第二次存储的时候存入了 25K DAI, 那么由于重入攻击,总的铸造的 pooltokens 将会是双倍,也就是 50K DAI 。
以此类推,黑客总共发起 17次重入攻击并获得了总共 2,030,841.0177个DAI 资产。
值得注意的是,在攻击的最开始,攻击者还使用了 dYdX 的闪贷功能(https://etherscan.io/tx/0xddf8c15880a20efa0f3964207d345ff71fbb9400032b5d33b9346876bd131dc2)。
核心漏洞详解:
接下来,我们分析下存在漏洞的代币存储逻辑。Akropolis 的用户可以将代币存储入Delphi Savings Pools,而资金池会铸造相应的 pooltokens 给用户。核心逻辑在SavingsModule::deposit()(1,944行)。
第一步:攻击者调用 deposit() 函数并提供 _tokens 参数。这个函数在进一步调用 depositToProtocol(_protocol, _tokens, _dnAmounts) 前后会计算代币的余额,并通过代币余额的变化来决定将要铸造的 poolTokens 数目(第1,970行)。而 depositToProtocol() 函数会调用目标代币的 safeTransferFrom()函数来进行代币的转账(第2,004行)。然而 deposit() 函数没有对重入攻击进行检测,也没有检查存入的代币是否为恶意代币;
第二步:在恶意代币的 transferFrom() 函数被调用的时候,触发钩子函数,从而再次调用 deposit() 函数;
第三步:因为第二次调用 deposit() 函数的时候攻击者存入了真正的 DAI 代币使得池子的代币余额发生变化,所以攻击者可以获得资金池铸造的 poolTokens;
第四步:当第二次 deposit() 函数调用结束的时候,代码执行流程将返回第一次存储代币调用 depositToProtocol() 函数的上下文。这个时候,代币余额变化将被再次计算。此时代币余额的变化和第二次调用 deposit() 函数代币余额变化一样。因此攻击者可以再次获得相应数目的 poolTokens。
被盗资产情况:
这次攻击的被盗资产目前被存储在钱包[0x9f26](https://etherscan.io/address/0x9f26ae5cd245bfeeb5926d61497550f79d9c6c1c)中。PeckShield 旗下数字资产追踪平台 CoinHolmes 正在对该地址做全方位监控,并对其资金流向做进一步的锁定分析和追踪,以便协助项目方挽回被盗资产。
위믹스3.0 최초의 DAO ‘원더다오’, 노드 카운슬 파트너 합류
위믹스3.0 최초의 DAO ‘원더다오’, 노드 카운슬 파트너 합류 l 탈중앙화 자율조직 형태로 결성…구성원 모두가 위믹스3.0 운영에 참여 가능l 스마트 컨트랙트 기반 모듈화 ...
[주간톡톡] 양의 탈을 쓴 늑대는 양일까? 늑대일까?
주간톡톡은 한주간의 블록체인 소식을 재구성해 독자들과 재미있게 이야기해보는 코너입니다. 이번주는 페이스북의 스테이블 코인 프로젝트 '디엠(Diem)'에 대해 알아보겠습니다. 그럼 ...
IBM, 블록체인 와인 추적 서비스 '빈어슈어(Assure)' 공개
IBM이 재배지부터 매장까지 와인 공급망을 추적할 수 있는 블록체인 기반 플랫폼을 공개했다.10일(현지시간) 발표에 따르면 IBM은 와인 모니터링 업체 e프로브넌스(eProven...