Hawk High

First Flight #39
Beginner FriendlySolidity
100 EXP
View results
Submission Details
Impact: high
Likelihood: medium
Invalid

Floating-Point Precision Loss and Rounding Errors in Integer Calculations

Summary

In the graduateAndUpgrade function, the calculation of teacher payments and principal wages involves integer arithmetic simulating floating-point operations. This can result in precision loss and rounding errors, particularly when dividing values like bursary * TEACHER_WAGE / PRECISION. These issues may lead to incorrect distribution of funds or other unintended behavior, especially when handling fractional amounts, such as wages or bursaries.

Vulnerability Details

In the provided code, the logic for distributing payments to teachers and the principal uses integer division to simulate floating-point values by scaling with a PRECISION factor:

uint256 payPerTeacher = (bursary * TEACHER_WAGE) / PRECISION;
uint256 principalPay = (bursary * PRINCIPAL_WAGE) / PRECISION;
  • Precision Loss: Solidity only supports integer arithmetic. When dividing (bursary * TEACHER_WAGE) by PRECISION, any fractional part is discarded. This can lead to an inaccurate division, as the remainder is lost in the process, resulting in the rounding down of the value.

  • Rounding Errors: Since the division is done using integers, the results may not match the expected fractional precision. For example, if the bursary * TEACHER_WAGE result doesn’t divide evenly by PRECISION, the remaining decimal part will be discarded, resulting in incorrect calculations for payPerTeacher and principalPay.

  • Security Implications: In financial applications, precision errors can lead to underpayment or overpayment, which may result in unintentional fund distribution or exploitation. An attacker could manipulate values to trigger unintended behavior in the fund distribution logic.

POC:

Let’s assume the following values:

  • bursary = 5e18

  • TEACHER_WAGE = 35

  • PRECISION = 100

The formula becomes:

TeacherPay = (5e18 * 35) / 100;

This simplifies to:

TeacherPay = 175e18 / 100 = 1.75e20; or 1e18

Impact

  • Precision Loss: Truncation due to integer division leads to loss of decimal precision, affecting the calculations of payPerTeacher and principalPay.

  • Rounding Errors: The contract may distribute less than expected to the teachers and the principal, especially when dealing with fractional cents.

  • Potential Financial Loss: Due to the rounding errors, teachers and principals may not receive the intended full payments, and small discrepancies could accumulate over time, causing a significant issue in contract behavior.

Tools Used

Foundry

Recommendations

Use Safe Math Libraries: Consider using libraries like OpenZeppelin’s SafeMath or FixedPointMathLib to handle precision and rounding errors when working with scaling factors.

Updates

Lead Judging Commences

yeahchibyke Lead Judge 4 months ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Appeal created

batblock Submitter
4 months ago
yeahchibyke Lead Judge
4 months ago
yeahchibyke Lead Judge 4 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.