Core Contracts

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

Unchecked arithmetic in `Auction#getPrice()` lead to DoS blocking users from bidding

Summary

The getPrice function in the Auction contract has an unchecked arithmetic operation that can cause an underflow, leading to a denial-of-service (DoS) condition. If reservePrice is greater than startingPrice, the subtraction operation will revert, preventing the contract from functioning correctly.

Vulnerability Details

The getPrice function calculates the price dynamically but does not check if reservePrice is greater than startingPrice (in provided docs, there is nothing referring to this, so it may happen). If reservePrice > startingPrice, an underflow occurs:

return state.startingPrice - (
(state.startingPrice - state.reservePrice) *
(block.timestamp - state.startTime) /
(state.endTime - state.startTime)
);

Next, function buytake getPriceto calculate price that will be transferred by user to bid on the ZENO auction:

function buy(uint256 amount) external whenActive {
require(amount <= state.totalRemaining, "Not enough ZENO remaining");
uint256 price = getPrice();
uint256 cost = price * amount;
require(usdc.transferFrom(msg.sender, businessAddress, cost), "Transfer failed");
bidAmounts[msg.sender] += amount;
state.totalRemaining -= amount;
state.lastBidTime = block.timestamp;
state.lastBidder = msg.sender;
zeno.mint(msg.sender, amount);
emit ZENOPurchased(msg.sender, amount, price);
}

Let's assume next initial conditions:

  • startingPrice = 1000

  • reservePrice = 2000 (Invalid case)

The subtraction 1000 - 2000 underflows, causing a revert.

it("should revert due to underflow in getPrice", async function () {
await auction.setPrices(1000, 2000); // setting startingPrice < reservePrice
await expect(auction.getPrice()).to.be.reverted;
});

Output:

Error: Transaction reverted: arithmetic underflow

Impact

If the underflow occurs, the auction will become completely inoperable, preventing users from retrieving the price and making bids. This results in a full contract denial-of-service (auction with these incorrect parameters).

Tools Used

Manual review.

Recommendations

Add a check in the constructor and setPrices function to prevent invalid price ranges:

require(_startingPrice >= _reservePrice, "Invalid price range");
Updates

Lead Judging Commences

inallhonesty Lead Judge 3 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.