sherlock-audit / 2022-10-merit-circle-judging

1 stars 0 forks source link

JohnSmith - Unsafe cast on point correction calculations #39

Closed sherlock-admin closed 2 years ago

sherlock-admin commented 2 years ago

JohnSmith

medium

Unsafe cast on point correction calculations

Summary

Unsafe cast may lead to wrong results.

Vulnerability Detail

Every time an accaunt's shares are minted or burned, there is a point correction calculation for the account, which involves uint256 pointsPerShare. To do the needed multiplication *shares pointsPerShare**, we have to cast all operands to same type. In function _correctPoints() shares represented as int256 _shares. So we need to cast uint256 pointsPerShare to int256. The way it is done: int256(pointsPerShare) will lead to problems when pointsPerShare become > type(int256).max

Impact

Unsafe cast will lead pointsPerShare to have some negative value in scope of this calculation, which will lead to wrong value for pointsCorrection[_account] to be stored, and as result wrong amount of rewards distributed to the account.

Code Snippet

merit-liquidity-mining/contracts/base/AbstractRewards.sol
125:   function _correctPoints(address _account, int256 _shares) internal {
126:     pointsCorrection[_account] = pointsCorrection[_account] + (_shares * (int256(pointsPerShare)));
127:   }

Tool used

Manual Review

Recommendation

Use SafeCast library to safely cast the uint256 to int256

function _correctPoints(address _account, int256 _shares) internal {
-  pointsCorrection[_account] = pointsCorrection[_account] + (_shares * (int256(pointsPerShare)));
+  pointsCorrection[_account] = pointsCorrection[_account] + (_shares * pointsPerShare.toInt256());
  }

Duplicate of #59