SIP-399: Perps V3 - Flash Loan Utility

Author
StatusDraft
TypeGovernance
NetworkBase
ImplementorTBD
ReleaseTBD
Created2024-07-16

Simple Summary

Deploy a Flash Loan utility contract to enable users to close their Perps V3 positions in a single transaction.

Abstract

This SIP proposes to deploy a new contract, PerpsFlashLoanUtil, which will allow users to close their Perps V3 positions by utilizing flash loans. This contract interacts with the Synthetix proxies and Uniswap's SwapRouter to facilitate the necessary operations. The contract also includes a utility function to set Uniswap pool addresses dynamically based on the collateral or margin type.

Motivation

The motivation behind this proposal comes from requests by Perps integrators and partners who seek a better user experience when closing Perps positions. The current process can be cumbersome, requiring multiple steps and transactions. This flash loan utility contract aims to streamline the process, allowing users to close positions atomically, thereby improving efficiency and user satisfaction.

Specification

Overview

The PerpsFlashLoanUtil contract will allow users to close their Perps positions using flash loans from the Aave protocol. The process involves wrapping USDC to snxUSD, repaying debt, modifying collateral, unwrapping to the original collateral type, swapping to USDC, and repaying the flash loan.

Rationale

The proposed solution leverages existing Synthetix and Uniswap contracts to facilitate the flash loan process. By using a flash loan, users can close their Perps positions without needing to front the necessary collateral. The contract allows for dynamic setting of Uniswap pool addresses and supporting various collateral types.

Technical Specification

Interfaces

/**
 * @title Interface for the PerpsFlashLoanUtil contract.
 * @notice Provides functions for requesting flash loans to close perps V3 positions.
 */
interface IPerpsFlashLoanUtil {
    /**
     * @notice Requests a flash loan.
     * @param _amount The amount of USDC to flash loan.
     * @param _collateralType The address of the collateral type to use.
     * @param _marketId The ID of the market for the flash loan.
     * @param _accountId The account ID to use for the flash loan.
     */
    function requestFlashLoan(
        uint256 _amount,
        address _collateralType,
        uint128 _marketId,
        uint128 _accountId
    ) external;

    /**
     * @notice Executes the flash loan operation.
     * @param asset The address of the asset being flash loaned.
     * @param amount The amount of the asset being flash loaned.
     * @param premium The premium to be paid for the flash loan.
     * @param initiator The address that initiated the flash loan.
     * @param params Additional parameters for the flash loan operation.
     * @return success True if the operation was successful, false otherwise.
     */
    function executeOperation(
        address asset,
        uint256 amount,
        uint256 premium,
        address initiator,
        bytes calldata params
    ) external returns (bool success);

    /**
     * @notice Sets the Uniswap pool address for a given collateral type.
     * @param _collateralType The address of the collateral type.
     * @param _poolAddress The pool address to be set for the collateral type.
     */
    function setPoolAddress(address _collateralType, address _poolAddress) external;
}

Contract Summary

  • setPoolAddress: Allows the contract owner to set the Uniswap pool address for different collateral types.
  • requestFlashLoan: Requests a flash loan and encodes the necessary parameters for closing a Perps position.
  • executeOperation: Handles the flash loan callback, performing the necessary operations to close the Perps position and repay the flash loan.

Test Cases

Initial State Tests

  • Verify the contract owner can set pool addresses using setPoolAddress.

Flash Loan Util Tests

  • Test requestFlashLoan with various parameters to ensure the correct encoding and decoding of parameters.
  • Test executeOperation for different collateral types and ensure the flash loan is repaid correctly.
  • Ensure the contract can handle scenarios where the collateral type is already USDC and no swap is necessary.
  • Test the Uniswap swap functionality by mocking the Quoter and SwapRouter to verify the amountOutMinimum calculation and the exact input swap execution.

Copyright and related rights waived via CC0.