The getUserDeposits function in the PerpetualVault contract uses a uint8 type for its loop counter while iterating over a user's deposits. Since uint8 can only hold values up to 255, if a single user accumulates more than 255 deposits, the function will enter an infinite loop due to counter overflow, causing transactions to fail with out-of-gas errors.
In the getUserDeposits function:
The vulnerability stems from:
Using uint8 for the loop counter i, which can only represent values from 0 to 255
Comparing this counter against length, which is a uint256 that could be larger than 255
Incrementing the counter inside an unchecked block, which bypasses Solidity's default overflow checks
When i reaches 255 and is incremented, it will overflow to 0 without any error, creating an infinite loop
When a user has more than 255 deposits, the loop will:
Iterate through deposits 0-255 normally
When attempting to increment i from 255 to 256, it will overflow to 0
Since 0 < length, the loop will continue and process deposit 0 again
This creates an infinite loop, eventually causing an out-of-gas error
Users who accumulate more than 255 deposits will be unable to retrieve their complete deposit history
The function will always revert with an out-of-gas error for these users
This blocks access to critical vault functionality for long-term power users
Front-end interfaces using this function will break for affected users
The issue may affect institutional users or automated strategies that make frequent deposits
Since deposits accumulate over time, this creates a ticking time bomb where users eventually lose access
If any outer systems rely on that function it will be DoS-ed for them too
Manual code review
Change the type of the loop counter to match the type of the length variable:
This ensures that the loop counter can handle the same range of values as the length variable, preventing the potential overflow and infinite loop, regardless of how many deposits a user has accumulated.
Please read the CodeHawks documentation to know which submissions are valid. If you disagree, provide a coded PoC and explain the real likelihood and the detailed impact on the mainnet without any supposition (if, it could, etc) to prove your point.
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.