Skip to content

Latest commit

 

History

History
64 lines (38 loc) · 2.01 KB

File metadata and controls

64 lines (38 loc) · 2.01 KB

Sneaky Neon Skunk

High

Re-entrancy exploit attack

Summary

The Auction.sol::_removeBid() function is vulnerable to a re-entrancy attack due to an external call to IERC20(buyCouponToken).safeTransfer made before fully updating the contract's state. A malicious bidder contract can exploit this by re-entering the function (or related functions) and manipulating the contract's state while it is in an inconsistent state.

Root Cause

    // Refund the buy tokens for the removed bid
 @>   IERC20(buyCouponToken).safeTransfer(bidder, sellCouponAmount); // @audit re-entrancy attack

    emit BidRemoved(bidIndex, bidder, buyReserveAmount, sellCouponAmount);

    // Update state
 @>   delete bids[bidIndex];
 @>  bidCount--;

Internal Pre-conditions

No response

External Pre-conditions

No response

Attack Path

https://github.com/sherlock-audit/2024-12-plaza-finance/blob/main/plaza-evm/src/Auction.sol#L325

Impact

Attack Setup: An attacker creates a malicious contract that calls Auction.sol::_removeBid() and re-enters the function during the execution of the safeTransfer call. Triggering the Attack: The attacker bids in the auction, triggering a bid removal when their bid is no longer the highest or lowest. When the contract attempts to refund tokens using the safeTransfer call, the attacker’s malicious contract is called. The malicious contract, in its fallback function, re-enters the vulnerable _removeBid() function.

Legitimate Bids are Not Removed: The linked list might not update, meaning bids that should be removed from the auction remain, invalidating the auction process. Invalid Bids are Accepted: A malicious actor could manipulate the bid list to make invalid bids appear as the highest or lowest bid, disrupting the auction.

PoC

No response

Mitigation

// Update state before external calls
delete bids[bidIndex];
bidCount--;

// Refund the buy tokens for the removed bid
IERC20(buyCouponToken).safeTransfer(bidder, sellCouponAmount);