Skip to content

Commit b4b4759

Browse files
authored
Merge pull request #257 from crytic/dev-cheat-codes
Added discussion on how and when to use cheat codes
2 parents 77dc85c + d9b8cb0 commit b4b4759

File tree

3 files changed

+53
-0
lines changed

3 files changed

+53
-0
lines changed

SUMMARY.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,7 @@
8282
- [How to detect high gas consumption](./program-analysis/echidna/advanced/finding-transactions-with-high-gas-consumption.md)
8383
- [How to perform smart contract fuzzing at a large scale](./program-analysis/echidna/advanced/smart-contract-fuzzing-at-scale.md)
8484
- [How to test bytecode-only contracts](./program-analysis/echidna/advanced/testing-bytecode.md)
85+
- [How and when to use cheat codes](program-analysis/echidna/advanced/on-using-cheat-codes.md)
8586
- [How to use hevm cheats to test permit](./program-analysis/echidna/advanced/hevm-cheats-to-test-permit.md)
8687
- [How to seed Echidna with unit tests](./program-analysis/echidna/advanced/end-to-end-testing.md)
8788
- [Understanding and using `allContracts`](./program-analysis/echidna/advanced/using-all-contracts.md)

program-analysis/echidna/advanced/README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
- [How to Perform Large-scale Smart Contract Fuzzing](./smart-contract-fuzzing-at-scale.md): Explore how to use Echidna for long fuzzing campaigns on complex smart contracts.
77
- [How to Test a Library](https://blog.trailofbits.com/2020/08/17/using-echidna-to-test-a-smart-contract-library/): Learn about using Echidna to test the Set Protocol library (blog post).
88
- [How to Test Bytecode-only Contracts](./testing-bytecode.md): Learn how to fuzz contracts without source code or perform differential fuzzing between Solidity and Vyper.
9+
- [How and when to use cheat codes](./on-using-cheat-codes.md): How to use hevm cheat codes in general
910
- [How to Use Hevm Cheats to Test Permit](./hevm-cheats-to-test-permit.md): Find out how to test code that relies on ecrecover signatures by using hevm cheat codes.
1011
- [How to Seed Echidna with Unit Tests](./end-to-end-testing.md): Discover how to use existing unit tests to seed Echidna.
1112
- [Understanding and Using `allContracts`](./using-all-contracts.md): Learn what `allContracts` testing is and how to utilize it effectively.
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
# How and when to use cheat codes
2+
3+
**Table of contents:**
4+
5+
- [How and when to use cheat codes](#how-and-when-to-use-cheat-codes)
6+
- [Introduction](#introduction)
7+
- [Cheat codes available in Echidna](#cheat-codes-available-in-echidna)
8+
- [Advice on the use of cheat codes](#advice-on-the-use-of-cheat-codes)
9+
10+
## Introduction
11+
12+
When testing smart contracts in Solidity itself, it can be helpful to use cheat codes in order to overcome some of the limitations of the EVM/Solidity.
13+
Cheat codes are special functions that allow to change the state of the EVM in ways that are not posible in production. These were introduced by Dapptools in hevm and adopted (and expanded) in other projects such as Foundry.
14+
15+
## Cheat codes available in Echidna
16+
17+
Echidna supports all cheat codes that are available in [hevm](https://github.com/ethereum/hevm). These are documented here: https://hevm.dev/controlling-the-unit-testing-environment.html#cheat-codes.
18+
If a new cheat code is added in the future, Echidna only needs to update the hevm version and everything should work out of the box.
19+
20+
As an example, the `prank` cheat code is able to set the `msg.sender` address in the context of the next external call:
21+
22+
```solidity
23+
interface IHevm {
24+
function prank(address) external;
25+
}
26+
27+
contract TestPrank {
28+
address constant HEVM_ADDRESS = 0x7109709ECfa91a80626fF3989D68f67F5b1DD12D;
29+
IHevm hevm = IHevm(HEVM_ADDRESS);
30+
Contract c = ...
31+
32+
function prankContract() public payable {
33+
hevm.prank(address(0x42424242);
34+
c.f(); // `c` will be called with `msg.sender = 0x42424242`
35+
}
36+
}
37+
```
38+
39+
A specific example on the use of `sign` cheat code is available [here in our documentation](hevm-cheats-to-test-permit.md).
40+
41+
## Risks of cheat codes
42+
43+
While we provide support for the use of cheat codes, these should be used responsibly. Consider that:
44+
45+
- Cheat codes can break certain assumptions in Solidity. For example, the compiler assumes that `block.number` is constant during a transaction. There are [reports of the optimizer interfering with (re)computation of the `block.number` or `block.timestamp`](https://github.com/ethereum/solidity/issues/12963#issuecomment-1110162425), which can generate incorrect tests when using cheat codes.
46+
47+
- Cheat codes can introduce false positives on the testing. For instance, using `prank` to simulate calls from a contract can allow transactions that are not possible in the blockchain.
48+
49+
- Using too many cheat codes:
50+
- can be confusing or error-prone. Certain cheat code like `prank` allow to change caller in the next external call: It can be difficult to follow, in particular if it is used in internal functions or modifiers.
51+
- will create a dependency of your code with the particular tool or cheat code implementation: It can cause produce migrations to other tools or reusing the test code to be more difficult than expected.

0 commit comments

Comments
 (0)