The process of cancelling the limit order starts from LimitOrderManager by calling the cancelLimitOrder
/// @notice Function to cancel limitorder
/// @param tokenId limitorder id
/// @param unwrapVault to user wallet/vault
function cancelLimitOrder(uint256 tokenId, bool unwrapVault) public {
This code snippet is the definition of a function called cancelLimitOrder
that takes in two arguments: tokenId
and unwrapVault
. The function is defined as public
, which means it can be called by any contract or external actor. The function is designed to cancel a limit order identified by the given tokenId
. The unwrapVault
argument is a boolean that specifies whether the refund amount should be transferred to the user's wallet or their vault.
require(msg.sender == limitOrderToken.ownerOf(tokenId), "NOT_ID_OWNER");
LimitOrder memory limitOrder = limitOrders[tokenId];
require(limitOrder.status != LimitOrderStatus.closed, "Limit Order:Inactive");
This code snippet checks that the sender of the cancelLimitOrder
function is the owner of the limit order specified by tokenId
, and that the limit order is not closed. The limitOrder
struct is then retrieved from storage using tokenId
.
(, , , , , , address _token0, address _token1) = limitOrder.pool.getImmutables();
uint256 totalClaimableAmount = limitOrder.amountOut - limitOrder.claimedAmount;
uint256 refundAmount;
This code snippet checks that the caller of the function is the owner of the specified limit order, retrieves the limit order object from storage, and checks that the limit order is active. It then retrieves the addresses of the two tokens involved in the limit order from the limit order's pool and calculates the total claimable amount for the limit order. It initializes a variable called refundAmount
which will be used to store the amount that will be refunded to the caller.
if (limitOrder.zeroForOne) {
// refundAmount = (totalClaimableAmount * 10**12) / limitOrder.price;
refundAmount = FullMath.mulDivRoundingUp(totalClaimableAmount, 2**96, limitOrder.sqrtpriceX96);
refundAmount = FullMath.mulDivRoundingUp(refundAmount, 2**96, limitOrder.sqrtpriceX96);
limitOrder.pool.cancelLimitOrder(refundAmount, limitOrder.tick, limitOrder.zeroForOne);
_transferOut(_token0, msg.sender, refundAmount, unwrapVault);
} else {
// refundAmount = (limitOrder.price * totalClaimableAmount) / (10**12);
refundAmount = FullMath.mulDivRoundingUp(limitOrder.sqrtpriceX96, totalClaimableAmount, 2**96);
refundAmount = FullMath.mulDivRoundingUp(limitOrder.sqrtpriceX96, refundAmount, 2**96);
limitOrder.pool.cancelLimitOrder(refundAmount, limitOrder.tick, limitOrder.zeroForOne);
_transferOut(_token1, msg.sender, refundAmount, unwrapVault);
}
This code calculates the amount of tokens that should be refunded when a limit order is cancelled. If limitOrder.zeroForOne
is true, it calculates the refund amount using the formula
refundAmount = (totalClaimableAmount * 10**12) / limitOrder.price
, and transfers the tokens to the sender using the _transferOut
function. If limitOrder.zeroForOne
is false, it calculates the refund amount using the formula refundAmount = (limitOrder.price * totalClaimableAmount) / (10**12)
and transfers the tokens to the sender in the same way. It then calls the cancelLimitOrder
function on the limit order's pool with the calculated refund amount and the tick and zeroForOne
values from the limit order. Finally, it burns the limit order token and sets the limit order's status to closed.
limitOrderToken.burn(tokenId);
limitOrders[tokenId].status = LimitOrderStatus.closed;
emit CancelLimitOrder(address(limitOrder.pool), tokenId, refundAmount);
}