The price field in the Listing struct (L56) and the _price parameter in list() (L127) and updatePrice() (L185) are typed as uint32. The maximum uint32 value is 4,294,967,295, which with USDC's 6 decimals equals ~4294.97 USDC. However, the fee calculation function _calculateFees() (L229-236) defines three fee tiers using uint256 thresholds:
| Constant | Line | Value | USDC Equivalent |
|---|---|---|---|
LOW_FEE_THRESHOLD |
L28 | 1000e6 (1,000,000,000) |
1,000 USDC |
MID_FEE_THRESHOLD |
L29 | 10_000e6 (10,000,000,000) |
10,000 USDC |
type(uint32).max |
-- | 4,294,967,295 | ~4,294 USDC |
Since type(uint32).max (4,294,967,295) < MID_FEE_THRESHOLD (10,000,000,000), the listing.price value passed to _calculateFees() at L175 can never exceed MID_FEE_THRESHOLD. This makes the third branch of _calculateFees() at L235 -- the HIGH_FEE_BPS (5%) tier -- permanently unreachable dead code:
The root cause is the type mismatch: the Listing struct stores price as uint32 (L56), and both list() (L127) and updatePrice() (L185) accept uint32 parameters, but the fee thresholds are defined as uint256 with values exceeding uint32 range. When listing.price (uint32) is passed to _calculateFees(uint256) at L175, it is implicitly upcast to uint256, but its value can never exceed 4,294,967,295.
The three constrained locations:
This produces two impacts:
Broken fee structure: The protocol's HIGH_FEE_BPS (500, L26) and MID_FEE_THRESHOLD (10,000e6, L29) are dead code. The MID_FEE tier is also only partially reachable (covers ~1000-4294 USDC instead of the designed 1000-10,000 USDC range).
Capped marketplace: NFTs cannot be listed above ~4294 USDC, preventing high-value sales on the marketplace entirely.
Likelihood:
The uint32 constraint is hardcoded in the Listing struct (L56) and both listing functions (L127, L185) -- it affects 100% of listings
The HIGH_FEE tier is unreachable in every possible scenario -- there is no code path that can trigger the 5% fee
The MID_FEE tier is partially unreachable: prices between ~4295 and 10,000 USDC cannot exist
Impact:
Protocol collects 3% instead of the designed 5% on the highest-value sales -- at the maximum price of ~4294 USDC, the protocol loses ~85.9 USDC in fees per sale (HIGH_FEE would collect ~214.7 USDC vs MID_FEE's ~128.8 USDC)
The marketplace cannot support NFTs priced above ~4294 USDC, severely limiting the protocol's utility for high-value collections
The HIGH_FEE_BPS constant (L26), MID_FEE_THRESHOLD constant (L29), and the third branch of _calculateFees() (L235) are all dead code
Two Foundry tests demonstrate both impacts. Run with forge test --match-contract M03PoCTest -vv:
Change the price type from uint32 to uint256 in the Listing struct and both function parameters. This removes the artificial cap, enables the full fee tier structure, and allows high-value NFT sales.
This fix:
Enables the full fee tier structure: LOW_FEE (1%) up to 1,000 USDC, MID_FEE (3%) up to 10,000 USDC, HIGH_FEE (5%) above 10,000 USDC
Removes the ~4294 USDC price cap, allowing high-value NFT sales
Aligns with _calculateFees() (L229) which already accepts uint256
Is compatible with all existing downstream code: buy() (L148), collectUsdcFromSelling() (L175-176), and events (L18-19) all already use uint256 for price-related values
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.
The contest is complete and the rewards are being distributed.