HardhatDeFi
15,000 USDC
View results
Submission Details
Severity: high
Invalid

Unvalidated Aave Withdrawal Returns Allow Silent Partial Yield Claims

Description

The _claimYield function in the smart contract accepts the returned amount from Aave's withdraw function without validation against the expected withdrawal amount. This could lead to silent failures where less tokens are withdrawn than requested, potentially causing accounting inconsistencies and loss of funds.

Impact

  • Users may receive fewer tokens than they should without any reversion

  • Incorrect event emissions could mislead monitoring systems and users

  • Potential accounting discrepancies in the protocol

  • Risk of financial loss if integrated systems rely on event data

https://github.com/Cyfrin/2025-01-diva/blob/main/contracts/src/AaveDIVAWrapperCore.sol#L470

uint256 _amountReturned = IAave(_aaveV3Pool).withdraw(
_collateralToken,
_getAccruedYieldPrivate(_collateralToken),
_recipient
);
emit YieldClaimed(owner(), _recipient, _collateralToken, _amountReturned);

The function:

  1. Calls Aave's withdraw without storing the expected amount

  2. Emits an event with the returned amount without verification

  3. Returns the amount without ensuring it matches the requested withdrawal

Proof of Concept

  1. User attempts to withdraw 100 tokens of accrued yield

  2. Due to liquidity constraints, Aave returns only 90 tokens

  3. Function emits event with 90 tokens and returns successfully

  4. User receives fewer tokens than entitled without any indication of partial withdrawal

Recommendation

Implement validation of the returned amount:

function _claimYield(address _collateralToken, address _recipient) internal returns (uint256) {
if (_collateralTokenToWToken[_collateralToken] == address(0)) {
revert CollateralTokenNotRegistered();
}
if (_recipient == address(0)) revert ZeroAddress();
uint256 expectedAmount = _getAccruedYieldPrivate(_collateralToken);
uint256 _amountReturned = IAave(_aaveV3Pool).withdraw(
_collateralToken,
expectedAmount,
_recipient
);
if (_amountReturned < expectedAmount) {
revert InsufficientWithdrawalAmount(expectedAmount, _amountReturned);
}
emit YieldClaimed(owner(), _recipient, _collateralToken, _amountReturned);
return _amountReturned;
}
Updates

Lead Judging Commences

bube Lead Judge 9 months ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.