最近发生的Curve池漏洞跟我们之前见过的加密货币黑客事件不太一样,因为这次问题不是直接与智能合约本身的漏洞有关,而是跟使用的编程语言Vyper的底层编译器有关。

Vyper是一个面向智能合约的编程语言,采用了类似Python的风格,专门用于与以太坊虚拟机(EVM)交互。

这次漏洞的影响非常严重,每天都有新闻报道着数额庞大的损失。目前情况似乎已经得到了控制,但在此之前,黑客盗取了超过7000万美元的资金。据LlamaRisk的事后评估,一些DeFi项目的池子也遭到黑客攻击,包括PEGD的pETH/ETH池子损失了1100万美元,Metronome的msETH/ETH池子损失了340万美元,Alchemix的alETH/ETH池子损失了2260万美元,而Curve DAO池子损失了大约2470万美元。

这次漏洞被称为重入错误,它主要出现在Vyper编程语言的一些版本上,特别是v0.2.15、v0.2.16和v0.3.0。所以使用这些特定版本的Vyper的项目都可能成为攻击的目标。

什么是重入(reentrancy)? 

了理解这次漏洞为什么会发生,我们先来了解一下什么是重入以及它是如何工作的。

所谓重入,就是指一个函数在执行的过程中,可以被中断,并且在之前的调用完成之前,安全地再次被调用。这种机制在硬件中断处理和递归等应用中经常被使用。

为了让一个函数成为可重入的,它需要满足一些条件:

首先,它不能使用全局和静态数据。这是一种约定,意思是在函数执行时,不要依赖于全局的数据或者静态变量。因为如果一个函数在执行过程中被中断,然后再次被调用,全局和静态数据可能会被破坏或者丢失信息。

其次,它不能修改自己的代码。无论函数何时被中断,都应该能够以相同的方式继续执行。如果函数在执行过程中修改了自己的代码,那么再次调用时可能会出现错误。

最后,它不能调用其他不是可重入的函数。也就是说,在一个可重入函数中,不应该调用其他可能不是可重入的函数。因为如果这样做,就可能造成不可预测的结果,导致程序崩溃或者出现错误。

太难懂了,咱们就不细讲了

如何被利用的?

我们来解释一下重入攻击是如何导致资金被盗和在Curve攻击中损失7000万美元的。

首先,我们知道重入攻击是指一个恶意合约反复调用智能合约中的某个函数的方法。而在Curve攻击中,这个函数是用来提现用户在池中的流动性的。这个函数有一个漏洞,就是在更新金额之前没有做足够的检查。

让我们看看攻击的具体流程:

  1. 假设一个易受攻击的智能合约有10个以太币。

  2. 攻击者调用存款函数,并存入1个以太币。

  3. 攻击者接着调用提现函数,准备提取1个以太币。在这个函数里,它会检查攻击者的账户中是否有1个以太币。

  4. 然而,在将1个以太币转移到攻击者的账户之前,这个函数没有更新合约中的余额。这意味着合约仍然认为有10个以太币在里面。

  5. 攻击者再次调用提现函数(重新入场),再次准备提取1个以太币。

  6. 因为合约仍然认为有10个以太币在里面,所以它会再次给攻击者转移1个以太币。

  7. 这个过程会一直重复,直到合约中没有更多的流动性为止。

通过这种方式,攻击者可以反复调用提现函数,几乎将合约中所有的流动性都转移到自己的账户里,导致合约中的资金被盗。

这种漏洞对于攻击者来说非常有利,因为在合约中的金额并没有实时更新,导致攻击者可以不断地重复攻击,直到合约中没有可提现的资金为止。#Crv