Skip to content

Latest commit

 

History

History
87 lines (68 loc) · 3.87 KB

File metadata and controls

87 lines (68 loc) · 3.87 KB

Daring Mustard Crab

Medium

Incorrect Output and Gas Inefficiency in _sqrt Function

Summary

The _sqrt function incorrectly returns 0 for y = 2 and y = 3, causing precision issues. Additionally, the function is inefficient in terms of gas consumption, performing unnecessary iterations and divisions.

Severity: Medium Impact: Medium Likelihood: Low to Medium

Affected Line Of Code:

https://github.com/sherlock-audit/2025-01-peapods-finance/blob/main/contracts/contracts/AutoCompoundingPodLp.sol#L397-L408

The affected line of code is:

else if (y != 0) {
    z = 1;
}

Issue Explanation: This logic fails to correctly handle cases where y = 2 or y = 3. The function should return 1 for these values, but instead, it results in 0 due to the missing explicit check.

The gas inefficiency stems from redundant iterations in the loop:

while (x < z) {
    z = x;
    x = (y / x + x) / 2;
}

The calculation inside the loop could be optimized to reduce unnecessary divisions and improve efficiency.

Finding Description

The _sqrt function is designed to calculate the square root of a given number y using the Babylonian method. However, the function does not return the correct result for small values of y, specifically when y = 2 and y = 3. It also wastes gas by performing unnecessary iterations.

Security Guarantees Broken:

  • Precision: The function's incorrect handling of small values breaks the expected output, leading to invalid results.
  • Gas Efficiency: The function performs more iterations than necessary, leading to excess gas consumption, which can be particularly problematic when used in high-frequency calculations or on-chain environments with gas limits.

This issue does not automatically trigger a vulnerability but could propagate through the system if the function is called in critical operations, such as financial calculations. Malicious or unintended inputs may result in incorrect results, leading to invalid computations.

Impact Explanation

The impact of this issue is classified as Medium for the following reasons:

  • Incorrect Output: For y = 2 and y = 3, the function incorrectly returns 0, which could break logic relying on precise square root calculations (e.g., pricing mechanisms, financial computations).
  • Gas Wastage: The inefficiencies in the algorithm lead to increased gas costs. Although this is not a direct security risk, it could result in unnecessary expense, especially in high-frequency usage.

Likelihood Explanation

The likelihood of this issue occurring depends on the contract's use cases:

  • If the _sqrt function is frequently called with values 2 or 3, or used in high-frequency loops, it becomes more likely to cause unwanted behavior (incorrect results) or increased gas costs.
  • This issue is not triggered by every call but is more likely in contexts where square root calculations are critical, such as in financial applications.

Proof of Concept(POC)

Input:

uint256 result = _sqrt(2); // Expected output: 1, actual output: 0

Demonstration: When y = 2, the function incorrectly returns 0 instead of 1.

Recommendation

The issue can be fixed by ensuring that small values of y are handled properly and optimizing the gas usage of the algorithm.

Fix:

function _sqrt(uint256 y) private pure returns (uint256 z) {
    if (y > 3) {
        z = y;
        uint256 x = y / 2;
        while (x < z) {
            z = x;
            x = (y / x + x) >> 1; // Optimized division for gas efficiency
        }
    } else {
        z = (y == 0) ? 0 : 1; // Ensure correct output for y = 2, 3
    }
}

This fix ensures that:

The function handles small values (y = 2, y = 3) correctly by setting z = 1. The algorithm is optimized to use fewer iterations and gas by using y / 2 as the initial guess and >> 1 for cheaper division.