Potential for Undetected Unfavorable Trade Outcomes in GnosisTrade's settle function
Vulnerability Details
The GnosisTrade contract is designed to execute trades using the Gnosis EasyAuction mechanism. The settle function finalizes the trade and includes a mechanism to check if the trade outcome meets the expected worst-case price.
The issue lies in how the clearing price is calculated and compared to the worst-case price. The function uses adjusted values for sold and bought amounts, which could potentially mask unfavorable trade outcomes in certain scenarios.
Code snippet
function settle()
external
stateTransition(TradeStatus.OPEN, TradeStatus.CLOSED)
returns (uint256 soldAmt, uint256 boughtAmt)
{
// ...
// Check clearing prices
if (sellBal < initBal) {
soldAmt = initBal - sellBal;
// Gnosis rounds defensively in the buy token; we should not consider it a violation
uint256 adjustedSoldAmt = Math.max(soldAmt, 1);
uint256 adjustedBuyAmt = boughtAmt + 1;
// D27{buyTok/sellTok}
uint192 clearingPrice = shiftl_toFix(adjustedBuyAmt, 9).divu(adjustedSoldAmt, FLOOR);
if (clearingPrice.lt(worstCasePrice)) broker.reportViolation();
}
}
Impact
Possible Failure to Detect Unfavorable Trades: In certain edge cases, particularly with small trade amounts, the adjustments made to soldAmt and boughtAmt could prevent the detection of trades that actually performed worse than the worst-case price.
False Sense of Security: Users and the system may believe that all unfavorable trades are being caught, when in reality, some might slip through due to these adjustments.
Scenario
Let's say the worst-case price is set to 1 buy token per 1 sell token.
The auction concludes with a slightly unfavorable outcome: 99 sell tokens for 98 buy tokens.
In the settle function:
soldAmt = 99
boughtAmt = 98
adjustedSoldAmt = max(99, 1) = 99
adjustedBuyAmt = 98 + 1 = 99
The calculated clearingPrice becomes 99/99 = 1, which is not less than the worst-case price.
No violation is reported, even though the actual trade was unfavorable.
Mitigation
Consider removing or refining the adjustments made to soldAmt and boughtAmt.
Implement a more precise comparison that accounts for the actual amounts without adjustments.
Add additional checks or a tolerance factor to catch edge cases where the current mechanism might fail.
Lines of code
https://github.com/code-423n4/2024-07-reserve/blob/3f133997e186465f4904553b0f8e86ecb7bbacbf/contracts/plugins/trading/GnosisTrade.sol#L175
Vulnerability details
Potential for Undetected Unfavorable Trade Outcomes in GnosisTrade's
settle
functionVulnerability Details
The GnosisTrade contract is designed to execute trades using the Gnosis EasyAuction mechanism. The
settle
function finalizes the trade and includes a mechanism to check if the trade outcome meets the expected worst-case price.The issue lies in how the clearing price is calculated and compared to the worst-case price. The function uses adjusted values for sold and bought amounts, which could potentially mask unfavorable trade outcomes in certain scenarios.
Code snippet
Impact
soldAmt
andboughtAmt
could prevent the detection of trades that actually performed worse than the worst-case price.Scenario
settle
function:soldAmt
= 99boughtAmt
= 98adjustedSoldAmt
= max(99, 1) = 99adjustedBuyAmt
= 98 + 1 = 99clearingPrice
becomes 99/99 = 1, which is not less than the worst-case price.Mitigation
soldAmt
andboughtAmt
.Assessed type
Context