Liquid Staking

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

Error in merkle tree check

Summary

Error in merkle tree check. This implies that the strategy can't hold any tokens when a Merkle root is set, which is likely not the intended behavior.

Vulnerability Details

/**
* @notice Returns the maximum amount of tokens this strategy can hold
* @return maximum deposits
*/
function getMaxDeposits() public view virtual override returns (uint256) {
return stakeController.getMerkleRoot() == bytes32(0) ? super.getMaxDeposits() : 0;
}

The issue with the getMaxDeposits function lies in its logic and the interpretation of the Merkle root. Let's break it down:

  1. The function returns 0 if the Merkle root is not zero (i.e., if a Merkle root exists).This implies that the strategy can't hold any tokens when a Merkle root is set, which is likely not the intended behavior.

    The presence of a Merkle root (i.e., when it's not zero) typically indicates that the staking contract is in a state where it can accept stakes or perform certain operations.

    Returning 0 in this case would prevent the strategy from holding any tokens precisely when it should be able to.

    Generally, a non-zero Merkle root would indicate that the staking system is active and should be able to accept deposits.

    The current implementation does the opposite, allowing deposits only when the Merkle root is zero.

Impact

Incorrect logic leads to unintended results

Tools Used

Manual Review

Recommendations

contract CommunityVCS is VaultControllerStrategy {
// ... (other contract code)

/**
* @notice Returns the maximum amount of tokens this strategy can hold
* @return maximum deposits
*/
function getMaxDeposits() public view virtual override returns (uint256) {
bytes32 merkleRoot = stakeController.getMerkleRoot();
if (merkleRoot == bytes32(0)) {
// If Merkle root is not set, staking might not be active
return 0;
}
// Check if staking is active
if (!stakeController.isActive()) {
return 0;
}
// Get the max deposits from the parent implementation
uint256 maxDeposits = super.getMaxDeposits();
// Additional checks can be added here if needed
// For example, we might want to limit deposits based on the total stake in the staking contract
uint256 totalStake = stakeController.getTotalStake();
uint256 maxStake = stakeController.getMaxPoolSize();
if (totalStake >= maxStake) {
return 0; // Staking pool is full
}
// Limit maxDeposits to the remaining space in the staking pool
return Math.min(maxDeposits, maxStake - totalStake);
}
// ... (other functions)

}

Updates

Lead Judging Commences

inallhonesty Lead Judge 8 months ago
Submission Judgement Published
Invalidated
Reason: Incorrect statement

Support

FAQs

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