4、经典案例:Harvest Finance攻击(2020年10月)
2020年10月26日,Harvest Finance被闪电贷攻击,损失约3400万美元。这是我当年追踪过的最有意思的DeFi攻击之一。为什么?因为它不是简单的合约漏洞,而是经济模型层面的博弈。说白了,代码没写错,但业务逻辑被人玩坏了。
4.1 攻击流程详解
攻击者只用了一笔交易就完成了整个攻击。我拆开来看,其实就三步:
- 借出巨额USDC:通过闪电贷从Aave借了数千万USDC
- 操纵Curve池:用借来的USDC在Curve的USDC/USDT池中大量兑换,把池子比例拉偏
- 套利收割:利用Harvest Finance的fUSDC-2池与Curve池之间的价差,反复存取套利
嗯,这里有个关键点——攻击者为什么能反复套利?因为Harvest Finance的定价机制依赖Curve池的实时价格,而Curve池已经被他一手操控了。
核心逻辑:攻击者让Curve池中的USDC变贵,然后以这个虚高的价格向Harvest存入USDC,换出更多的fUSDC份额。等池子恢复后,再赎回套利。
4.2 漏洞分析:Curve池操纵
咱们来深入看看Curve池是怎么被操纵的。Curve的稳定币兑换池用的是StableSwap算法,它的特点是:
- 正常时,1 USDC ≈ 1 USDT,滑点极低
- 但一旦池子严重失衡,价格就会剧烈偏离
攻击者干了什么?他往Curve的USDC/USDT池里一次性注入了大量USDC,导致池子里的USDC占比从50%飙升到90%以上。这时候,1 USDC能换到的USDT就远不止1个了。
// 攻击前的Curve池状态(简化)
USDC: 10,000,000
USDT: 10,000,000
价格: 1 USDC ≈ 1 USDT
// 攻击者注入5000万USDC后
USDC: 60,000,000
USDT: 10,000,000
价格: 1 USDC ≈ 1.2 USDT // 虚高!
我在项目中遇到过类似的问题。当时我们做了一个AMM池,也是依赖外部预言机定价。审计时我就说:“你这个池子如果被大额交易冲击,内部价格会失真,然后被套利机器人盯上。”结果对方没当回事,后来果然出了事。
避坑指南:我曾经以为只要合约代码没bug就安全了,但Harvest Finance告诉我——经济模型的安全比代码安全更难把控。你写的代码完全符合预期,但攻击者利用的是你预期之外的场景。
4.3 教训与反思
这次攻击暴露了三个核心问题:
| 问题 | 具体表现 | 改进方向 |
|---|---|---|
| 定价依赖单一来源 | Harvest直接使用Curve池的瞬时价格 | 引入TWAP(时间加权平均价格) |
| 无滑点保护 | 大额交易没有价格检查 | 设置最大滑点比例 |
| 闪电贷无限制 | 攻击者可以借到任意金额 | 限制单笔交易规模 |
我个人习惯在审计DeFi项目时,会特别关注“价格从哪里来”这个问题。如果答案是“从某个流动性池来”,那我就会追问:这个池子会不会被操纵?操纵成本是多少?
我的经验:判断一个DeFi协议是否安全,可以问三个问题:
- 它的价格来源是否容易被操纵?
- 大额交易是否有保护机制?
- 闪电贷能否被用来攻击它的经济模型?
如果三个答案都是“是”,那这个协议基本就是待宰的羔羊。
你想想看,Harvest Finance的团队其实很优秀,代码质量也不错。但他们低估了闪电贷的破坏力。2020年那会儿,闪电贷攻击还是个新鲜事物,很多人没意识到:一笔交易就能借到几千万美元,然后瞬间完成攻击。
现在回头看,Harvest Finance的教训已经成了DeFi安全领域的经典教材。每次我给别人讲闪电贷攻击,都会拿这个案例开头。因为它足够简单,又足够深刻——不是代码错了,是经济模型错了。
这个流程图你看懂了吗?其实整个攻击就三个步骤,一笔交易。攻击者先借钱,再拉偏池子,最后套利。整个过程不到30秒。
公众号:蓝海资料掘金营,微信deep3321