Platform: Code4rena
Start Date: 06/09/2022
Pot Size: $90,000 USDC
Total HM: 33
Participants: 168
Period: 9 days
Judge: GalloDaSballo
Total Solo HM: 10
Id: 157
League: ETH
Rank: 156/168
Findings: 1
Award: $45.41
🌟 Selected for report: 0
🚀 Solo Findings: 0
🌟 Selected for report: pfapostol
Also found by: 0x1f8b, 0x4non, 0x5rings, 0xA5DF, 0xSmartContract, 0xc0ffEE, 0xkatana, Aymen0909, Bnke0x0, CertoraInc, Chandr, CodingNameKiki, Cr4ckM3, Deivitto, DimSon, Franfran, JAGADESH, JC, Jeiwan, Lambda, LeoS, Matin, Metatron, Migue, MiloTruck, PPrieditis, PaludoX0, R2, RaymondFam, Respx, ReyAdmirado, Rolezn, Saintcode_, Samatak, SnowMan, StevenL, Tointer, TomJ, Tomo, WatchDogs, Waze, _Adam, __141345__, ajtra, asutorufos, ballx, brgltd, bulej93, c3phas, ch0bu, dharma09, djxploit, durianSausage, easy_peasy, fatherOfBlocks, gianganhnguyen, gogo, imare, leosathya, lucacez, martin, oyc_109, pauliax, peiw, prasantgupta52, ret2basic, rfa, robee, sikorico, simon135, tofunmi, volky, wagmi, zishansami
45.4138 USDC - $45.41
Solidity does not recognize null as a value, so uint variables are initialized to zero. Setting a uint variable to zero is redundant and can waste gas.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/treasury/Treasury.sol#L162 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L119 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L133 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L189 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L229
Remove the redundant zero initialization
uint256 i;
instead of uint256 i = 0;
Using > 0
uses slightly more gas than using != 0
. Use != 0
when comparing uint variables to zero, which cannot hold values below zero
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/token/ERC721Votes.sol#L203 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Address.sol#L50 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/ERC1967Upgrade.sol#L61
Replace > 0
with != 0
to save gas
Using a prefix increment (++i) instead of a postfix increment (i++) saves gas for each loop cycle and so can have a big gas impact when the loop executes on a large number of elements.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L91 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L154 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/token/ERC721Votes.sol#L207 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/token/ERC721Votes.sol#L222
Use prefix not postfix to increment in a loop
For loops that use i++ do not need to use safemath for this operation because the loop would run out of gas long before this point. Making this addition operation unsafe using unchecked saves gas.
Sample code to make the for loop increment unsafe
for (uint i = 0; i < length; i = unchecked_inc(i)) { // do something that doesn't change the value of i } function unchecked_inc(uint i) returns (uint) { unchecked { return i + 1; } }
Idea borrowed from https://gist.github.com/hrkrshnn/ee8fabd532058307229d65dcd5836ddc#the-increment-in-for-loop-post-condition-can-be-made-unchecked
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/treasury/Treasury.sol#L162 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L119 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L133 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L189 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L229 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L80 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L108 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L132 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L261
Make the increment in for loops unsafe to save gas
Comparing a value to zero can be done using the iszero
EVM opcode. This can save gas
Source from t11s https://twitter.com/transmissions11/status/1474465495243898885
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L135 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L278 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L418 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L445 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L100 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L222 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L85 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L175 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L248 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/token/ERC721Votes.sol#L67
Use the assembly iszero
evm opcode to compare values to zero
Identifying a function as payable saves gas. Functions that have a modifier like onlyOwner cannot be called by normal users and will not mistakenly receive ETH. These functions can be payable to save gas.
There are many functions that have the onlyOwner modifier in the contracts. Some examples are https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/treasury/Treasury.sol#L180 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L564 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L572 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L580 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L588 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L596 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L605 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L618 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L95 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L347 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L355 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L363 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L376 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L244 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L263 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L307 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L315 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L323 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L331 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L374 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Ownable.sol#L63 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Ownable.sol#L71 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Ownable.sol#L87 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L187 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L196 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L209
Add payable to these functions for gas savings
Identifying a constructor as payable saves gas. Constructors should only be called by the admin or deployer and should not mistakenly receive ETH. Constructors can be payable to save gas.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/treasury/Treasury.sol#L32 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L41 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/MetadataRenderer.sol#L32 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/Token.sol#L30 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L39 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/ERC1967Proxy.sol#L21 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L55
Add payable to these functions for gas savings
An internal function can save gas vs. a modifier. A modifier inlines the code of the original function but an internal function does not.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Initializable.sol#L27 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Initializable.sol#L33 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Initializable.sol#L55 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Ownable.sol#L28 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Ownable.sol#L34 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/ReentrancyGuard.sol#L39 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Pausable.sol#L22 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Pausable.sol#L28 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/UUPS.sol#L25 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/UUPS.sol#L32
Use internal functions in place of modifiers to save gas.
Booleans are more expensive than uint256 or any type that takes up a full word because each write operation emits an extra SLOAD to first read the slot's contents, replace the bits taken up by the boolean, and then write back. This is the compiler's defense against contract upgrades and pointer aliasing, and it cannot be disabled.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/types/GovernorTypesV1.sol#L52 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/types/GovernorTypesV1.sol#L53 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/types/GovernorTypesV1.sol#L54 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/token/metadata/types/MetadataRendererTypesV1.sol#L11 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L136 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/Auction.sol#L349 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/auction/types/AuctionTypesV1.sol#L35 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Initializable.sol#L20 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/utils/Pausable.sol#L15 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/ERC1967Upgrade.sol#L36 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/proxy/ERC1967Upgrade.sol#L57
Replace bool variables with uints
When multiply or dividing by a power of two, it is cheaper to bitshift than to use standard math operations.
There is a divide by 2 operation on these lines https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/lib/token/ERC721Votes.sol#L95
Bitshift right by one bit instead of dividing by 2 to save gas
Many constant variables are public, but changing the visibility of these variables to private or internal can save gas.
Locations where this was found include https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/governance/governor/Governor.sol#L27 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L25 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L28 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L31 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L34 https://github.com/code-423n4/2022-09-nouns-builder/tree/main/src/manager/Manager.sol#L37
Declare some public variables as private or internal to save gas.
Example: change this line
bytes32 public constant VOTE_TYPEHASH = keccak256("Vote(address voter,uint256 proposalId,uint256 support,uint256 nonce,uint256 deadline)");
to this line
bytes32 internal constant VOTE_TYPEHASH = keccak256("Vote(address voter,uint256 proposalId,uint256 support,uint256 nonce,uint256 deadline)");
The contracts are all written entirely in solidity. Writing contracts with vyper instead of solidity can save gas.
Source https://twitter.com/eiber_david/status/1515737811881807876 doggo demonstrates https://twitter.com/fubuloubu/status/1528179581974417414?t=-hcq_26JFDaHdAQZ-wYxCA&s=19
Write some or all of the contracts in vyper to save gas
#0 - GalloDaSballo
2022-09-26T14:58:55Z
100 gas, mostly noise