Core Contracts

Regnum Aurum Acquisition Corp
HardhatReal World AssetsNFT
77,280 USDC
View results
Submission Details
Severity: high
Valid

The increase function of the veRAACToken contract incorrectly added amount twice to the userLock.amount

Summary

The increaseLock function in the LockManager library is designed to allow users to add more tokens to their existing lock. However, there is a logical error in the increase function of the veRAACToken contract where the userLock.amount is incorrectly added twice: once in increaseLock and again in the increase function. This results in an incorrect calculation of the total locked amount and voting power, leading to potential inconsistencies in the contract state.

Vulnerability Details

The increaseLock function in the LockManager library correctly updates the lock.amount and state.totalLocked by adding the additionalAmount.

function increaseLock(
LockState storage state,
address user,
uint256 additionalAmount
) internal {
Lock storage lock = state.locks[user];
if (!lock.exists) revert LockNotFound();
if (lock.end <= block.timestamp) revert LockExpired();
// Maximum lock amount
if (lock.amount + additionalAmount > state.maxLockAmount) revert AmountExceedsLimit();
// Maximum total locked amount
// if (state.totalLocked + additionalAmount > state.maxTotalLocked) revert AmountExceedsLimit();
lock.amount += additionalAmount;
state.totalLocked += additionalAmount;
emit LockIncreased(user, additionalAmount);
}

However, in the increase function of the veRAACToken contract, the userLock.amount is added again when calculating the new voting power:

function increase(uint256 amount) external nonReentrant whenNotPaused {
// Increase lock using LockManager
_lockState.increaseLock(msg.sender, amount);
_updateBoostState(msg.sender, locks[msg.sender].amount);
// Update voting power
LockManager.Lock memory userLock = _lockState.locks[msg.sender];
(int128 newBias, int128 newSlope) = _votingState.calculateAndUpdatePower(
msg.sender,
userLock.amount + amount,
userLock.end
);

Here the userLock.amount + amount is incorrect, leading to the incorrect result of the newBias.

Impact

  • Incorrect Voting Power: The voting power calculation is inflated because the additionalAmount is added twice.

  • State Inconsistency: The total locked amount and voting power do not accurately reflect the actual state of the contract.

  • Unfair Advantage: Users who increase their lock may receive more voting power than they are entitled to.

The impact is High, the likelihood is High, so the severity is High.

Tools Used

Manual Review

Recommendations

Consider following fix:

function increase(uint256 amount) external nonReentrant whenNotPaused {
// Increase lock using LockManager
_lockState.increaseLock(msg.sender, amount);
_updateBoostState(msg.sender, locks[msg.sender].amount);
// Update voting power
LockManager.Lock memory userLock = _lockState.locks[msg.sender];
(int128 newBias, int128 newSlope) = _votingState.calculateAndUpdatePower(
msg.sender,
userLock.amount,
userLock.end
);
Updates

Lead Judging Commences

inallhonesty Lead Judge 7 months ago
Submission Judgement Published
Validated
Assigned finding tags:

veRAACToken::increase doubles the voting power of users

Support

FAQs

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

Give us feedback!