Platform: Code4rena
Start Date: 11/08/2022
Pot Size: $40,000 USDC
Total HM: 8
Participants: 108
Period: 4 days
Judge: hickuphh3
Total Solo HM: 2
Id: 152
League: ETH
Rank: 99/108
Findings: 1
Award: $20.60
馃専 Selected for report: 0
馃殌 Solo Findings: 0
馃専 Selected for report: Dravee
Also found by: 0x040, 0x1f8b, 0xDjango, 0xHarry, 0xNazgul, 0xSmartContract, 0xbepresent, 0xkatana, Amithuddar, Aymen0909, Bnke0x0, Chom, CodingNameKiki, Deivitto, DevABDee, Diraco, ElKu, Fitraldys, Funen, IllIllI, JC, LeoS, Metatron, MiloTruck, Noah3o6, ReyAdmirado, Rohan16, Rolezn, Saw-mon_and_Natalie, Sm4rty, SpaceCake, TomJ, Tomio, Trabajo_de_mates, Waze, Yiko, __141345__, ajtra, apostle0x01, bobirichman, brgltd, bulej93, c3phas, cRat1st0s, carlitox477, d3e4, durianSausage, erictee, fatherOfBlocks, gerdusx, gogo, hakerbaya, ignacio, jag, joestakey, ladboy233, medikko, mics, newfork01, oyc_109, pfapostol, robee, rvierdiiev, sach1r0, saian, samruna, sikorico, simon135, wagmi, zeesaw, zkhorse, zuhaibmohd
20.6 USDC - $20.60
File Name | SHA-1 Hash |
---|---|
2022-08-foundation/contracts/mixins/shared/MarketFees.sol | cc89c1197e723dc6f7d40d7870f3a95bcae79cc6 |
2022-08-foundation/contracts/libraries/BytesLibrary.sol | 7b56beeacd9fe2f209c7fa4d2845a26b24f9f46e |
2022-08-foundation/contracts/NFTDropCollection.sol | a9ccc8bf45af4dbad6828bc4b8b5524c4e2a1dee |
In Solidity 0.8+, there鈥檚 a default overflow check on unsigned integers.
for (uint256 i = 0; i < creatorShares.length; ++i) {
The code would go from:
for (uint256 i = 0; i < creatorShares.length; ++i) { creatorRev += creatorShares[i]; }
to:
for (uint256 i = 0; i < creatorShares.length; ) { creatorRev += creatorShares[i]; unchecked { ++i; } }
VS Code
If a variable is not set/initialized, it is assumed to have the default value (0
, false
, 0x0
, etc depending on the data type). If you explicitly initialize it with its default value, you are just wasting gas.
for (uint256 i = 0; i < 20; ++i) {
for (uint256 i = 0; i < 4; ++i) {
for (uint256 i = 0; i < creatorRecipients.length; ++i) {
for (uint256 i = 0; i < creatorShares.length; ++i) {
for (uint256 i = 0; i < creatorRecipients.length; ++i) {
Do not initialize variables with default values.
VS Code
!= 0
rather than > 0
for unsigned integers in require()
statementsWhen the optimizer is enabled, gas is wasted by doing a greater-than operation, rather than a not-equals operation inside require()
statements. When using !=,
the optimizer is able to avoid the EQ
, ISZERO
, and associated operations, by relying on the JUMPI
that comes afterwards, which itself checks for zero.
require(_maxTokenId > 0, "NFTDropCollection: `_maxTokenId` must be set");
Use != 0
rather than > 0
for unsigned integers in require()
statements.
VS Code
Less expensive and able to use dynamic information in them.
Use custom errors.
VS Code
#0 - HardlyDifficult
2022-08-18T23:44:15Z
unchecked loop in
getFeesAndRecipients
getFeesAndRecipients
is a read only function not intended to be used on-chain, but as a best practice we will add unchecked there as well.
Don't initialize variables with default values.
Invalid. This optimization technique is no longer applicable with the current version of Solidity.
Use != 0 instead of > 0
Invalid. We tested the recommendation and got the following results:
createNFTDropCollection gas reporter results: using > 0 (current): - 319246 路 319578 路 319361 using != 0 (recommendation): - 319252 路 319584 路 319367 impact: +6 gas
Custom errors
Agree but won't fix at this time. We use these in the market but not in collections. Unfortunately custom errors are still not as good of an experience for users (e.g. on etherscan). We used them in the market originally because we were nearing the max contract size limit and this was a good way to reduce the bytecode. We'll consider this in the future as tooling continues to improve.