40,000 USDC
View results
Submission Details
Severity: gas
Valid

Use uint256 instead of enum for state checks

Summary

Instances where a state is checked should use a uint256 instead of the enum values.

Vulnerability Details

Enum values are simple uint's under the hood and there is a gas cost when using enums for state checking rather than simpyl using numbers. Although enums grant readability, states choices are often hardcoded and can be replaced with uint256s instead.

The initial gas report for the normal enum usage can be seen here:

| src/Escrow.sol:Escrow contract | | | | | |
|--------------------------------|-----------------|-------|--------|-------|---------|
| Deployment Cost | Deployment Size | | | | |
| 591897 | 3665 | | | | |
| Function Name | min | avg | median | max | # calls |
| confirmReceipt | 316 | 24518 | 40322 | 40322 | 11 |
| getArbiter | 346 | 346 | 346 | 346 | 2 |
| getArbiterFee | 367 | 367 | 367 | 367 | 1 |
| getBuyer | 258 | 258 | 258 | 258 | 2 |
| getPrice | 284 | 284 | 284 | 284 | 1 |
| getSeller | 368 | 368 | 368 | 368 | 2 |
| getState | 329 | 329 | 329 | 329 | 4 |
| getTokenContract | 214 | 214 | 214 | 214 | 1 |
| initiateDispute | 316 | 17468 | 23603 | 23603 | 11 |
| resolveDispute | 383 | 19753 | 1868 | 62460 | 11 |

Impact

Additional gas charges are given to the user when using enums to check state.

Tools Used

  • VS code

  • Foundry

  • Manual reading

Recommendations

It is recommended to change all usage of the enum to use uint256s. During this audit tests were completed using the smaller value of uint8 (due to the small number of states), however the gas was actually lower when using uint256s due to the way solidity casts the values to uint256 before usage. All instances were not added to relevant links, however upon changing the storage variable value type all other instances must be altered to compile.

Overall, this gave noticable gas savings when it came to creating new escrow's as well as usage of the escrow contract directly as a buyer/seller/disputer. All tests passed as expected without the enum values used for states.

The final gas report can be seen below:

| src/Escrow.sol:Escrow contract | | | | | |
|--------------------------------|-----------------|-------|--------|-------|---------|
| Deployment Cost | Deployment Size | | | | |
| 555459 | 3483 | | | | |
| Function Name | min | avg | median | max | # calls |
| confirmReceipt | 316 | 24484 | 40283 | 40283 | 11 |
| getArbiter | 346 | 346 | 346 | 346 | 2 |
| getArbiterFee | 367 | 367 | 367 | 367 | 1 |
| getBuyer | 258 | 258 | 258 | 258 | 2 |
| getPrice | 284 | 284 | 284 | 284 | 1 |
| getSeller | 368 | 368 | 368 | 368 | 2 |
| getState | 271 | 271 | 271 | 271 | 4 |
| getTokenContract | 214 | 214 | 214 | 214 | 1 |
| initiateDispute | 318 | 17418 | 23551 | 23551 | 11 |
| resolveDispute | 383 | 19717 | 1831 | 62419 | 11 |
| src/EscrowFactory.sol:EscrowFactory contract | | | | | |
|----------------------------------------------|-----------------|--------------------|--------|---------------------|---------|
| Deployment Cost | Deployment Size | | | | |
| 1647339 | 8256 | | | | |
| Function Name | min | avg | median | max | # calls |
| computeEscrowAddress | 10523 | 10523 | 10523 | 10523 | 2 |
| newEscrow | 11832 | 297913115351035703 | 590039 | 8937393460515996962 | 30 |

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.