Skip to content

Commit

Permalink
feat: added refundETH function and necessary comments
Browse files Browse the repository at this point in the history
  • Loading branch information
chefburger committed Jul 15, 2024
1 parent f1a8a37 commit 2208034
Show file tree
Hide file tree
Showing 30 changed files with 116 additions and 38 deletions.
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1018368
1018370
Original file line number Diff line number Diff line change
@@ -1 +1 @@
978417
978375
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1022832
1022790
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1100791
1100788
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1060904
1060857
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1098718
1098671
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1018380
1018382
Original file line number Diff line number Diff line change
@@ -1 +1 @@
978429
978387
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1022829
1022787
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1098773
1098770
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1058886
1058839
Original file line number Diff line number Diff line change
@@ -1 +1 @@
1096696
1096649
Original file line number Diff line number Diff line change
@@ -1 +1 @@
737793
737801
Original file line number Diff line number Diff line change
@@ -1 +1 @@
694746
694710
Original file line number Diff line number Diff line change
@@ -1 +1 @@
739171
739135
Original file line number Diff line number Diff line change
@@ -1 +1 @@
797611
797609
Original file line number Diff line number Diff line change
@@ -1 +1 @@
757099
757053
Original file line number Diff line number Diff line change
@@ -1 +1 @@
799013
798967
Original file line number Diff line number Diff line change
@@ -1 +1 @@
737805
737813
Original file line number Diff line number Diff line change
@@ -1 +1 @@
694758
694722
Original file line number Diff line number Diff line change
@@ -1 +1 @@
739168
739132
Original file line number Diff line number Diff line change
@@ -1 +1 @@
795593
795591
Original file line number Diff line number Diff line change
@@ -1 +1 @@
755081
755035
Original file line number Diff line number Diff line change
@@ -1 +1 @@
796991
796945
51 changes: 40 additions & 11 deletions src/base/BaseMigrator.sol
Original file line number Diff line number Diff line change
Expand Up @@ -10,23 +10,38 @@ import {IWETH9} from "../interfaces/external/IWETH9.sol";
import {PeripheryImmutableState} from "./PeripheryImmutableState.sol";
import {Multicall} from "./Multicall.sol";
import {SelfPermit} from "./SelfPermit.sol";
import {Currency} from "pancake-v4-core/src/types/Currency.sol";
import {Currency, CurrencyLibrary} from "pancake-v4-core/src/types/Currency.sol";
import {IBaseMigrator} from "../interfaces/IBaseMigrator.sol";

contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, SelfPermit {
constructor(address _WETH9) PeripheryImmutableState(_WETH9) {}

/// @notice refund native ETH to caller
/// This is useful when the caller sends more ETH then he specifies in arguments
function refundETH() external payable override {
if (address(this).balance > 0) CurrencyLibrary.NATIVE.transfer(msg.sender, address(this).balance);
}

/// @notice compare if tokens from v2 pair are the same as token0/token1. Revert with
/// `TOKEN_NOT_MATCH` if tokens does not match
function checkTokenMatchFromV2(address v2Pair, Currency token0, Currency token1) internal view {
address token0V2 = IPancakePair(v2Pair).token0();
address token1V2 = IPancakePair(v2Pair).token1();
_compare(token0V2, token1V2, Currency.unwrap(token0), Currency.unwrap(token1));
_checkIfTokenPairMatch(token0V2, token1V2, token0, token1);
}

/// @notice compare if tokens from v3 pool are the same as token0/token1. Revert with
/// `TOKEN_NOT_MATCH` if tokens does not match
function checkTokenMatchFromV3(address nfp, uint256 tokenId, Currency token0, Currency token1) internal view {
(,, address token0V3, address token1V3,,,,,,,,) = IV3NonfungiblePositionManager(nfp).positions(tokenId);
_compare(token0V3, token1V3, Currency.unwrap(token0), Currency.unwrap(token1));
_checkIfTokenPairMatch(token0V3, token1V3, token0, token1);
}

/// @notice withdraw liquidity from v2 pool (fee will always be included)
/// It may revert if amount0/amount1 received is less than expected
/// @param v2PoolParams the parameters to withdraw liquidity from v2 pool
/// @return amount0Received the actual amount of token0 received (in order of v4 pool)
/// @return amount1Received the actual amount of token1 received (in order of v4 pool)
function withdrawLiquidityFromV2(V2PoolParams calldata v2PoolParams)
internal
returns (uint256 amount0Received, uint256 amount1Received)
Expand All @@ -47,6 +62,11 @@ contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, Self
}
}

/// @notice withdraw liquidity from v3 pool and collect fee if specified in `v3PoolParams`
/// It may revert if the caller is not the owner of the token or amount0/amount1 received is less than expected
/// @param v3PoolParams the parameters to withdraw liquidity from v3 pool
/// @return amount0Received the actual amount of token0 received (in order of v4 pool)
/// @return amount1Received the actual amount of token1 received (in order of v4 pool)
function withdrawLiquidityFromV3(V3PoolParams calldata v3PoolParams)
internal
returns (uint256 amount0Received, uint256 amount1Received)
Expand Down Expand Up @@ -87,7 +107,7 @@ contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, Self
}
}

