Stratax Contracts

First Flight #57
Beginner FriendlyDeFi
100 EXP
Submission Details
Impact: high
Likelihood: high

Stale or incorrect chainlink price not validated

Author Revealed upon completion

Root + Impact

The getPrice() function in StrataxOracle.sol retrieves Chainlink price data using latestRoundData() but ignores critical staleness and validity indicators (updatedAt and answeredInRound). This allows the contract to use outdated prices without detecting that Chainlink has stopped updating. Positions are opened and unwound using stale/incorrect prices, leading to incorrect leverage calculations, improper position sizing, and potential liquidations or substantial value loss.

Description

When a leveraged position is created or unwound, the contract calls calculateOpenParams() and calculateUnwindParams() to compute how much collateral to supply and how much to borrow. These calculations depend critically on accurate, real-time token prices from the oracle. The Stratax smart contract uses prices from StrataxOracle.getPrice() to size positions with the correct leverage multiplier.

function getPrice(address _token) public view returns (uint256 price) {
address priceFeedAddress = priceFeeds[_token];
require(priceFeedAddress != address(0), "Price feed not set for token");
AggregatorV3Interface priceFeed = AggregatorV3Interface(priceFeedAddress);
@> Missing checks: updatedAt and answeredInRound are not validated
(, int256 answer,,,) = priceFeed.latestRoundData();
require(answer > 0, "Invalid price from oracle");
price = uint256(answer);
}

Risk

Likelihood:

  • Depends on feed and network conditions

Impact:

  • Position is opened with higher effective leverage than intended (user expects 3x but gets 4x due to stale price). Position is immediately undercollateralized.

  • Stale price causes wrong collateral/debt ratio; position enters liquidation within minutes or hours as it tries to rebalance or as market moves slightly. User loses principal + liquidation penalties.

Proof of Concept

Recommended Mitigation

  • Require updatedAt within a max age (e.g. 30 mins or 1 hour) and answer == answeredInRound (or equivalent staleness checks) and revert with a clear error if stale.

Support

FAQs

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

Give us feedback!