Closed howlbot-integration[bot] closed 4 months ago
alex-ppg marked the issue as not a duplicate
The Warden demonstrates an interesting problem in the Reallocation
contract's usable tick calculation which will round towards 0
instead of rounding towards negative infinity.
The function is utilized to calculate the next lower and upper ticks that liquidity should be reallocated in, and the values fed to the Reallocation::calculateUsableTick
function utilize a pair's risk parameter configuration and specifically the rangeSize
. This value is simply validated as non-zero by the AddPairLogic
, thereby permitting a non-zero rangeSize
configuration to result in a re-allocation to a single tick position which is something the Predy team does not wish to be possible.
The maximum impact of the vulnerability is a re-allocation being performed across one less tick than expected/configured and will manifest solely when the lower tick is in the negative range but the upper tick is in the positive range.
I appreciate the Warden's due diligence and believe it is an issue that the Sponsor should fix, however, I do not believe its impact can be considered as H or M. It will solely arise for a rangeSize
configuration that is a multiple of tickSpacing / 2
(medium likelihood), and will manifest itself only when the lower tick is negative and the upper tick is positive (low likelihood). The impact will be a suboptimal allocation of funds (medium impact), thereby rendering the overall submission to be a QA (L) risk issue.
alex-ppg changed the severity to QA (Quality Assurance)
alex-ppg marked the issue as grade-c
@alex-ppg's explanation is very clear and reasonable.
Lines of code
https://github.com/code-423n4/2024-05-predy/blob/e96f378007e3dc56b184079f0c0e4fe48a72efaa/src/libraries/Reallocation.sol#L109-L121 https://github.com/code-423n4/2024-05-predy/blob/e96f378007e3dc56b184079f0c0e4fe48a72efaa/src/libraries/Reallocation.sol#L120
Vulnerability details
Issue Description
Reallocation:calculateUsableTick
is responsible for rounding a given_tick
value to the nearest multiple oftickSpacing
. However, the current implementation always rounds down, which can lead to incorrect rounding for negative_tick
values.Code:
Line
result = (result / tickSpacing) * tickSpacing;
is responsible for rounding down the_tick
value to the nearest multiple oftickSpacing
.Example: Let's say the case where
_tick
is -1 andtickSpacing
is 2.Initially,
result
is set to -1. Since -1 is not less thanTickMath.MIN_TICK
or greater thanTickMath.MAX_TICK
, the conditional statements are skipped. The lineresult = (result / tickSpacing) * tickSpacing;
is executed, which becomesresult = (-1 / 2) * 2;
. The integer division-1 / 2
results in 0 (rounding down), and then0 * 2
gives 0.Therefore, the final value of
result
is 0.However the correct nearest multiple of 2 to -1 should be -2, not 0.
Impact
The incorrect rounding behavior can lead to the following issues in the Uniswap V3 pool.
Incorrect pricing: The tick values are used to calculate the price of the trading pair. If the tick values are incorrect, the pricing calculations will also be incorrect, leading to potential losses for liquidity providers and traders. Incorrect liquidity distribution: The tick values are used to determine the liquidity distribution within the pool. If the tick values are incorrect, the liquidity may be distributed incorrectly, leading to potential losses or inefficient use of liquidity. Potential arbitrage opportunities: If the pricing and liquidity distribution are incorrect, it may create arbitrage opportunities for traders, potentially leading to losses for liquidity providers.
Proof of Concept
https://github.com/code-423n4/2024-05-predy/blob/e96f378007e3dc56b184079f0c0e4fe48a72efaa/src/libraries/Reallocation.sol#L120
Tools Used
Vs Code
Recommended Mitigation Steps
The
calculateUsableTick
should be modified to round the_tick
value to the nearest multiple oftickSpacing
, regardless of whether the_tick
value is positive or negative.Assessed type
Math