Skip to content

Commit

Permalink
prevent batch auction cancellations during final 10% of auction (#1203)
Browse files Browse the repository at this point in the history
  • Loading branch information
tbrent authored Sep 10, 2024
1 parent f532a2a commit 72a9c2d
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 1 deletion.
10 changes: 9 additions & 1 deletion contracts/plugins/trading/GnosisTrade.sol
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@ contract GnosisTrade is ITrade, Versioned {
TradeKind public constant KIND = TradeKind.BATCH_AUCTION;
uint256 public constant FEE_DENOMINATOR = 1000;

// Can only cancel order in first 90% of the auction
uint192 public constant CANCEL_WINDOW = 9e17; // {1} first 90% of auction

// Upper bound for the max number of orders we're happy to have the auction clear in;
// When we have good price information, this determines the minimum buy amount per order.
uint96 public constant MAX_ORDERS = 5000; // bounded to avoid going beyond block gas limit
Expand Down Expand Up @@ -141,10 +144,15 @@ contract GnosisTrade is ITrade, Versioned {
// amount is > 0 and < type(uint256).max.
AllowanceLib.safeApproveFallbackToMax(address(sell), address(gnosis), req.sellAmount);

// Can only cancel within the CANCEL_WINDOW
uint48 cancellationEndTime = uint48(
block.timestamp + (batchAuctionLength * CANCEL_WINDOW) / FIX_ONE
);

auctionId = gnosis.initiateAuction(
sell,
buy,
endTime,
cancellationEndTime,
endTime,
_sellAmount,
minBuyAmount,
Expand Down
41 changes: 41 additions & 0 deletions test/integration/EasyAuction.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -363,6 +363,47 @@ describeFork(`Gnosis EasyAuction Mainnet Forking - P${IMPLEMENTATION}`, function
expect(await rsr.balanceOf(backingManager.address)).to.equal(0)
})

it('cannot cancel in last 10% of auction', async () => {
// Place 2 orders
const bidAmt = buyAmt.add(1)
await token0.connect(addr1).approve(easyAuction.address, bidAmt.mul(3))
await easyAuction
.connect(addr1)
.placeSellOrders(auctionId, [sellAmt], [bidAmt], [QUEUE_START], ethers.constants.HashZero)
await easyAuction
.connect(addr1)
.placeSellOrders(
auctionId,
[sellAmt],
[bidAmt.mul(2)],
[QUEUE_START],
ethers.constants.HashZero
)

// Advance halfway
await advanceTime(config.batchAuctionLength.div(2).toString())

// Cancel successfully
const OrderHelperFactory = await ethers.getContractFactory('IterableOrderedOrderSetWrapper')
const orderHelper = await OrderHelperFactory.deploy()
const userId = await easyAuction.callStatic.getUserId(addr1.address)
const order = await orderHelper.encodeOrder(userId, sellAmt, bidAmt)
await easyAuction.connect(addr1).cancelSellOrders(auctionId, [order])

// Advance near end
await advanceTime(config.batchAuctionLength.div(2).sub(10).toString())

// Cannot cancel
const order2 = await orderHelper.encodeOrder(userId, sellAmt, bidAmt.mul(2))
await expect(
easyAuction.connect(addr1).cancelSellOrders(auctionId, [order2])
).to.be.revertedWith('no longer in order placement and cancelation phase')

// End auction
await advanceTime(config.batchAuctionLength.div(2).toString())
await easyAuction.settleAuction(auctionId)
})

it('full volume -- bid at 2x price', async () => {
const bidAmt = buyAmt.add(1)
sellAmt = sellAmt.div(2)
Expand Down

0 comments on commit 72a9c2d

Please sign in to comment.