paint-brush
模糊测试:通过随机输入进行智能合约测试经过@alvinslee
1,290 讀數
1,290 讀數

模糊测试:通过随机输入进行智能合约测试

经过 Alvin Lee5m2023/04/24
Read on Terminal Reader

太長; 讀書

模糊测试是一种用一堆随机输入轰炸您的代码以查看会发生什么的方法。这是一种快速、高效、强力的方法来测试您可能没有想到的边缘案例和场景。 Diligence Fuzzing 提供 10 小时的免费 fuzzing 测试。
featured image - 模糊测试:通过随机输入进行智能合约测试
Alvin Lee HackerNoon profile picture
0-item
1-item

测试智能合约非常重要。为什么?智能合约在生产、公共黑客目标中通常是不可变的,并且通常涉及重大的财务影响。短篇小说?使用智能合约,您不想搞砸。您需要进行大量测试、经常测试和彻底测试。智能合约测试涉及所有常见的问题——单元测试、集成测试、自动化测试——但也强烈推荐模糊测试——一种用一堆随机输入轰炸你的代码以查看会发生什么的方法。


让我们来看看究竟什么是模糊测试作为一种测试方法,以及如何使用 ConsenSys Diligence Fuzzing等工具轻松地将其包含在软件测试工作流程中。我们将使用示例 defi 智能联系人浏览教程,看看它是如何完成的。


什么是模糊测试,我为什么要使用它?

模糊测试(或模糊测试)涉及针对智能合约发送数百万个无效、意外和(半)随机数据,以引起意外行为并检测漏洞。这是一种快速、高效、强力的方法来测试您可能没有想到的边缘案例和场景。它补充了您的其他测试流程和审核。


模糊测试在传统的全栈开发中已经存在了一段时间,但是现在出现了一类新的工具,可以将模糊测试应用于 web3 中的智能合约测试。一些模糊测试工具包括开源EchidnaMythX


然而,在本文中,我将深入探讨Diligence Fuzzing ,它提供模糊测试服务——一种非常酷且简单的模糊测试方法。


要使用 Diligence Fuzzing,您可以使用Scribble注释您的智能合约。基本上,您在代码中使用 Scribble 注释来告诉模糊器该函数期望的输出类型。


它看起来像这样:


 /// #invariant {:msg "balances are in sync"} unchecked_sum(_balances) == _totalSupply;


您可以从提交智能合约代码的 Web UI 调用模糊器。您点击运行,大约 10 分钟后,您会收到一份报告,其中包含发现的问题、问题位置、覆盖率百分比等。


这是检查某些边缘情况的简单而强大的方法。

测试 DeFi 智能合约

假设我们有一个新的 DeFi 协议和我们想要推出的相应代币。 DeFi 是前沿金融,写起来很有趣,关键是我们没有任何错误。 DeFi 智能合约通常涉及数百万(或更多)用户资金。因此,我们希望确保尽可能彻底地测试(和审计)我们的智能合约。


重要说明:此代码中有漏洞是故意的!这样我们就可以展示模糊测试如何捕捉这些错误。请不要将此代码用于任何用途。


让我们开始吧。


使用 Diligence Fuzzing (FaaS) 的示例

第 1 步:设置 Diligence 帐户。

首先,我们需要我们的 Diligence 帐户。在Diligence注册。您可以免费获得 10 小时的模糊测试时间来试用。

第 2 步:创建新的 API 密钥。

单击右上角的帐户名称,单击“创建新的 API 密钥”,然后为其命名。这个 API 密钥允许我们连接到 FaaS。





第 3 步:设置本地环境。

克隆以下存储库:

https://github.com/ConsenSys/scribble-exercise-1.git


从命令行导航到存储库文件夹,该文件夹现在将成为您的项目根文件夹。如果您的机器需要,请激活 Python venv。然后,运行以下命令来安装项目依赖项:


 $ npm i -g eth-scribble ganache truffle $ pip3 install diligence-fuzzing

第 4 步:输入您的 API 密钥。

编辑.fuzz.yml文件以使用您的 Diligence 帐户 API 密钥作为 key 的值。

您生成的文件应如下所示:


 .fuzz.yml fuzz: # Tell the CLI where to find the compiled contracts and compilation artifacts build_directory: build/contracts ... campaign_name_prefix: "ERC20 campaign" # Point to your ganache node which holds the seed rpc_url: "http://localhost:8545" key: "DILIGENCE API KEY GOES HERE" ...

第 5 步:编写并注释您的合同。

现在让我们在contracts/vulnerableERC20.sol查看我们的智能合约。在这里,我们的新 DeFi 协议有一个易受攻击的代币(正如它的名字!)。我们显然需要尽可能多地测试它。因此,让我们使用模糊器希望捕获的 Scribble 添加检查。


在合约定义之上,添加:


 /// #invariant "balances are in sync" unchecked_sum(_balances) == _totalSupply;


在传递函数之上,添加:


 /// #if_succeeds msg.sender != _to ==> _balances[_to] == old(_balances[_to]) + _value; /// #if_succeeds msg.sender != _to ==> _balances[msg.sender] == old(_balances[msg.sender]) - _value; /// #if_succeeds msg.sender == _to ==> _balances[msg.sender] == old(_balances[_to]); /// #if_succeeds old(_balances[msg.sender]) >= _value;


所以现在让我们看看模糊测试器是否会捕捉到一些东西。请注意我们添加到合同中的注释,以帮助测试人员了解我们期望发生的事情。请注意,在配置中,测试器设置为最多运行 10 分钟,因此它可能无法捕获所有内容。

第 6 步:四处模糊。

现在我们准备好测试了!在项目根文件夹中,运行make fuzz以调用 make 文件,该文件将编译、构建并将所有内容发送到 FaaS。

第 7 步:查看结果。

返回您的仪表板,您应该会看到类似于下面的内容。等待几秒钟,让活动开始。



生成完成后,您应该会看到类似于下图的内容:

我们甚至可以看到代码覆盖率!



几分钟后,我们看到失败!


单击属性,我们会看到任何违规行为。是的,我们有一个错误!单击行位置可查看我们潜在代码漏洞的详细信息。



我们就到此为止,但如果让模糊器继续运行,它可能会找到更多!


结论

模糊测试可能是软件开发和测试过程中的关键步骤。它可以帮助您识别否则可能会被忽视的潜在漏洞。通过使用它,您开始认识和理解常见的陷阱和挑战。利用Diligence Fuzzing等工具,编写更好的智能合约,成为更好的开发人员!