Liquid Staking

Stakelink
DeFiHardhatOracle
50,000 USDC
View results
Submission Details
Severity: medium
Invalid

Missing Validation of _batchIds

Summary

Vulnerability Details

The WIthdrawalPool.sol::withdraw function assumes that each batchId is valid and references a valid batch in the withdrawalBatches mapping. However, there is no check to ensure that _batchIds[i] corresponds to an existing batch. If an invalid batchId is provided, the function will still proceed, which could result in faulty calculations or potential unintended behavior.

function withdraw(uint256[] calldata _withdrawalIds, uint256[] calldata _batchIds) external {
address owner = msg.sender;
uint256 amountToWithdraw;
for (uint256 i = 0; i < _withdrawalIds.length; ++i) {
uint256 withdrawalId = _withdrawalIds[i];
Withdrawal memory withdrawal = queuedWithdrawals[_withdrawalIds[i]];
uint256 batchId = _batchIds[i];
WithdrawalBatch memory batch = withdrawalBatches[batchId];
if (withdrawalOwners[withdrawalId] != owner) revert SenderNotAuthorized();
// @audit add a validation check
if (
batchId != 0 && withdrawalId <= withdrawalBatches[batchId - 1].indexOfLastWithdrawal
) revert InvalidWithdrawalId();
if (
batchId != 0 &&
withdrawalId > batch.indexOfLastWithdrawal &&
withdrawal.partiallyWithdrawableAmount == 0
) revert InvalidWithdrawalId();
if (withdrawalId <= batch.indexOfLastWithdrawal) {
amountToWithdraw +=
withdrawal.partiallyWithdrawableAmount +
(uint256(batch.stakePerShares) * uint256(withdrawal.sharesRemaining)) /
1e18;
delete queuedWithdrawals[withdrawalId];
delete withdrawalOwners[withdrawalId];
} else {
amountToWithdraw += withdrawal.partiallyWithdrawableAmount;
queuedWithdrawals[withdrawalId].partiallyWithdrawableAmount = 0;
}
}
token.safeTransfer(owner, amountToWithdraw);
emit Withdraw(owner, amountToWithdraw);
}

Impact

  • Invalid batchId: If an invalid batchId is passed, the contract may reference non-existent or incorrect data, leading to faulty withdrawal calculations or erroneous batch processing.

  • Potential Funds Loss: Users may end up withdrawing incorrect amounts due to invalid or incorrect batchId references, leading to under-withdrawal or over-withdrawal. This can result in unfair distribution of funds or even a loss of user trust.

Tools Used

Manual Review

Recommendations

The contract should validate that the batchId provided by the user corresponds to a valid batch in the withdrawalBatches mapping. Specifically, we need to confirm that the batchId exists and contains valid data.

This line ensures that the batchId corresponds to a valid batch in the withdrawalBatches mapping. If the batch.indexOfLastWithdrawal is zero, it means that the batch does not exist or is not initialized, and the transaction will revert with the error message "Invalid batchId".

require(batch.indexOfLastWithdrawal != 0, "Invalid batchId");
Updates

Lead Judging Commences

inallhonesty Lead Judge about 1 year ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Support

FAQs

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