Core Contracts

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

Incorrect Voting Power Calculation

Summary

The voting power calculation in the contract is flawed due to improper handling of the bias value, which is cast to uint128 before being used. This can lead to precision loss or incorrect voting power calculations if the bias value exceeds the range of uint128.

Vulnerability Details

Root Cause

The issue arises in the lock function, where the bias value is cast to uint128 before being used to calculate voting power:

// Calculate initial voting power
(int128 bias, int128 slope) = _votingState.calculateAndUpdatePower(
msg.sender,
amount,
unlockTime
);

proof of concept

Steps to Reproduce

  • Deploy the veRAACToken contract with the RAAC token address.

  • User A locks 10 million RAAC tokens for 4 years (MAX_LOCK_DURATION).

  • Observe the bias value calculated for User A.

  • Verify that the bias value exceeds the range of uint128.

  • Observe the voting power calculated for User A after casting bias to uint128.

  • Verify that the voting power is incorrect due to precision loss.

Expected Behavior

The voting power calculation should use the full precision of the bias value without truncation.


Actual Behavior

The bias value is truncated when cast to uint128, leading to incorrect voting power.

Code Example

// Simulate incorrect voting power calculation
function testIncorrectVotingPowerCalculation() public {
// Step 1: Deploy the contract
veRAACToken veRAAC = new veRAACToken(raacTokenAddress);
// Step 2: Simulate a large lock
uint256 lockAmount = 10_000_000e18; // 10 million RAAC tokens
uint256 lockDuration = 1460 days; // 4 years
veRAAC.lock(lockAmount, lockDuration);
// Step 3: Retrieve the calculated voting power
uint256 votingPower = veRAAC.getVotingPower(userA);
// Step 4: Verify that the voting power is incorrect due to precision loss
// Expected voting power: (lockAmount * lockDuration) / MAX_LOCK_DURATION
uint256 expectedVotingPower = (lockAmount * lockDuration) / veRAAC.MAX_LOCK_DURATION();
assert(votingPower != expectedVotingPower, "Voting power is incorrect due to precision loss");
}

Output

  • The bias value exceeds the range of uint128 and is truncated when cast to uint128.

  • The calculated voting power for User A is incorrect due to precision loss.

Impact

  • Users may receive incorrect voting power, undermining the fairness of the governance system.

  • Large bias values could be truncated, leading to significant discrepancies in voting power.

  • Incorrect voting power calculations could distort voting outcomes, reducing trust in the governance mechanism.

Tools Used

Manual Code Review

Recommendations

  • Use int256 or uint256 for the bias value instead of int128 to avoid precision loss.

(int256 bias, int128 slope) = _votingState.calculateAndUpdatePower(
msg.sender,
amount,
unlockTime
);
uint256 newPower = uint256(bias); // Correct: No casting to uint128
  • Add checks to ensure that the bias value does not exceed the range of uint128 before casting.

require(bias >= type(int128).min && bias <= type(int128).max, "Bias out of range");
  • Emit an event when voting power is calculated to improve transparency and facilitate debugging

Updates

Lead Judging Commences

inallhonesty Lead Judge 7 months ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity
inallhonesty Lead Judge 7 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.

Give us feedback!