/// @dev receive extra tokens from user if necessary and normalize all the WETH to native ETH
/// @notice receive extra tokens from user if specifies in arguments and normalize all the WETH to native ETH
function batchAndNormalizeTokens(Currency currency0, Currency currency1, uint256 extraAmount0, uint256 extraAmount1)
internal
{
Expand All @@ -109,7 +129,7 @@ contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, Self
}

if (extraAmount0 != 0 || extraAmount1 != 0) {
emit MoreFundsAdded(address(token0), address(token1), extraAmount0, extraAmount1);
emit ExtraFundsAdded(address(token0), address(token1), extraAmount0, extraAmount1);
}

// even if user sends native ETH, we still need to unwrap the part from source pool
Expand All @@ -119,6 +139,7 @@ contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, Self
}
}

/// @notice approve the maximum amount of token if the current allowance is insufficient for following operations
function approveMaxIfNeeded(Currency currency, address to, uint256 amount) internal {
ERC20 token = ERC20(Currency.unwrap(currency));
if (token.allowance(address(this), to) >= amount) {
Expand All @@ -127,20 +148,28 @@ contract BaseMigrator is IBaseMigrator, PeripheryImmutableState, Multicall, Self
SafeTransferLib.safeApprove(token, to, type(uint256).max);
}

function _compare(address _token0, address _token1, address token0, address token1) private view {
if (token0 == address(0) && _token0 == WETH9) {
if (token1 != _token1) {
/// @notice Check and revert if tokens from both v2/v3 and v4 pair does not match
/// @param v2v3Token0 token0 from v2/v3 pair
/// @param v2v3Token1 token1 from v2/v3 pair
/// @param v4Token0 token0 from v4 pair
/// @param v4Token1 token1 from v4 pair
function _checkIfTokenPairMatch(address v2v3Token0, address v2v3Token1, Currency v4Token0, Currency v4Token1)
private
view
{
if (v4Token0.isNative() && v2v3Token0 == WETH9) {
if (Currency.unwrap(v4Token1) != v2v3Token1) {
revert TOKEN_NOT_MATCH();
}
} else if (token0 == address(0) && _token1 == WETH9) {
if (token1 != _token0) {
} else if (v4Token0.isNative() && v2v3Token1 == WETH9) {
if (Currency.unwrap(v4Token1) != v2v3Token0) {
revert TOKEN_NOT_MATCH();
}
} else {
/// @dev the order of token0 and token1 is always sorted
/// v2: https://github.com/pancakeswap/pancake-swap-core-v2/blob/38aad83854a46a82ea0e31988ff3cddb2bffb71a/contracts/PancakeFactory.sol#L27
/// v3: https://github.com/pancakeswap/pancake-v3-contracts/blob/5cc479f0c5a98966c74d94700057b8c3ca629afd/projects/v3-core/contracts/PancakeV3Factory.sol#L66
if (token0 != _token0 || token1 != _token1) {
if (Currency.unwrap(v4Token0) != v2v3Token0 || Currency.unwrap(v4Token1) != v2v3Token1) {
revert TOKEN_NOT_MATCH();
}
}
Expand Down
13 changes: 12 additions & 1 deletion src/interfaces/IBaseMigrator.sol
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,14 @@ interface IBaseMigrator is IPeripheryImmutableState, IMulticall, ISelfPermit {
error INSUFFICIENT_AMOUNTS_RECEIVED();
error NOT_TOKEN_OWNER();

event MoreFundsAdded(address currency0, address currency1, uint256 extraAmount0, uint256 extraAmount1);
/// @notice The event emitted when extra funds are added to the migrator
/// @param currency0 the address of the token0
/// @param currency1 the address of the token1
/// @param extraAmount0 the amount of extra token0
/// @param extraAmount1 the amount of extra token1
event ExtraFundsAdded(address currency0, address currency1, uint256 extraAmount0, uint256 extraAmount1);

/// @notice Parameters for removing liquidity from v2
struct V2PoolParams {
// the PancakeSwap v2-compatible pair
address pair;
Expand All @@ -25,6 +31,7 @@ interface IBaseMigrator is IPeripheryImmutableState, IMulticall, ISelfPermit {
uint256 amount1Min;
}

/// @notice Parameters for removing liquidity from v3
struct V3PoolParams {
// the PancakeSwap v3-compatible NFP
address nfp;
Expand All @@ -36,4 +43,8 @@ interface IBaseMigrator is IPeripheryImmutableState, IMulticall, ISelfPermit {
bool collectFee;
uint256 deadline;
}

/// @notice refund native ETH to caller
/// This is useful when the caller sends more ETH then he specifies in arguments
function refundETH() external payable;
}
9 changes: 9 additions & 0 deletions src/pool-bin/BinMigrator.sol
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ contract BinMigrator is IBinMigrator, BaseMigrator {
binFungiblePositionManager = IBinFungiblePositionManager(_binFungiblePositionManager);
}

/// @inheritdoc IBinMigrator
function migrateFromV2(
V2PoolParams calldata v2PoolParams,
V4BinPoolParams calldata v4PoolParams,
Expand Down Expand Up @@ -60,6 +61,7 @@ contract BinMigrator is IBinMigrator, BaseMigrator {
}
}

/// @inheritdoc IBinMigrator
function migrateFromV3(
V3PoolParams calldata v3PoolParams,
V4BinPoolParams calldata v4PoolParams,
Expand Down Expand Up @@ -106,6 +108,12 @@ contract BinMigrator is IBinMigrator, BaseMigrator {
}
}

/// @dev adding liquidity to target bin pool, collect surplus ETH if necessary
/// @param params bin position manager add liquidity params
/// @return amount0Consumed the actual amount of token0 consumed
/// @return amount1Consumed the actual amount of token1 consumed
/// @return tokenIds the list of the id of the position token minted
/// @return liquidityMinted the list of the amount of the position token minted
function _addLiquidityToTargetPool(IBinFungiblePositionManager.AddLiquidityParams memory params)
internal
returns (
Expand All @@ -131,6 +139,7 @@ contract BinMigrator is IBinMigrator, BaseMigrator {
}
}

/// @inheritdoc IBinMigrator
/// @notice Planned to be batched with migration operations through multicall to save gas
function initialize(PoolKey memory poolKey, uint24 activeId, bytes calldata hookData) external payable override {
return binFungiblePositionManager.initialize(poolKey, activeId, hookData);
Expand Down
12 changes: 11 additions & 1 deletion src/pool-bin/interfaces/IBinMigrator.sol
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,11 @@ interface IBinMigrator is IBaseMigrator {
uint256 deadline;
}

/// @notice Migrate liquidity from v2 to v4
/// @param v2PoolParams ncessary info for removing liqudity the source v2 pool
/// @param v4PoolParams necessary info for adding liquidity the target v4 bin-pool
/// @param extraAmount0 the extra amount of token0 that user wants to add (optional, usually 0)
/// @param extraAmount1 the extra amount of token1 that user wants to add (optional, usually 0)
function migrateFromV2(
V2PoolParams calldata v2PoolParams,
V4BinPoolParams calldata v4PoolParams,
Expand All @@ -32,6 +37,11 @@ interface IBinMigrator is IBaseMigrator {
uint256 extraAmount1
) external payable;

/// @notice Migrate liquidity from v3 to v4
/// @param v3PoolParams ncessary info for removing liqudity the source v3 pool
/// @param v4PoolParams necessary info for adding liquidity the target v4 bin-pool
/// @param extraAmount0 the extra amount of token0 that user wants to add (optional, usually 0)
/// @param extraAmount1 the extra amount of token1 that user wants to add (optional, usually 0)
function migrateFromV3(
V3PoolParams calldata v3PoolParams,
V4BinPoolParams calldata v4PoolParams,
Expand All @@ -40,7 +50,7 @@ interface IBinMigrator is IBaseMigrator {
uint256 extraAmount1
) external payable;

/// @notice Initialize a new pool
/// @notice Initialize a pool for a given pool key, the function will forwards the call to the BinPoolManager
/// @dev Call this when the pool does not exist and is not initialized
/// @param poolKey The pool key
/// @param activeId The active id of the pool
Expand Down
9 changes: 9 additions & 0 deletions src/pool-cl/CLMigrator.sol
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ contract CLMigrator is ICLMigrator, BaseMigrator {
nonfungiblePositionManager = INonfungiblePositionManager(_nonfungiblePositionManager);
}

/// @inheritdoc ICLMigrator
function migrateFromV2(
V2PoolParams calldata v2PoolParams,
V4CLPoolParams calldata v4PoolParams,
Expand Down Expand Up @@ -57,6 +58,7 @@ contract CLMigrator is ICLMigrator, BaseMigrator {
}
}

/// @inheritdoc ICLMigrator
function migrateFromV3(
V3PoolParams calldata v3PoolParams,
V4CLPoolParams calldata v4PoolParams,
Expand Down Expand Up @@ -100,6 +102,12 @@ contract CLMigrator is ICLMigrator, BaseMigrator {
}
}

/// @dev adding liquidity to target cl pool, collect surplus ETH if necessary
/// @param params cl position manager add liquidity params
/// @return tokenId the id of the newly minted position token
/// @return liquidity the amount of liquidity minted
/// @return amount0Consumed the actual amount of token0 consumed
/// @return amount1Consumed the actual amount of token1 consumed
function _addLiquidityToTargetPool(INonfungiblePositionManager.MintParams memory params)
internal
returns (uint256 tokenId, uint128 liquidity, uint256 amount0Consumed, uint256 amount1Consumed)
Expand All @@ -120,6 +128,7 @@ contract CLMigrator is ICLMigrator, BaseMigrator {
}
}

/// @inheritdoc ICLMigrator
/// @notice Planned to be batched with migration operations through multicall to save gas
function initialize(PoolKey memory poolKey, uint160 sqrtPriceX96, bytes calldata hookData)
external
Expand Down
Loading

0 comments on commit 2208034

Please sign in to comment.