Feature Tip: Add private address tag to any address under My Name Tag !
Source Code
Overview
ETH Balance
0 ETH
Eth Value
$0.00Transaction Hash |
Method
|
Block
|
From
|
To
|
|||||
---|---|---|---|---|---|---|---|---|---|
Latest 1 internal transaction
Advanced mode:
Parent Transaction Hash | Method | Block |
From
|
To
|
|||
---|---|---|---|---|---|---|---|
0x61010060 | 18798274 | 570 days ago | Contract Creation | 0 ETH |
Loading...
Loading
Contract Name:
UniswapV3Adapter
Compiler Version
v0.8.17+commit.8df45f5f
Optimization Enabled:
Yes with 1000 runs
Other Settings:
london EvmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: GPL-2.0-or-later // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; import {RAY} from "@gearbox-protocol/core-v2/contracts/libraries/Constants.sol"; import {AbstractAdapter} from "../AbstractAdapter.sol"; import {AdapterType} from "@gearbox-protocol/sdk-gov/contracts/AdapterType.sol"; import {ISwapRouter} from "../../integrations/uniswap/IUniswapV3.sol"; import {BytesLib} from "../../integrations/uniswap/BytesLib.sol"; import {IUniswapV3Adapter, UniswapV3PoolStatus} from "../../interfaces/uniswap/IUniswapV3Adapter.sol"; /// @title Uniswap V3 Router adapter /// @notice Implements logic allowing CAs to perform swaps via Uniswap V3 contract UniswapV3Adapter is AbstractAdapter, IUniswapV3Adapter { using BytesLib for bytes; AdapterType public constant override _gearboxAdapterType = AdapterType.UNISWAP_V3_ROUTER; uint16 public constant override _gearboxAdapterVersion = 3_00; /// @dev The length of the bytes encoded address uint256 private constant ADDR_SIZE = 20; /// @dev The length of the uint24 encoded address uint256 private constant FEE_SIZE = 3; /// @dev The offset of a single token address and pool fee uint256 private constant NEXT_OFFSET = ADDR_SIZE + FEE_SIZE; /// @dev The length of the path with 1 hop uint256 private constant PATH_2_LENGTH = 2 * ADDR_SIZE + FEE_SIZE; /// @dev The length of the path with 2 hops uint256 private constant PATH_3_LENGTH = 3 * ADDR_SIZE + 2 * FEE_SIZE; /// @dev The length of the path with 3 hops uint256 private constant PATH_4_LENGTH = 4 * ADDR_SIZE + 3 * FEE_SIZE; /// @dev Mapping from (token0, token1, fee) to whether the pool can be traded through the adapter mapping(address => mapping(address => mapping(uint24 => bool))) internal _poolStatus; /// @notice Constructor /// @param _creditManager Credit manager address /// @param _router Uniswap V3 Router address constructor(address _creditManager, address _router) AbstractAdapter(_creditManager, _router) // U:[UNI3-1] {} /// @notice Swaps given amount of input token for output token through a single pool /// @param params Swap params, see `ISwapRouter.ExactInputSingleParams` for details /// @dev `params.recipient` is ignored since it can only be the credit account function exactInputSingle(ISwapRouter.ExactInputSingleParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-3] ISwapRouter.ExactInputSingleParams memory paramsUpdate = params; // U:[UNI3-3] paramsUpdate.recipient = creditAccount; // U:[UNI3-3] // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove( params.tokenIn, params.tokenOut, abi.encodeCall(ISwapRouter.exactInputSingle, (paramsUpdate)), false ); // U:[UNI3-3] } /// @notice Swaps all balance of input token for output token through a single pool, except the specified amount /// @param params Swap params, see `ExactDiffInputSingleParams` for details function exactDiffInputSingle(ExactDiffInputSingleParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-4] uint256 amount = IERC20(params.tokenIn).balanceOf(creditAccount); // U:[UNI3-4] if (amount <= params.leftoverAmount) return (0, 0); unchecked { amount -= params.leftoverAmount; // U:[UNI3-4] } ISwapRouter.ExactInputSingleParams memory paramsUpdate = ISwapRouter.ExactInputSingleParams({ tokenIn: params.tokenIn, tokenOut: params.tokenOut, fee: params.fee, recipient: creditAccount, deadline: params.deadline, amountIn: amount, amountOutMinimum: (amount * params.rateMinRAY) / RAY, sqrtPriceLimitX96: params.sqrtPriceLimitX96 }); // U:[UNI3-4] // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove( params.tokenIn, params.tokenOut, abi.encodeCall(ISwapRouter.exactInputSingle, (paramsUpdate)), params.leftoverAmount <= 1 ); // U:[UNI3-4] } /// @notice Swaps given amount of input token for output token through multiple pools /// @param params Swap params, see `ISwapRouter.ExactInputParams` for details /// @dev `params.recipient` is ignored since it can only be the credit account /// @dev `params.path` must have at most 3 hops through allowed pools function exactInput(ISwapRouter.ExactInputParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-5] (bool valid, address tokenIn, address tokenOut) = _validatePath(params.path); if (!valid) revert InvalidPathException(); // U:[UNI3-5] ISwapRouter.ExactInputParams memory paramsUpdate = params; // U:[UNI3-5] paramsUpdate.recipient = creditAccount; // U:[UNI3-5] // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove(tokenIn, tokenOut, abi.encodeCall(ISwapRouter.exactInput, (paramsUpdate)), false); // U:[UNI3-5] } /// @notice Swaps all balance of input token for output token through multiple pools, except the specified amount /// @param params Swap params, see `ExactDiffInputParams` for details /// @dev `params.path` must have at most 3 hops through allowed pools function exactDiffInput(ExactDiffInputParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-6] (bool valid, address tokenIn, address tokenOut) = _validatePath(params.path); if (!valid) revert InvalidPathException(); // U:[UNI3-6] uint256 amount = IERC20(tokenIn).balanceOf(creditAccount); // U:[UNI3-6] if (amount <= params.leftoverAmount) return (0, 0); unchecked { amount -= params.leftoverAmount; // U:[UNI3-6] } ISwapRouter.ExactInputParams memory paramsUpdate = ISwapRouter.ExactInputParams({ path: params.path, recipient: creditAccount, deadline: params.deadline, amountIn: amount, amountOutMinimum: (amount * params.rateMinRAY) / RAY }); // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove( tokenIn, tokenOut, abi.encodeCall(ISwapRouter.exactInput, (paramsUpdate)), params.leftoverAmount <= 1 ); // U:[UNI3-6] } /// @notice Swaps input token for given amount of output token through a single pool /// @param params Swap params, see `ISwapRouter.ExactOutputSingleParams` for details /// @dev `params.recipient` is ignored since it can only be the credit account function exactOutputSingle(ISwapRouter.ExactOutputSingleParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-7] ISwapRouter.ExactOutputSingleParams memory paramsUpdate = params; // U:[UNI3-7] paramsUpdate.recipient = creditAccount; // U:[UNI3-7] // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove( params.tokenIn, params.tokenOut, abi.encodeCall(ISwapRouter.exactOutputSingle, (paramsUpdate)), false ); // U:[UNI3-7] } /// @notice Swaps input token for given amount of output token through multiple pools /// @param params Swap params, see `ISwapRouter.ExactOutputParams` for details /// @dev `params.recipient` is ignored since it can only be the credit account /// @dev `params.path` must have at most 3 hops through allowed pools function exactOutput(ISwapRouter.ExactOutputParams calldata params) external override creditFacadeOnly // U:[UNI3-2] returns (uint256 tokensToEnable, uint256 tokensToDisable) { address creditAccount = _creditAccount(); // U:[UNI3-8] (bool valid, address tokenOut, address tokenIn) = _validatePath(params.path); if (!valid) revert InvalidPathException(); // U:[UNI3-8] ISwapRouter.ExactOutputParams memory paramsUpdate = params; // U:[UNI3-8] paramsUpdate.recipient = creditAccount; // U:[UNI3-8] // calling `_executeSwap` because we need to check if output token is registered as collateral token in the CM (tokensToEnable, tokensToDisable,) = _executeSwapSafeApprove(tokenIn, tokenOut, abi.encodeCall(ISwapRouter.exactOutput, (paramsUpdate)), false); // U:[UNI3-8] } // ------------- // // CONFIGURATION // // ------------- // /// @notice Returns whether the (token0, token1, fee) pool is allowed to be traded through the adapter function isPoolAllowed(address token0, address token1, uint24 fee) public view override returns (bool) { (token0, token1) = _sortTokens(token0, token1); return _poolStatus[token0][token1][fee]; } /// @notice Sets status for a batch of pools /// @param pools Array of `UniswapV3PoolStatus` objects function setPoolStatusBatch(UniswapV3PoolStatus[] calldata pools) external override configuratorOnly // U:[UNI3-9] { uint256 len = pools.length; unchecked { for (uint256 i; i < len; ++i) { (address token0, address token1) = _sortTokens(pools[i].token0, pools[i].token1); _poolStatus[token0][token1][pools[i].fee] = pools[i].allowed; // U:[UNI3-9] emit SetPoolStatus(token0, token1, pools[i].fee, pools[i].allowed); // U:[UNI3-9] } } } // ------- // // HELPERS // // ------- // /// @dev Performs sanity checks on a swap path, if path is valid also returns input and output tokens /// - Path length must be no more than 4 (i.e., at most 3 hops) /// - Each swap must be through an allowed pool function _validatePath(bytes memory path) internal view returns (bool valid, address tokenIn, address tokenOut) { uint256 len = path.length; if (len != PATH_2_LENGTH && len != PATH_3_LENGTH && len != PATH_4_LENGTH) return (false, tokenIn, tokenOut); // U:[UNI3-10] tokenIn = path.toAddress(0); // U:[UNI3-10] uint24 fee = path.toUint24(ADDR_SIZE); tokenOut = path.toAddress(NEXT_OFFSET); // U:[UNI3-10] valid = isPoolAllowed(tokenIn, tokenOut, fee); // U:[UNI3-10] if (valid && len > PATH_2_LENGTH) { address tokenMid = tokenOut; fee = path.toUint24(NEXT_OFFSET + ADDR_SIZE); tokenOut = path.toAddress(2 * NEXT_OFFSET); // U:[UNI3-10] valid = isPoolAllowed(tokenMid, tokenOut, fee); // U:[UNI3-10] if (valid && len > PATH_3_LENGTH) { tokenMid = tokenOut; fee = path.toUint24(2 * NEXT_OFFSET + ADDR_SIZE); tokenOut = path.toAddress(3 * NEXT_OFFSET); // U:[UNI3-10] valid = isPoolAllowed(tokenMid, tokenOut, fee); // U:[UNI3-10] } } } /// @dev Sorts two token addresses function _sortTokens(address token0, address token1) internal pure returns (address, address) { if (uint160(token0) < uint160(token1)) { return (token0, token1); } else { return (token1, token0); } } }
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts (last updated v4.9.0) (token/ERC20/IERC20.sol) pragma solidity ^0.8.0; /** * @dev Interface of the ERC20 standard as defined in the EIP. */ interface IERC20 { /** * @dev Emitted when `value` tokens are moved from one account (`from`) to * another (`to`). * * Note that `value` may be zero. */ event Transfer(address indexed from, address indexed to, uint256 value); /** * @dev Emitted when the allowance of a `spender` for an `owner` is set by * a call to {approve}. `value` is the new allowance. */ event Approval(address indexed owner, address indexed spender, uint256 value); /** * @dev Returns the amount of tokens in existence. */ function totalSupply() external view returns (uint256); /** * @dev Returns the amount of tokens owned by `account`. */ function balanceOf(address account) external view returns (uint256); /** * @dev Moves `amount` tokens from the caller's account to `to`. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transfer(address to, uint256 amount) external returns (bool); /** * @dev Returns the remaining number of tokens that `spender` will be * allowed to spend on behalf of `owner` through {transferFrom}. This is * zero by default. * * This value changes when {approve} or {transferFrom} are called. */ function allowance(address owner, address spender) external view returns (uint256); /** * @dev Sets `amount` as the allowance of `spender` over the caller's tokens. * * Returns a boolean value indicating whether the operation succeeded. * * IMPORTANT: Beware that changing an allowance with this method brings the risk * that someone may use both the old and the new allowance by unfortunate * transaction ordering. One possible solution to mitigate this race * condition is to first reduce the spender's allowance to 0 and set the * desired value afterwards: * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729 * * Emits an {Approval} event. */ function approve(address spender, uint256 amount) external returns (bool); /** * @dev Moves `amount` tokens from `from` to `to` using the * allowance mechanism. `amount` is then deducted from the caller's * allowance. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transferFrom(address from, address to, uint256 amount) external returns (bool); }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Holdings, 2022 pragma solidity ^0.8.10; // Denominations uint256 constant WAD = 1e18; uint256 constant RAY = 1e27; uint16 constant PERCENTAGE_FACTOR = 1e4; //percentage plus two decimals // 25% of type(uint256).max uint256 constant ALLOWANCE_THRESHOLD = type(uint96).max >> 3; // FEE = 50% uint16 constant DEFAULT_FEE_INTEREST = 50_00; // 50% // LIQUIDATION_FEE 1.5% uint16 constant DEFAULT_FEE_LIQUIDATION = 1_50; // 1.5% // LIQUIDATION PREMIUM 4% uint16 constant DEFAULT_LIQUIDATION_PREMIUM = 4_00; // 4% // LIQUIDATION_FEE_EXPIRED 2% uint16 constant DEFAULT_FEE_LIQUIDATION_EXPIRED = 1_00; // 2% // LIQUIDATION PREMIUM EXPIRED 2% uint16 constant DEFAULT_LIQUIDATION_PREMIUM_EXPIRED = 2_00; // 2% // DEFAULT PROPORTION OF MAX BORROWED PER BLOCK TO MAX BORROWED PER ACCOUNT uint16 constant DEFAULT_LIMIT_PER_BLOCK_MULTIPLIER = 2; // Seconds in a year uint256 constant SECONDS_PER_YEAR = 365 days; uint256 constant SECONDS_PER_ONE_AND_HALF_YEAR = (SECONDS_PER_YEAR * 3) / 2; // OPERATIONS // Leverage decimals - 100 is equal to 2x leverage (100% * collateral amount + 100% * borrowed amount) uint8 constant LEVERAGE_DECIMALS = 100; // Maximum withdraw fee for pool in PERCENTAGE_FACTOR format uint8 constant MAX_WITHDRAW_FEE = 100; uint256 constant EXACT_INPUT = 1; uint256 constant EXACT_OUTPUT = 2; address constant UNIVERSAL_CONTRACT = 0xCcCCccccCCCCcCCCCCCcCcCccCcCCCcCcccccccC;
// SPDX-License-Identifier: GPL-2.0-or-later // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IAdapter} from "@gearbox-protocol/core-v2/contracts/interfaces/IAdapter.sol"; import {ICreditManagerV3} from "@gearbox-protocol/core-v3/contracts/interfaces/ICreditManagerV3.sol"; import {CallerNotCreditFacadeException} from "@gearbox-protocol/core-v3/contracts/interfaces/IExceptions.sol"; import {ACLTrait} from "@gearbox-protocol/core-v3/contracts/traits/ACLTrait.sol"; /// @title Abstract adapter /// @dev Inheriting adapters MUST use provided internal functions to perform all operations with credit accounts abstract contract AbstractAdapter is IAdapter, ACLTrait { /// @notice Credit manager the adapter is connected to address public immutable override creditManager; /// @notice Address provider contract address public immutable override addressProvider; /// @notice Address of the contract the adapter is interacting with address public immutable override targetContract; /// @notice Constructor /// @param _creditManager Credit manager to connect the adapter to /// @param _targetContract Address of the adapted contract constructor(address _creditManager, address _targetContract) ACLTrait(ICreditManagerV3(_creditManager).addressProvider()) nonZeroAddress(_targetContract) { creditManager = _creditManager; addressProvider = ICreditManagerV3(_creditManager).addressProvider(); targetContract = _targetContract; } /// @dev Ensures that caller of the function is credit facade connected to the credit manager /// @dev Inheriting adapters MUST use this modifier in all external functions that operate on credit accounts modifier creditFacadeOnly() { _revertIfCallerNotCreditFacade(); _; } /// @dev Ensures that caller is credit facade connected to the credit manager function _revertIfCallerNotCreditFacade() internal view { if (msg.sender != ICreditManagerV3(creditManager).creditFacade()) { revert CallerNotCreditFacadeException(); } } /// @dev Ensures that active credit account is set and returns its address function _creditAccount() internal view returns (address) { return ICreditManagerV3(creditManager).getActiveCreditAccountOrRevert(); } /// @dev Ensures that token is registered as collateral in the credit manager and returns its mask function _getMaskOrRevert(address token) internal view returns (uint256 tokenMask) { tokenMask = ICreditManagerV3(creditManager).getTokenMaskOrRevert(token); } /// @dev Approves target contract to spend given token from the active credit account /// Reverts if active credit account is not set or token is not registered as collateral /// @param token Token to approve /// @param amount Amount to approve function _approveToken(address token, uint256 amount) internal { ICreditManagerV3(creditManager).approveCreditAccount(token, amount); } /// @dev Executes an external call from the active credit account to the target contract /// Reverts if active credit account is not set /// @param callData Data to call the target contract with /// @return result Call result function _execute(bytes memory callData) internal returns (bytes memory result) { return ICreditManagerV3(creditManager).execute(callData); } /// @dev Executes a swap operation without input token approval /// Reverts if active credit account is not set or any of passed tokens is not registered as collateral /// @param tokenIn Input token that credit account spends in the call /// @param tokenOut Output token that credit account receives after the call /// @param callData Data to call the target contract with /// @param disableTokenIn Whether `tokenIn` should be disabled after the call /// (for operations that spend the entire account's balance of the input token) /// @return tokensToEnable Bit mask of tokens that should be enabled after the call /// @return tokensToDisable Bit mask of tokens that should be disabled after the call /// @return result Call result function _executeSwapNoApprove(address tokenIn, address tokenOut, bytes memory callData, bool disableTokenIn) internal returns (uint256 tokensToEnable, uint256 tokensToDisable, bytes memory result) { tokensToEnable = _getMaskOrRevert(tokenOut); uint256 tokenInMask = _getMaskOrRevert(tokenIn); if (disableTokenIn) tokensToDisable = tokenInMask; result = _execute(callData); } /// @dev Executes a swap operation with maximum input token approval, and revokes approval after the call /// Reverts if active credit account is not set or any of passed tokens is not registered as collateral /// @param tokenIn Input token that credit account spends in the call /// @param tokenOut Output token that credit account receives after the call /// @param callData Data to call the target contract with /// @param disableTokenIn Whether `tokenIn` should be disabled after the call /// (for operations that spend the entire account's balance of the input token) /// @return tokensToEnable Bit mask of tokens that should be enabled after the call /// @return tokensToDisable Bit mask of tokens that should be disabled after the call /// @return result Call result /// @custom:expects Credit manager reverts when trying to approve non-collateral token function _executeSwapSafeApprove(address tokenIn, address tokenOut, bytes memory callData, bool disableTokenIn) internal returns (uint256 tokensToEnable, uint256 tokensToDisable, bytes memory result) { tokensToEnable = _getMaskOrRevert(tokenOut); if (disableTokenIn) tokensToDisable = _getMaskOrRevert(tokenIn); _approveToken(tokenIn, type(uint256).max); result = _execute(callData); _approveToken(tokenIn, 1); } }
// SPDX-License-Identifier: UNLICENSED // Gearbox. Generalized leverage protocol that allows to take leverage and then use it across other DeFi protocols and platforms in a composable way. // (c) Gearbox Foundation, 2023 pragma solidity ^0.8.17; enum AdapterType { ABSTRACT, UNISWAP_V2_ROUTER, UNISWAP_V3_ROUTER, CURVE_V1_EXCHANGE_ONLY, YEARN_V2, CURVE_V1_2ASSETS, CURVE_V1_3ASSETS, CURVE_V1_4ASSETS, CURVE_V1_STECRV_POOL, CURVE_V1_WRAPPER, CONVEX_V1_BASE_REWARD_POOL, CONVEX_V1_BOOSTER, CONVEX_V1_CLAIM_ZAP, LIDO_V1, UNIVERSAL, LIDO_WSTETH_V1, BALANCER_VAULT, AAVE_V2_LENDING_POOL, AAVE_V2_WRAPPED_ATOKEN, COMPOUND_V2_CERC20, COMPOUND_V2_CETHER, ERC4626_VAULT }
// SPDX-License-Identifier: MIT pragma solidity >=0.7.5; pragma abicoder v2; interface ISwapRouter { struct ExactInputSingleParams { address tokenIn; address tokenOut; uint24 fee; address recipient; uint256 deadline; uint256 amountIn; uint256 amountOutMinimum; uint160 sqrtPriceLimitX96; } function exactInputSingle(ExactInputSingleParams calldata params) external payable returns (uint256 amountOut); struct ExactInputParams { bytes path; address recipient; uint256 deadline; uint256 amountIn; uint256 amountOutMinimum; } function exactInput(ExactInputParams calldata params) external payable returns (uint256 amountOut); struct ExactOutputSingleParams { address tokenIn; address tokenOut; uint24 fee; address recipient; uint256 deadline; uint256 amountOut; uint256 amountInMaximum; uint160 sqrtPriceLimitX96; } function exactOutputSingle(ExactOutputSingleParams calldata params) external payable returns (uint256 amountIn); struct ExactOutputParams { bytes path; address recipient; uint256 deadline; uint256 amountOut; uint256 amountInMaximum; } function exactOutput(ExactOutputParams calldata params) external payable returns (uint256 amountIn); }
// SPDX-License-Identifier: GPL-2.0-or-later /* * @title Solidity Bytes Arrays Utils * @author Gonçalo Sá <[email protected]> * * @dev Bytes tightly packed arrays utility library for ethereum contracts written in Solidity. * The library lets you concatenate, slice and type cast bytes arrays both in memory and storage. */ pragma solidity >=0.8.0 <0.9.0; library BytesLib { function toAddress(bytes memory _bytes, uint256 _start) internal pure returns (address) { require(_bytes.length >= _start + 20, "toAddress_outOfBounds"); address tempAddress; assembly { tempAddress := div(mload(add(add(_bytes, 0x20), _start)), 0x1000000000000000000000000) } return tempAddress; } function toUint24(bytes memory _bytes, uint256 _start) internal pure returns (uint24) { require(_start + 3 >= _start, "toUint24_overflow"); require(_bytes.length >= _start + 3, "toUint24_outOfBounds"); uint24 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x3), _start)) } return tempUint; } function concat(bytes memory _preBytes, bytes memory _postBytes) internal pure returns (bytes memory) { bytes memory tempBytes; assembly { // Get a location of some free memory and store it in tempBytes as // Solidity does for memory variables. tempBytes := mload(0x40) // Store the length of the first bytes array at the beginning of // the memory for tempBytes. let length := mload(_preBytes) mstore(tempBytes, length) // Maintain a memory counter for the current write location in the // temp bytes array by adding the 32 bytes for the array length to // the starting location. let mc := add(tempBytes, 0x20) // Stop copying when the memory counter reaches the length of the // first bytes array. let end := add(mc, length) for { // Initialize a copy counter to the start of the _preBytes data, // 32 bytes into its memory. let cc := add(_preBytes, 0x20) } lt(mc, end) { // Increase both counters by 32 bytes each iteration. mc := add(mc, 0x20) cc := add(cc, 0x20) } { // Write the _preBytes data into the tempBytes memory 32 bytes // at a time. mstore(mc, mload(cc)) } // Add the length of _postBytes to the current length of tempBytes // and store it as the new length in the first 32 bytes of the // tempBytes memory. length := mload(_postBytes) mstore(tempBytes, add(length, mload(tempBytes))) // Move the memory counter back from a multiple of 0x20 to the // actual end of the _preBytes data. mc := end // Stop copying when the memory counter reaches the new combined // length of the arrays. end := add(mc, length) for { let cc := add(_postBytes, 0x20) } lt(mc, end) { mc := add(mc, 0x20) cc := add(cc, 0x20) } { mstore(mc, mload(cc)) } // Update the free-memory pointer by padding our last write location // to 32 bytes: add 31 bytes to the end of tempBytes to move to the // next 32 byte block, then round down to the nearest multiple of // 32. If the sum of the length of the two arrays is zero then add // one before rounding down to leave a blank 32 bytes (the length block with 0). mstore( 0x40, and( add(add(end, iszero(add(length, mload(_preBytes)))), 31), not(31) // Round down to the nearest 32 bytes. ) ) } return tempBytes; } function slice(bytes memory _bytes, uint256 _start, uint256 _length) internal pure returns (bytes memory) { require(_length + 31 >= _length, "slice_overflow"); require(_bytes.length >= _start + _length, "slice_outOfBounds"); bytes memory tempBytes; assembly { switch iszero(_length) case 0 { // Get a location of some free memory and store it in tempBytes as // Solidity does for memory variables. tempBytes := mload(0x40) // The first word of the slice result is potentially a partial // word read from the original array. To read it, we calculate // the length of that partial word and start copying that many // bytes into the array. The first word we copy will start with // data we don't care about, but the last `lengthmod` bytes will // land at the beginning of the contents of the new array. When // we're done copying, we overwrite the full first word with // the actual length of the slice. let lengthmod := and(_length, 31) // The multiplication in the next line is necessary // because when slicing multiples of 32 bytes (lengthmod == 0) // the following copy loop was copying the origin's length // and then ending prematurely not copying everything it should. let mc := add(add(tempBytes, lengthmod), mul(0x20, iszero(lengthmod))) let end := add(mc, _length) for { // The multiplication in the next line has the same exact purpose // as the one above. let cc := add(add(add(_bytes, lengthmod), mul(0x20, iszero(lengthmod))), _start) } lt(mc, end) { mc := add(mc, 0x20) cc := add(cc, 0x20) } { mstore(mc, mload(cc)) } mstore(tempBytes, _length) //update free-memory pointer //allocating the array padded to 32 bytes like the compiler does now mstore(0x40, and(add(mc, 31), not(31))) } //if we want a zero-length slice let's just return a zero-length array default { tempBytes := mload(0x40) //zero out the 32 bytes slice we are about to return //we need to do it because Solidity does not garbage collect mstore(tempBytes, 0) mstore(0x40, add(tempBytes, 0x20)) } } return tempBytes; } }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IAdapter} from "@gearbox-protocol/core-v2/contracts/interfaces/IAdapter.sol"; import {ISwapRouter} from "../../integrations/uniswap/IUniswapV3.sol"; struct UniswapV3PoolStatus { address token0; address token1; uint24 fee; bool allowed; } interface IUniswapV3AdapterTypes { /// @notice Params for exact diff input swap through a single pool /// @param tokenIn Input token /// @param tokenOut Output token /// @param fee Fee level of the pool to swap through /// @param deadline Maximum timestamp until which the transaction is valid /// @param leftoverAmount Amount of tokenIn to keep on the account /// @param rateMinRAY Minimum exchange rate between input and output tokens, scaled by 1e27 /// @param sqrtPriceLimitX96 Maximum execution price, ignored if 0 struct ExactDiffInputSingleParams { address tokenIn; address tokenOut; uint24 fee; uint256 deadline; uint256 leftoverAmount; uint256 rateMinRAY; uint160 sqrtPriceLimitX96; } /// @notice Params for exact diff input swap through multiple pools /// @param path Bytes-encoded swap path, see Uniswap docs for details /// @param deadline Maximum timestamp until which the transaction is valid /// @param leftoverAmount Amount of tokenIn to keep on the account /// @param rateMinRAY Minimum exchange rate between input and output tokens, scaled by 1e27 struct ExactDiffInputParams { bytes path; uint256 deadline; uint256 leftoverAmount; uint256 rateMinRAY; } } interface IUniswapV3AdapterEvents { /// @notice Emitted when new status is set for a pool event SetPoolStatus(address indexed token0, address indexed token1, uint24 indexed fee, bool allowed); } interface IUniswapV3AdapterExceptions { /// @notice Thrown when sanity checks on a swap path fail error InvalidPathException(); } /// @title Uniswap V3 Router adapter interface interface IUniswapV3Adapter is IAdapter, IUniswapV3AdapterTypes, IUniswapV3AdapterEvents, IUniswapV3AdapterExceptions { function exactInputSingle(ISwapRouter.ExactInputSingleParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); function exactDiffInputSingle(ExactDiffInputSingleParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); function exactInput(ISwapRouter.ExactInputParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); function exactDiffInput(ExactDiffInputParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); function exactOutputSingle(ISwapRouter.ExactOutputSingleParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); function exactOutput(ISwapRouter.ExactOutputParams calldata params) external returns (uint256 tokensToEnable, uint256 tokensToDisable); // ------------- // // CONFIGURATION // // ------------- // function isPoolAllowed(address token0, address token1, uint24 fee) external view returns (bool); function setPoolStatusBatch(UniswapV3PoolStatus[] calldata pools) external; }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.0; import { AdapterType } from "@gearbox-protocol/sdk-gov/contracts/AdapterType.sol"; /// @title Adapter interface interface IAdapter { function _gearboxAdapterType() external view returns (AdapterType); function _gearboxAdapterVersion() external view returns (uint16); function creditManager() external view returns (address); function addressProvider() external view returns (address); function targetContract() external view returns (address); }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IVersion} from "@gearbox-protocol/core-v2/contracts/interfaces/IVersion.sol"; uint8 constant BOT_PERMISSIONS_SET_FLAG = 1; uint8 constant DEFAULT_MAX_ENABLED_TOKENS = 4; address constant INACTIVE_CREDIT_ACCOUNT_ADDRESS = address(1); /// @notice Debt management type /// - `INCREASE_DEBT` borrows additional funds from the pool, updates account's debt and cumulative interest index /// - `DECREASE_DEBT` repays debt components (quota interest and fees -> base interest and fees -> debt principal) /// and updates all corresponding state varibles (base interest index, quota interest and fees, debt). /// When repaying all the debt, ensures that account has no enabled quotas. enum ManageDebtAction { INCREASE_DEBT, DECREASE_DEBT } /// @notice Collateral/debt calculation mode /// - `GENERIC_PARAMS` returns generic data like account debt and cumulative indexes /// - `DEBT_ONLY` is same as `GENERIC_PARAMS` but includes more detailed debt info, like accrued base/quota /// interest and fees /// - `FULL_COLLATERAL_CHECK_LAZY` checks whether account is sufficiently collateralized in a lazy fashion, /// i.e. it stops iterating over collateral tokens once TWV reaches the desired target. /// Since it may return underestimated TWV, it's only available for internal use. /// - `DEBT_COLLATERAL` is same as `DEBT_ONLY` but also returns total value and total LT-weighted value of /// account's tokens, this mode is used during account liquidation /// - `DEBT_COLLATERAL_SAFE_PRICES` is same as `DEBT_COLLATERAL` but uses safe prices from price oracle enum CollateralCalcTask { GENERIC_PARAMS, DEBT_ONLY, FULL_COLLATERAL_CHECK_LAZY, DEBT_COLLATERAL, DEBT_COLLATERAL_SAFE_PRICES } struct CreditAccountInfo { uint256 debt; uint256 cumulativeIndexLastUpdate; uint128 cumulativeQuotaInterest; uint128 quotaFees; uint256 enabledTokensMask; uint16 flags; uint64 lastDebtUpdate; address borrower; } struct CollateralDebtData { uint256 debt; uint256 cumulativeIndexNow; uint256 cumulativeIndexLastUpdate; uint128 cumulativeQuotaInterest; uint256 accruedInterest; uint256 accruedFees; uint256 totalDebtUSD; uint256 totalValue; uint256 totalValueUSD; uint256 twvUSD; uint256 enabledTokensMask; uint256 quotedTokensMask; address[] quotedTokens; address _poolQuotaKeeper; } struct CollateralTokenData { address token; uint16 ltInitial; uint16 ltFinal; uint40 timestampRampStart; uint24 rampDuration; } struct RevocationPair { address spender; address token; } interface ICreditManagerV3Events { /// @notice Emitted when new credit configurator is set event SetCreditConfigurator(address indexed newConfigurator); } /// @title Credit manager V3 interface interface ICreditManagerV3 is IVersion, ICreditManagerV3Events { function pool() external view returns (address); function underlying() external view returns (address); function creditFacade() external view returns (address); function creditConfigurator() external view returns (address); function addressProvider() external view returns (address); function accountFactory() external view returns (address); function name() external view returns (string memory); // ------------------ // // ACCOUNT MANAGEMENT // // ------------------ // function openCreditAccount(address onBehalfOf) external returns (address); function closeCreditAccount(address creditAccount) external; function liquidateCreditAccount( address creditAccount, CollateralDebtData calldata collateralDebtData, address to, bool isExpired ) external returns (uint256 remainingFunds, uint256 loss); function manageDebt(address creditAccount, uint256 amount, uint256 enabledTokensMask, ManageDebtAction action) external returns (uint256 newDebt, uint256 tokensToEnable, uint256 tokensToDisable); function addCollateral(address payer, address creditAccount, address token, uint256 amount) external returns (uint256 tokensToEnable); function withdrawCollateral(address creditAccount, address token, uint256 amount, address to) external returns (uint256 tokensToDisable); function externalCall(address creditAccount, address target, bytes calldata callData) external returns (bytes memory result); function approveToken(address creditAccount, address token, address spender, uint256 amount) external; function revokeAdapterAllowances(address creditAccount, RevocationPair[] calldata revocations) external; // -------- // // ADAPTERS // // -------- // function adapterToContract(address adapter) external view returns (address targetContract); function contractToAdapter(address targetContract) external view returns (address adapter); function execute(bytes calldata data) external returns (bytes memory result); function approveCreditAccount(address token, uint256 amount) external; function setActiveCreditAccount(address creditAccount) external; function getActiveCreditAccountOrRevert() external view returns (address creditAccount); // ----------------- // // COLLATERAL CHECKS // // ----------------- // function priceOracle() external view returns (address); function fullCollateralCheck( address creditAccount, uint256 enabledTokensMask, uint256[] calldata collateralHints, uint16 minHealthFactor, bool useSafePrices ) external returns (uint256 enabledTokensMaskAfter); function isLiquidatable(address creditAccount, uint16 minHealthFactor) external view returns (bool); function calcDebtAndCollateral(address creditAccount, CollateralCalcTask task) external view returns (CollateralDebtData memory cdd); // ------ // // QUOTAS // // ------ // function poolQuotaKeeper() external view returns (address); function quotedTokensMask() external view returns (uint256); function updateQuota(address creditAccount, address token, int96 quotaChange, uint96 minQuota, uint96 maxQuota) external returns (uint256 tokensToEnable, uint256 tokensToDisable); // --------------------- // // CREDIT MANAGER PARAMS // // --------------------- // function maxEnabledTokens() external view returns (uint8); function fees() external view returns ( uint16 feeInterest, uint16 feeLiquidation, uint16 liquidationDiscount, uint16 feeLiquidationExpired, uint16 liquidationDiscountExpired ); function collateralTokensCount() external view returns (uint8); function getTokenMaskOrRevert(address token) external view returns (uint256 tokenMask); function getTokenByMask(uint256 tokenMask) external view returns (address token); function liquidationThresholds(address token) external view returns (uint16 lt); function ltParams(address token) external view returns (uint16 ltInitial, uint16 ltFinal, uint40 timestampRampStart, uint24 rampDuration); function collateralTokenByMask(uint256 tokenMask) external view returns (address token, uint16 liquidationThreshold); // ------------ // // ACCOUNT INFO // // ------------ // function creditAccountInfo(address creditAccount) external view returns ( uint256 debt, uint256 cumulativeIndexLastUpdate, uint128 cumulativeQuotaInterest, uint128 quotaFees, uint256 enabledTokensMask, uint16 flags, uint64 lastDebtUpdate, address borrower ); function getBorrowerOrRevert(address creditAccount) external view returns (address borrower); function flagsOf(address creditAccount) external view returns (uint16); function setFlagFor(address creditAccount, uint16 flag, bool value) external; function enabledTokensMaskOf(address creditAccount) external view returns (uint256); function creditAccounts() external view returns (address[] memory); function creditAccounts(uint256 offset, uint256 limit) external view returns (address[] memory); function creditAccountsLen() external view returns (uint256); // ------------- // // CONFIGURATION // // ------------- // function addToken(address token) external; function setCollateralTokenData( address token, uint16 ltInitial, uint16 ltFinal, uint40 timestampRampStart, uint24 rampDuration ) external; function setFees( uint16 feeInterest, uint16 feeLiquidation, uint16 liquidationDiscount, uint16 feeLiquidationExpired, uint16 liquidationDiscountExpired ) external; function setQuotedMask(uint256 quotedTokensMask) external; function setMaxEnabledTokens(uint8 maxEnabledTokens) external; function setContractAllowance(address adapter, address targetContract) external; function setCreditFacade(address creditFacade) external; function setPriceOracle(address priceOracle) external; function setCreditConfigurator(address creditConfigurator) external; }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; // ------- // // GENERAL // // ------- // /// @notice Thrown on attempting to set an important address to zero address error ZeroAddressException(); /// @notice Thrown when attempting to pass a zero amount to a funding-related operation error AmountCantBeZeroException(); /// @notice Thrown on incorrect input parameter error IncorrectParameterException(); /// @notice Thrown when balance is insufficient to perform an operation error InsufficientBalanceException(); /// @notice Thrown if parameter is out of range error ValueOutOfRangeException(); /// @notice Thrown when trying to send ETH to a contract that is not allowed to receive ETH directly error ReceiveIsNotAllowedException(); /// @notice Thrown on attempting to set an EOA as an important contract in the system error AddressIsNotContractException(address); /// @notice Thrown on attempting to receive a token that is not a collateral token or was forbidden error TokenNotAllowedException(); /// @notice Thrown on attempting to add a token that is already in a collateral list error TokenAlreadyAddedException(); /// @notice Thrown when attempting to use quota-related logic for a token that is not quoted in quota keeper error TokenIsNotQuotedException(); /// @notice Thrown on attempting to interact with an address that is not a valid target contract error TargetContractNotAllowedException(); /// @notice Thrown if function is not implemented error NotImplementedException(); // ------------------ // // CONTRACTS REGISTER // // ------------------ // /// @notice Thrown when an address is expected to be a registered credit manager, but is not error RegisteredCreditManagerOnlyException(); /// @notice Thrown when an address is expected to be a registered pool, but is not error RegisteredPoolOnlyException(); // ---------------- // // ADDRESS PROVIDER // // ---------------- // /// @notice Reverts if address key isn't found in address provider error AddressNotFoundException(); // ----------------- // // POOL, PQK, GAUGES // // ----------------- // /// @notice Thrown by pool-adjacent contracts when a credit manager being connected has a wrong pool address error IncompatibleCreditManagerException(); /// @notice Thrown when attempting to set an incompatible successor staking contract error IncompatibleSuccessorException(); /// @notice Thrown when attempting to vote in a non-approved contract error VotingContractNotAllowedException(); /// @notice Thrown when attempting to unvote more votes than there are error InsufficientVotesException(); /// @notice Thrown when attempting to borrow more than the second point on a two-point curve error BorrowingMoreThanU2ForbiddenException(); /// @notice Thrown when a credit manager attempts to borrow more than its limit in the current block, or in general error CreditManagerCantBorrowException(); /// @notice Thrown when attempting to connect a quota keeper to an incompatible pool error IncompatiblePoolQuotaKeeperException(); /// @notice Thrown when the quota is outside of min/max bounds error QuotaIsOutOfBoundsException(); // -------------- // // CREDIT MANAGER // // -------------- // /// @notice Thrown on failing a full collateral check after multicall error NotEnoughCollateralException(); /// @notice Thrown if an attempt to approve a collateral token to adapter's target contract fails error AllowanceFailedException(); /// @notice Thrown on attempting to perform an action for a credit account that does not exist error CreditAccountDoesNotExistException(); /// @notice Thrown on configurator attempting to add more than 255 collateral tokens error TooManyTokensException(); /// @notice Thrown if more than the maximum number of tokens were enabled on a credit account error TooManyEnabledTokensException(); /// @notice Thrown when attempting to execute a protocol interaction without active credit account set error ActiveCreditAccountNotSetException(); /// @notice Thrown when trying to update credit account's debt more than once in the same block error DebtUpdatedTwiceInOneBlockException(); /// @notice Thrown when trying to repay all debt while having active quotas error DebtToZeroWithActiveQuotasException(); /// @notice Thrown when a zero-debt account attempts to update quota error UpdateQuotaOnZeroDebtAccountException(); /// @notice Thrown when attempting to close an account with non-zero debt error CloseAccountWithNonZeroDebtException(); /// @notice Thrown when value of funds remaining on the account after liquidation is insufficient error InsufficientRemainingFundsException(); /// @notice Thrown when Credit Facade tries to write over a non-zero active Credit Account error ActiveCreditAccountOverridenException(); // ------------------- // // CREDIT CONFIGURATOR // // ------------------- // /// @notice Thrown on attempting to use a non-ERC20 contract or an EOA as a token error IncorrectTokenContractException(); /// @notice Thrown if the newly set LT if zero or greater than the underlying's LT error IncorrectLiquidationThresholdException(); /// @notice Thrown if borrowing limits are incorrect: minLimit > maxLimit or maxLimit > blockLimit error IncorrectLimitsException(); /// @notice Thrown if the new expiration date is less than the current expiration date or current timestamp error IncorrectExpirationDateException(); /// @notice Thrown if a contract returns a wrong credit manager or reverts when trying to retrieve it error IncompatibleContractException(); /// @notice Thrown if attempting to forbid an adapter that is not registered in the credit manager error AdapterIsNotRegisteredException(); /// @notice Thrown when trying to manually set total debt parameters in a credit facade that doesn't track them error TotalDebtNotTrackedException(); // ------------- // // CREDIT FACADE // // ------------- // /// @notice Thrown when attempting to perform an action that is forbidden in whitelisted mode error ForbiddenInWhitelistedModeException(); /// @notice Thrown if credit facade is not expirable, and attempted aciton requires expirability error NotAllowedWhenNotExpirableException(); /// @notice Thrown if a selector that doesn't match any allowed function is passed to the credit facade in a multicall error UnknownMethodException(); /// @notice Thrown when trying to close an account with enabled tokens error CloseAccountWithEnabledTokensException(); /// @notice Thrown if a liquidator tries to liquidate an account with a health factor above 1 error CreditAccountNotLiquidatableException(); /// @notice Thrown if too much new debt was taken within a single block error BorrowedBlockLimitException(); /// @notice Thrown if the new debt principal for a credit account falls outside of borrowing limits error BorrowAmountOutOfLimitsException(); /// @notice Thrown if a user attempts to open an account via an expired credit facade error NotAllowedAfterExpirationException(); /// @notice Thrown if expected balances are attempted to be set twice without performing a slippage check error ExpectedBalancesAlreadySetException(); /// @notice Thrown if attempting to perform a slippage check when excepted balances are not set error ExpectedBalancesNotSetException(); /// @notice Thrown if balance of at least one token is less than expected during a slippage check error BalanceLessThanExpectedException(); /// @notice Thrown when trying to perform an action that is forbidden when credit account has enabled forbidden tokens error ForbiddenTokensException(); /// @notice Thrown when new forbidden tokens are enabled during the multicall error ForbiddenTokenEnabledException(); /// @notice Thrown when enabled forbidden token balance is increased during the multicall error ForbiddenTokenBalanceIncreasedException(); /// @notice Thrown when the remaining token balance is increased during the liquidation error RemainingTokenBalanceIncreasedException(); /// @notice Thrown if `botMulticall` is called by an address that is not approved by account owner or is forbidden error NotApprovedBotException(); /// @notice Thrown when attempting to perform a multicall action with no permission for it error NoPermissionException(uint256 permission); /// @notice Thrown when attempting to give a bot unexpected permissions error UnexpectedPermissionsException(); /// @notice Thrown when a custom HF parameter lower than 10000 is passed into the full collateral check error CustomHealthFactorTooLowException(); /// @notice Thrown when submitted collateral hint is not a valid token mask error InvalidCollateralHintException(); // ------ // // ACCESS // // ------ // /// @notice Thrown on attempting to call an access restricted function not as credit account owner error CallerNotCreditAccountOwnerException(); /// @notice Thrown on attempting to call an access restricted function not as configurator error CallerNotConfiguratorException(); /// @notice Thrown on attempting to call an access-restructed function not as account factory error CallerNotAccountFactoryException(); /// @notice Thrown on attempting to call an access restricted function not as credit manager error CallerNotCreditManagerException(); /// @notice Thrown on attempting to call an access restricted function not as credit facade error CallerNotCreditFacadeException(); /// @notice Thrown on attempting to call an access restricted function not as controller or configurator error CallerNotControllerException(); /// @notice Thrown on attempting to pause a contract without pausable admin rights error CallerNotPausableAdminException(); /// @notice Thrown on attempting to unpause a contract without unpausable admin rights error CallerNotUnpausableAdminException(); /// @notice Thrown on attempting to call an access restricted function not as gauge error CallerNotGaugeException(); /// @notice Thrown on attempting to call an access restricted function not as quota keeper error CallerNotPoolQuotaKeeperException(); /// @notice Thrown on attempting to call an access restricted function not as voter error CallerNotVoterException(); /// @notice Thrown on attempting to call an access restricted function not as allowed adapter error CallerNotAdapterException(); /// @notice Thrown on attempting to call an access restricted function not as migrator error CallerNotMigratorException(); /// @notice Thrown when an address that is not the designated executor attempts to execute a transaction error CallerNotExecutorException(); /// @notice Thrown on attempting to call an access restricted function not as veto admin error CallerNotVetoAdminException(); // ------------------- // // CONTROLLER TIMELOCK // // ------------------- // /// @notice Thrown when the new parameter values do not satisfy required conditions error ParameterChecksFailedException(); /// @notice Thrown when attempting to execute a non-queued transaction error TxNotQueuedException(); /// @notice Thrown when attempting to execute a transaction that is either immature or stale error TxExecutedOutsideTimeWindowException(); /// @notice Thrown when execution of a transaction fails error TxExecutionRevertedException(); /// @notice Thrown when the value of a parameter on execution is different from the value on queue error ParameterChangedAfterQueuedTxException(); // -------- // // BOT LIST // // -------- // /// @notice Thrown when attempting to set non-zero permissions for a forbidden or special bot error InvalidBotException(); // --------------- // // ACCOUNT FACTORY // // --------------- // /// @notice Thrown when trying to deploy second master credit account for a credit manager error MasterCreditAccountAlreadyDeployedException(); /// @notice Thrown when trying to rescue funds from a credit account that is currently in use error CreditAccountIsInUseException(); // ------------ // // PRICE ORACLE // // ------------ // /// @notice Thrown on attempting to set a token price feed to an address that is not a correct price feed error IncorrectPriceFeedException(); /// @notice Thrown on attempting to interact with a price feed for a token not added to the price oracle error PriceFeedDoesNotExistException(); /// @notice Thrown when price feed returns incorrect price for a token error IncorrectPriceException(); /// @notice Thrown when token's price feed becomes stale error StalePriceException();
// SPDX-License-Identifier: BUSL-1.1 // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IACL} from "@gearbox-protocol/core-v2/contracts/interfaces/IACL.sol"; import {AP_ACL, IAddressProviderV3, NO_VERSION_CONTROL} from "../interfaces/IAddressProviderV3.sol"; import {CallerNotConfiguratorException} from "../interfaces/IExceptions.sol"; import {SanityCheckTrait} from "./SanityCheckTrait.sol"; /// @title ACL trait /// @notice Utility class for ACL (access-control list) consumers abstract contract ACLTrait is SanityCheckTrait { /// @notice ACL contract address address public immutable acl; /// @notice Constructor /// @param addressProvider Address provider contract address constructor(address addressProvider) nonZeroAddress(addressProvider) { acl = IAddressProviderV3(addressProvider).getAddressOrRevert(AP_ACL, NO_VERSION_CONTROL); } /// @dev Ensures that function caller has configurator role modifier configuratorOnly() { _ensureCallerIsConfigurator(); _; } /// @dev Reverts if the caller is not the configurator /// @dev Used to cut contract size on modifiers function _ensureCallerIsConfigurator() internal view { if (!_isConfigurator({account: msg.sender})) { revert CallerNotConfiguratorException(); } } /// @dev Checks whether given account has configurator role function _isConfigurator(address account) internal view returns (bool) { return IACL(acl).isConfigurator(account); } }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Holdings, 2022 pragma solidity ^0.8.10; /// @title Version interface /// @notice Defines contract version interface IVersion { /// @notice Contract version function version() external view returns (uint256); }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Holdings, 2022 pragma solidity ^0.8.10; import { IVersion } from "./IVersion.sol"; interface IACLExceptions { /// @dev Thrown when attempting to delete an address from a set that is not a pausable admin error AddressNotPausableAdminException(address addr); /// @dev Thrown when attempting to delete an address from a set that is not a unpausable admin error AddressNotUnpausableAdminException(address addr); } interface IACLEvents { /// @dev Emits when a new admin is added that can pause contracts event PausableAdminAdded(address indexed newAdmin); /// @dev Emits when a Pausable admin is removed event PausableAdminRemoved(address indexed admin); /// @dev Emits when a new admin is added that can unpause contracts event UnpausableAdminAdded(address indexed newAdmin); /// @dev Emits when an Unpausable admin is removed event UnpausableAdminRemoved(address indexed admin); } /// @title ACL interface interface IACL is IACLEvents, IACLExceptions, IVersion { /// @dev Returns true if the address is a pausable admin and false if not /// @param addr Address to check function isPausableAdmin(address addr) external view returns (bool); /// @dev Returns true if the address is unpausable admin and false if not /// @param addr Address to check function isUnpausableAdmin(address addr) external view returns (bool); /// @dev Returns true if an address has configurator rights /// @param account Address to check function isConfigurator(address account) external view returns (bool); /// @dev Returns address of configurator function owner() external view returns (address); }
// SPDX-License-Identifier: MIT // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {IVersion} from "@gearbox-protocol/core-v2/contracts/interfaces/IVersion.sol"; uint256 constant NO_VERSION_CONTROL = 0; bytes32 constant AP_CONTRACTS_REGISTER = "CONTRACTS_REGISTER"; bytes32 constant AP_ACL = "ACL"; bytes32 constant AP_PRICE_ORACLE = "PRICE_ORACLE"; bytes32 constant AP_ACCOUNT_FACTORY = "ACCOUNT_FACTORY"; bytes32 constant AP_DATA_COMPRESSOR = "DATA_COMPRESSOR"; bytes32 constant AP_TREASURY = "TREASURY"; bytes32 constant AP_GEAR_TOKEN = "GEAR_TOKEN"; bytes32 constant AP_WETH_TOKEN = "WETH_TOKEN"; bytes32 constant AP_WETH_GATEWAY = "WETH_GATEWAY"; bytes32 constant AP_ROUTER = "ROUTER"; bytes32 constant AP_BOT_LIST = "BOT_LIST"; bytes32 constant AP_GEAR_STAKING = "GEAR_STAKING"; bytes32 constant AP_ZAPPER_REGISTER = "ZAPPER_REGISTER"; interface IAddressProviderV3Events { /// @notice Emitted when an address is set for a contract key event SetAddress(bytes32 indexed key, address indexed value, uint256 indexed version); } /// @title Address provider V3 interface interface IAddressProviderV3 is IAddressProviderV3Events, IVersion { function addresses(bytes32 key, uint256 _version) external view returns (address); function getAddressOrRevert(bytes32 key, uint256 _version) external view returns (address result); function setAddress(bytes32 key, address value, bool saveVersion) external; }
// SPDX-License-Identifier: BUSL-1.1 // Gearbox Protocol. Generalized leverage for DeFi protocols // (c) Gearbox Foundation, 2023. pragma solidity ^0.8.17; import {ZeroAddressException} from "../interfaces/IExceptions.sol"; /// @title Sanity check trait abstract contract SanityCheckTrait { /// @dev Ensures that passed address is non-zero modifier nonZeroAddress(address addr) { _revertIfZeroAddress(addr); _; } /// @dev Reverts if address is zero function _revertIfZeroAddress(address addr) private pure { if (addr == address(0)) revert ZeroAddressException(); } }
{ "remappings": [ "@1inch/=node_modules/@1inch/", "@chainlink/=node_modules/@chainlink/", "@eth-optimism/=node_modules/@eth-optimism/", "@gearbox-protocol/=node_modules/@gearbox-protocol/", "@openzeppelin/=node_modules/@openzeppelin/", "@redstone-finance/=node_modules/@redstone-finance/", "ds-test/=lib/forge-std/lib/ds-test/src/", "eth-gas-reporter/=node_modules/eth-gas-reporter/", "forge-std/=lib/forge-std/src/" ], "optimizer": { "enabled": true, "runs": 1000 }, "metadata": { "useLiteralContent": false, "bytecodeHash": "ipfs" }, "outputSelection": { "*": { "*": [ "evm.bytecode", "evm.deployedBytecode", "devdoc", "userdoc", "metadata", "abi" ] } }, "evmVersion": "london", "libraries": {} }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"address","name":"_creditManager","type":"address"},{"internalType":"address","name":"_router","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"CallerNotConfiguratorException","type":"error"},{"inputs":[],"name":"CallerNotCreditFacadeException","type":"error"},{"inputs":[],"name":"InvalidPathException","type":"error"},{"inputs":[],"name":"ZeroAddressException","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"token0","type":"address"},{"indexed":true,"internalType":"address","name":"token1","type":"address"},{"indexed":true,"internalType":"uint24","name":"fee","type":"uint24"},{"indexed":false,"internalType":"bool","name":"allowed","type":"bool"}],"name":"SetPoolStatus","type":"event"},{"inputs":[],"name":"_gearboxAdapterType","outputs":[{"internalType":"enum AdapterType","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"_gearboxAdapterVersion","outputs":[{"internalType":"uint16","name":"","type":"uint16"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"acl","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"addressProvider","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"creditManager","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"components":[{"internalType":"bytes","name":"path","type":"bytes"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"leftoverAmount","type":"uint256"},{"internalType":"uint256","name":"rateMinRAY","type":"uint256"}],"internalType":"struct IUniswapV3AdapterTypes.ExactDiffInputParams","name":"params","type":"tuple"}],"name":"exactDiffInput","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"tokenIn","type":"address"},{"internalType":"address","name":"tokenOut","type":"address"},{"internalType":"uint24","name":"fee","type":"uint24"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"leftoverAmount","type":"uint256"},{"internalType":"uint256","name":"rateMinRAY","type":"uint256"},{"internalType":"uint160","name":"sqrtPriceLimitX96","type":"uint160"}],"internalType":"struct IUniswapV3AdapterTypes.ExactDiffInputSingleParams","name":"params","type":"tuple"}],"name":"exactDiffInputSingle","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"bytes","name":"path","type":"bytes"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"amountIn","type":"uint256"},{"internalType":"uint256","name":"amountOutMinimum","type":"uint256"}],"internalType":"struct ISwapRouter.ExactInputParams","name":"params","type":"tuple"}],"name":"exactInput","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"tokenIn","type":"address"},{"internalType":"address","name":"tokenOut","type":"address"},{"internalType":"uint24","name":"fee","type":"uint24"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"amountIn","type":"uint256"},{"internalType":"uint256","name":"amountOutMinimum","type":"uint256"},{"internalType":"uint160","name":"sqrtPriceLimitX96","type":"uint160"}],"internalType":"struct ISwapRouter.ExactInputSingleParams","name":"params","type":"tuple"}],"name":"exactInputSingle","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"bytes","name":"path","type":"bytes"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"amountOut","type":"uint256"},{"internalType":"uint256","name":"amountInMaximum","type":"uint256"}],"internalType":"struct ISwapRouter.ExactOutputParams","name":"params","type":"tuple"}],"name":"exactOutput","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"tokenIn","type":"address"},{"internalType":"address","name":"tokenOut","type":"address"},{"internalType":"uint24","name":"fee","type":"uint24"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"deadline","type":"uint256"},{"internalType":"uint256","name":"amountOut","type":"uint256"},{"internalType":"uint256","name":"amountInMaximum","type":"uint256"},{"internalType":"uint160","name":"sqrtPriceLimitX96","type":"uint160"}],"internalType":"struct ISwapRouter.ExactOutputSingleParams","name":"params","type":"tuple"}],"name":"exactOutputSingle","outputs":[{"internalType":"uint256","name":"tokensToEnable","type":"uint256"},{"internalType":"uint256","name":"tokensToDisable","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"token0","type":"address"},{"internalType":"address","name":"token1","type":"address"},{"internalType":"uint24","name":"fee","type":"uint24"}],"name":"isPoolAllowed","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"token0","type":"address"},{"internalType":"address","name":"token1","type":"address"},{"internalType":"uint24","name":"fee","type":"uint24"},{"internalType":"bool","name":"allowed","type":"bool"}],"internalType":"struct UniswapV3PoolStatus[]","name":"pools","type":"tuple[]"}],"name":"setPoolStatusBatch","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"targetContract","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"}]
Contract Creation Code
6101006040523480156200001257600080fd5b5060405162001dbe38038062001dbe833981016040819052620000359162000214565b8181816001600160a01b0316632954018c6040518163ffffffff1660e01b8152600401602060405180830381865afa15801562000076573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200009c91906200024c565b80620000a881620001cc565b604051632bdad0e360e11b8152621050d360ea1b6004820152600060248201526001600160a01b038316906357b5a1c690604401602060405180830381865afa158015620000fa573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200012091906200024c565b6001600160a01b0316608052508190506200013b81620001cc565b6001600160a01b03831660a081905260408051630a55006360e21b81529051632954018c916004808201926020929091908290030181865afa15801562000186573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001ac91906200024c565b6001600160a01b0390811660c0529190911660e052506200027192505050565b6001600160a01b038116620001f457604051635919af9760e11b815260040160405180910390fd5b50565b80516001600160a01b03811681146200020f57600080fd5b919050565b600080604083850312156200022857600080fd5b6200023383620001f7565b91506200024360208401620001f7565b90509250929050565b6000602082840312156200025f57600080fd5b6200026a82620001f7565b9392505050565b60805160a05160c05160e051611aea620002d460003960006101da0152600060f401526000818161021401528181610ba701528181610c7701528181610fc80152818161107a015261110d01526000818161026301526111c40152611aea6000f3fe608060405234801561001057600080fd5b50600436106100ea5760003560e01c8063bd90df701161008c578063ce30bbdb11610066578063ce30bbdb14610236578063db3e21981461024b578063de2873591461025e578063f28c04981461028557600080fd5b8063bd90df70146101d5578063c04b8d59146101fc578063c12c21c01461020f57600080fd5b80634a7c7f98116100c85780634a7c7f981461016e578063604ccd66146101915780636161dc85146101a657806378aa73a4146101b957600080fd5b80632954018c146100ef57806336f4e22814610133578063414bf3891461015b575b600080fd5b6101167f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b61014661014136600461136c565b610298565b6040805192835260208301919091520161012a565b610146610169366004611397565b610490565b61018161017c3660046113f6565b610538565b604051901515815260200161012a565b6101a461019f36600461143d565b610585565b005b6101466101b43660046114b2565b610749565b6101c261012c81565b60405161ffff909116815260200161012a565b6101167f000000000000000000000000000000000000000000000000000000000000000081565b61014661020a3660046114ff565b610962565b6101167f000000000000000000000000000000000000000000000000000000000000000081565b61023e600281565b60405161012a919061153c565b610146610259366004611397565b610a25565b6101167f000000000000000000000000000000000000000000000000000000000000000081565b6101466102933660046114ff565b610ad9565b6000806102a3610ba5565b60006102ad610c73565b905060006102be6020860186611564565b6040516370a0823160e01b81526001600160a01b03848116600483015291909116906370a0823190602401602060405180830381865afa158015610306573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061032a9190611581565b905084608001358111610344575060009485945092505050565b6040805161010081019091526080860135909103906000908061036a6020890189611564565b6001600160a01b0316815260200187602001602081019061038b9190611564565b6001600160a01b031681526020016103a96060890160408a0161159a565b62ffffff1681526001600160a01b0385166020820152606080890135604083015281018490526080016b033b2e3c9fd0803ce80000006103ed60a08a0135866115cb565b6103f791906115e2565b815260200161040c60e0890160c08a01611564565b6001600160a01b0316905290506104826104296020880188611564565b6104396040890160208a01611564565b8360405160240161044a9190611604565b60408051601f198184030181529190526020810180516001600160e01b031663414bf38960e01b179052600160808b01351115610cfc565b509095509350505050915091565b60008061049b610ba5565b60006104a5610c73565b905060006104b83686900386018661179a565b6001600160a01b0383166060820152905061052b6104d96020870187611564565b6104e96040880160208901611564565b836040516024016104fa9190611604565b60408051601f198184030181529190526020810180516001600160e01b031663414bf38960e01b1790526000610cfc565b5090969095509350505050565b60006105448484610d4a565b6001600160a01b0391821660009081526020818152604080832093909416825291825282812062ffffff9590951681529390529091205460ff169392505050565b61058d610d7e565b8060005b81811015610743576000806105f68686858181106105b1576105b16117b7565b6105c79260206080909202019081019150611564565b8787868181106105d9576105d96117b7565b90506080020160200160208101906105f19190611564565b610d4a565b9150915085858481811061060c5761060c6117b7565b905060800201606001602081019061062491906117db565b6001600160a01b0380841660009081526020818152604080832093861683529290529081209088888781811061065c5761065c6117b7565b9050608002016040016020810190610674919061159a565b62ffffff1681526020810191909152604001600020805460ff19169115159190911790558585848181106106aa576106aa6117b7565b90506080020160400160208101906106c2919061159a565b62ffffff16816001600160a01b0316836001600160a01b03167f09b440dc899072eb0be503cd79f97ae39c2716cfe43d617871aea507b19df4e989898881811061070e5761070e6117b7565b905060800201606001602081019061072691906117db565b604051901515815260200160405180910390a45050600101610591565b50505050565b600080610754610ba5565b600061075e610c73565b9050600080806107ab61077188806117f8565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610dbd92505050565b925092509250826107cf57604051635d883f4360e11b815260040160405180910390fd5b6040516370a0823160e01b81526001600160a01b038581166004830152600091908416906370a0823190602401602060405180830381865afa158015610819573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061083d9190611581565b90508760400135811161085a575060009788975095505050505050565b6040805160a08101825290890135909103906000908061087a8b806117f8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152505050908252506001600160a01b0388166020808301919091528b0135604082015260608082018590526080909101906b033b2e3c9fd0803ce8000000906108f5908d0135866115cb565b6108ff91906115e2565b815250905061095184848360405160240161091a91906118e1565b60408051601f198184030181529181526020820180516001600160e01b031663c04b8d5960e01b1790526001908e01351115610cfc565b509098509650505050505050915091565b60008061096d610ba5565b6000610977610c73565b90506000808061098a61077188806117f8565b925092509250826109ae57604051635d883f4360e11b815260040160405180910390fd5b60006109b9886119d1565b6001600160a01b0386166020820152604051909150610a1590849084906109e49085906024016118e1565b60408051601f198184030181529190526020810180516001600160e01b031663c04b8d5960e01b1790526000610cfc565b5090999098509650505050505050565b600080610a30610ba5565b6000610a3a610c73565b90506000610a4d3686900386018661179a565b6001600160a01b0383166060820152905061052b610a6e6020870187611564565b610a7e6040880160208901611564565b83604051602401610a8f9190611604565b60408051601f198184030181529190526020810180516001600160e01b03167fdb3e2198000000000000000000000000000000000000000000000000000000001790526000610cfc565b600080610ae4610ba5565b6000610aee610c73565b905060008080610b0161077188806117f8565b92509250925082610b2557604051635d883f4360e11b815260040160405180910390fd5b6000610b30886119d1565b6001600160a01b0386166020820152604051909150610a159083908590610b5b9085906024016118e1565b60408051601f198184030181529190526020810180516001600160e01b03167ff28c0498000000000000000000000000000000000000000000000000000000001790526000610cfc565b7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316632f7a18816040518163ffffffff1660e01b8152600401602060405180830381865afa158015610c03573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c2791906119dd565b6001600160a01b0316336001600160a01b031614610c71576040517f0c1d6a3f00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03166334878f546040518163ffffffff1660e01b8152600401602060405180830381865afa158015610cd3573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610cf791906119dd565b905090565b6000806060610d0a86610f8d565b92508315610d1e57610d1b87610f8d565b91505b610d2a8760001961103b565b610d33856110da565b9050610d4087600161103b565b9450945094915050565b600080826001600160a01b0316846001600160a01b03161015610d71575082905081610d77565b50819050825b9250929050565b610d8733611189565b610c71576040517f61081c1500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8051600090819081906003610dd4601460026115cb565b610dde91906119fa565b8114158015610e0e5750610df4600360026115cb565b610e00601460036115cb565b610e0a91906119fa565b8114155b8015610e3a5750610e206003806115cb565b610e2c601460046115cb565b610e3691906119fa565b8114155b15610e49576000935050610f86565b610e54856000611231565b92506000610e638660146112ac565b9050610e7b610e74600360146119fa565b8790611231565b9250610e88848483610538565b9450848015610ead57506003610ea0601460026115cb565b610eaa91906119fa565b82115b15610f835782610ed46014610ec36003826119fa565b610ecd91906119fa565b88906112ac565b9150610ef7610ee5600360146119fa565b610ef09060026115cb565b8890611231565b9350610f04818584610538565b9550858015610f335750610f1a600360026115cb565b610f26601460036115cb565b610f3091906119fa565b83115b15610f81575082610f556014610f4a6003826119fa565b610ec39060026115cb565b9150610f71610f66600360146119fa565b610ef09060036115cb565b9350610f7e818584610538565b95505b505b50505b9193909250565b6040517fd5c2f4860000000000000000000000000000000000000000000000000000000081526001600160a01b0382811660048301526000917f00000000000000000000000000000000000000000000000000000000000000009091169063d5c2f48690602401602060405180830381865afa158015611011573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110359190611581565b92915050565b6040517ffa30b30f0000000000000000000000000000000000000000000000000000000081526001600160a01b038381166004830152602482018390527f0000000000000000000000000000000000000000000000000000000000000000169063fa30b30f90604401600060405180830381600087803b1580156110be57600080fd5b505af11580156110d2573d6000803e3d6000fd5b505050505050565b6040517f09c5eabe0000000000000000000000000000000000000000000000000000000081526060906001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016906309c5eabe90611142908590600401611a0d565b6000604051808303816000875af1158015611161573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f191682016040526110359190810190611a20565b6040517f5f259aba0000000000000000000000000000000000000000000000000000000081526001600160a01b0382811660048301526000917f000000000000000000000000000000000000000000000000000000000000000090911690635f259aba90602401602060405180830381865afa15801561120d573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110359190611a97565b600061123e8260146119fa565b835110156112935760405162461bcd60e51b815260206004820152601560248201527f746f416464726573735f6f75744f66426f756e6473000000000000000000000060448201526064015b60405180910390fd5b5001602001516c01000000000000000000000000900490565b6000816112ba8160036119fa565b10156113085760405162461bcd60e51b815260206004820152601160248201527f746f55696e7432345f6f766572666c6f77000000000000000000000000000000604482015260640161128a565b6113138260036119fa565b835110156113635760405162461bcd60e51b815260206004820152601460248201527f746f55696e7432345f6f75744f66426f756e6473000000000000000000000000604482015260640161128a565b50016003015190565b600060e0828403121561137e57600080fd5b50919050565b6000610100828403121561137e57600080fd5b600061010082840312156113aa57600080fd5b6113b48383611384565b9392505050565b6001600160a01b03811681146113d057600080fd5b50565b80356113de816113bb565b919050565b803562ffffff811681146113de57600080fd5b60008060006060848603121561140b57600080fd5b8335611416816113bb565b92506020840135611426816113bb565b9150611434604085016113e3565b90509250925092565b6000806020838503121561145057600080fd5b823567ffffffffffffffff8082111561146857600080fd5b818501915085601f83011261147c57600080fd5b81358181111561148b57600080fd5b8660208260071b85010111156114a057600080fd5b60209290920196919550909350505050565b6000602082840312156114c457600080fd5b813567ffffffffffffffff8111156114db57600080fd5b8201608081850312156113b457600080fd5b600060a0828403121561137e57600080fd5b60006020828403121561151157600080fd5b813567ffffffffffffffff81111561152857600080fd5b611534848285016114ed565b949350505050565b602081016016831061155e57634e487b7160e01b600052602160045260246000fd5b91905290565b60006020828403121561157657600080fd5b81356113b4816113bb565b60006020828403121561159357600080fd5b5051919050565b6000602082840312156115ac57600080fd5b6113b4826113e3565b634e487b7160e01b600052601160045260246000fd5b8082028115828204841417611035576110356115b5565b6000826115ff57634e487b7160e01b600052601260045260246000fd5b500490565b610100810161103582846001600160a01b0380825116835280602083015116602084015262ffffff60408301511660408401528060608301511660608401526080820151608084015260a082015160a084015260c082015160c08401528060e08301511660e0840152505050565b634e487b7160e01b600052604160045260246000fd5b60405160a0810167ffffffffffffffff811182821017156116ab576116ab611672565b60405290565b604051601f8201601f1916810167ffffffffffffffff811182821017156116da576116da611672565b604052919050565b60006101008083850312156116f657600080fd5b6040519081019067ffffffffffffffff8211818310171561171957611719611672565b816040528092508335915061172d826113bb565b81815261173c602085016113d3565b602082015261174d604085016113e3565b604082015261175e606085016113d3565b60608201526080840135608082015260a084013560a082015260c084013560c082015261178d60e085016113d3565b60e0820152505092915050565b600061010082840312156117ad57600080fd5b6113b483836116e2565b634e487b7160e01b600052603260045260246000fd5b80151581146113d057600080fd5b6000602082840312156117ed57600080fd5b81356113b4816117cd565b6000808335601e1984360301811261180f57600080fd5b83018035915067ffffffffffffffff82111561182a57600080fd5b602001915036819003821315610d7757600080fd5b60005b8381101561185a578181015183820152602001611842565b50506000910152565b6000815180845261187b81602086016020860161183f565b601f01601f19169290920160200192915050565b6000815160a084526118a460a0850182611863565b90506001600160a01b0360208401511660208501526040830151604085015260608301516060850152608083015160808501528091505092915050565b6020815260006113b4602083018461188f565b600067ffffffffffffffff82111561190e5761190e611672565b50601f01601f191660200190565b600060a0828403121561192e57600080fd5b611936611688565b9050813567ffffffffffffffff81111561194f57600080fd5b8201601f8101841361196057600080fd5b80356020611975611970836118f4565b6116b1565b828152868284860101111561198957600080fd5b8282850183830137600081840183015284526119a68582016113d3565b8185015250505060408201356040820152606082013560608201526080820135608082015292915050565b6000611035368361191c565b6000602082840312156119ef57600080fd5b81516113b4816113bb565b80820180821115611035576110356115b5565b6020815260006113b46020830184611863565b600060208284031215611a3257600080fd5b815167ffffffffffffffff811115611a4957600080fd5b8201601f81018413611a5a57600080fd5b8051611a68611970826118f4565b818152856020838501011115611a7d57600080fd5b611a8e82602083016020860161183f565b95945050505050565b600060208284031215611aa957600080fd5b81516113b4816117cd56fea264697066735822122048b7223ac9fa8452d0825db48b5764539a749bcde69b941f86b1d33c248dc09c64736f6c634300081100330000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c561393556000000000000000000000000e592427a0aece92de3edee1f18e0157c05861564
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106100ea5760003560e01c8063bd90df701161008c578063ce30bbdb11610066578063ce30bbdb14610236578063db3e21981461024b578063de2873591461025e578063f28c04981461028557600080fd5b8063bd90df70146101d5578063c04b8d59146101fc578063c12c21c01461020f57600080fd5b80634a7c7f98116100c85780634a7c7f981461016e578063604ccd66146101915780636161dc85146101a657806378aa73a4146101b957600080fd5b80632954018c146100ef57806336f4e22814610133578063414bf3891461015b575b600080fd5b6101167f0000000000000000000000009ea7b04da02a5373317d745c1571c84aad03321d81565b6040516001600160a01b0390911681526020015b60405180910390f35b61014661014136600461136c565b610298565b6040805192835260208301919091520161012a565b610146610169366004611397565b610490565b61018161017c3660046113f6565b610538565b604051901515815260200161012a565b6101a461019f36600461143d565b610585565b005b6101466101b43660046114b2565b610749565b6101c261012c81565b60405161ffff909116815260200161012a565b6101167f000000000000000000000000e592427a0aece92de3edee1f18e0157c0586156481565b61014661020a3660046114ff565b610962565b6101167f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c56139355681565b61023e600281565b60405161012a919061153c565b610146610259366004611397565b610a25565b6101167f000000000000000000000000523da3a8961e4dd4f6206dbf7e6c749f51796bb381565b6101466102933660046114ff565b610ad9565b6000806102a3610ba5565b60006102ad610c73565b905060006102be6020860186611564565b6040516370a0823160e01b81526001600160a01b03848116600483015291909116906370a0823190602401602060405180830381865afa158015610306573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061032a9190611581565b905084608001358111610344575060009485945092505050565b6040805161010081019091526080860135909103906000908061036a6020890189611564565b6001600160a01b0316815260200187602001602081019061038b9190611564565b6001600160a01b031681526020016103a96060890160408a0161159a565b62ffffff1681526001600160a01b0385166020820152606080890135604083015281018490526080016b033b2e3c9fd0803ce80000006103ed60a08a0135866115cb565b6103f791906115e2565b815260200161040c60e0890160c08a01611564565b6001600160a01b0316905290506104826104296020880188611564565b6104396040890160208a01611564565b8360405160240161044a9190611604565b60408051601f198184030181529190526020810180516001600160e01b031663414bf38960e01b179052600160808b01351115610cfc565b509095509350505050915091565b60008061049b610ba5565b60006104a5610c73565b905060006104b83686900386018661179a565b6001600160a01b0383166060820152905061052b6104d96020870187611564565b6104e96040880160208901611564565b836040516024016104fa9190611604565b60408051601f198184030181529190526020810180516001600160e01b031663414bf38960e01b1790526000610cfc565b5090969095509350505050565b60006105448484610d4a565b6001600160a01b0391821660009081526020818152604080832093909416825291825282812062ffffff9590951681529390529091205460ff169392505050565b61058d610d7e565b8060005b81811015610743576000806105f68686858181106105b1576105b16117b7565b6105c79260206080909202019081019150611564565b8787868181106105d9576105d96117b7565b90506080020160200160208101906105f19190611564565b610d4a565b9150915085858481811061060c5761060c6117b7565b905060800201606001602081019061062491906117db565b6001600160a01b0380841660009081526020818152604080832093861683529290529081209088888781811061065c5761065c6117b7565b9050608002016040016020810190610674919061159a565b62ffffff1681526020810191909152604001600020805460ff19169115159190911790558585848181106106aa576106aa6117b7565b90506080020160400160208101906106c2919061159a565b62ffffff16816001600160a01b0316836001600160a01b03167f09b440dc899072eb0be503cd79f97ae39c2716cfe43d617871aea507b19df4e989898881811061070e5761070e6117b7565b905060800201606001602081019061072691906117db565b604051901515815260200160405180910390a45050600101610591565b50505050565b600080610754610ba5565b600061075e610c73565b9050600080806107ab61077188806117f8565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610dbd92505050565b925092509250826107cf57604051635d883f4360e11b815260040160405180910390fd5b6040516370a0823160e01b81526001600160a01b038581166004830152600091908416906370a0823190602401602060405180830381865afa158015610819573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061083d9190611581565b90508760400135811161085a575060009788975095505050505050565b6040805160a08101825290890135909103906000908061087a8b806117f8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152505050908252506001600160a01b0388166020808301919091528b0135604082015260608082018590526080909101906b033b2e3c9fd0803ce8000000906108f5908d0135866115cb565b6108ff91906115e2565b815250905061095184848360405160240161091a91906118e1565b60408051601f198184030181529181526020820180516001600160e01b031663c04b8d5960e01b1790526001908e01351115610cfc565b509098509650505050505050915091565b60008061096d610ba5565b6000610977610c73565b90506000808061098a61077188806117f8565b925092509250826109ae57604051635d883f4360e11b815260040160405180910390fd5b60006109b9886119d1565b6001600160a01b0386166020820152604051909150610a1590849084906109e49085906024016118e1565b60408051601f198184030181529190526020810180516001600160e01b031663c04b8d5960e01b1790526000610cfc565b5090999098509650505050505050565b600080610a30610ba5565b6000610a3a610c73565b90506000610a4d3686900386018661179a565b6001600160a01b0383166060820152905061052b610a6e6020870187611564565b610a7e6040880160208901611564565b83604051602401610a8f9190611604565b60408051601f198184030181529190526020810180516001600160e01b03167fdb3e2198000000000000000000000000000000000000000000000000000000001790526000610cfc565b600080610ae4610ba5565b6000610aee610c73565b905060008080610b0161077188806117f8565b92509250925082610b2557604051635d883f4360e11b815260040160405180910390fd5b6000610b30886119d1565b6001600160a01b0386166020820152604051909150610a159083908590610b5b9085906024016118e1565b60408051601f198184030181529190526020810180516001600160e01b03167ff28c0498000000000000000000000000000000000000000000000000000000001790526000610cfc565b7f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c5613935566001600160a01b0316632f7a18816040518163ffffffff1660e01b8152600401602060405180830381865afa158015610c03573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c2791906119dd565b6001600160a01b0316336001600160a01b031614610c71576040517f0c1d6a3f00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b565b60007f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c5613935566001600160a01b03166334878f546040518163ffffffff1660e01b8152600401602060405180830381865afa158015610cd3573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610cf791906119dd565b905090565b6000806060610d0a86610f8d565b92508315610d1e57610d1b87610f8d565b91505b610d2a8760001961103b565b610d33856110da565b9050610d4087600161103b565b9450945094915050565b600080826001600160a01b0316846001600160a01b03161015610d71575082905081610d77565b50819050825b9250929050565b610d8733611189565b610c71576040517f61081c1500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8051600090819081906003610dd4601460026115cb565b610dde91906119fa565b8114158015610e0e5750610df4600360026115cb565b610e00601460036115cb565b610e0a91906119fa565b8114155b8015610e3a5750610e206003806115cb565b610e2c601460046115cb565b610e3691906119fa565b8114155b15610e49576000935050610f86565b610e54856000611231565b92506000610e638660146112ac565b9050610e7b610e74600360146119fa565b8790611231565b9250610e88848483610538565b9450848015610ead57506003610ea0601460026115cb565b610eaa91906119fa565b82115b15610f835782610ed46014610ec36003826119fa565b610ecd91906119fa565b88906112ac565b9150610ef7610ee5600360146119fa565b610ef09060026115cb565b8890611231565b9350610f04818584610538565b9550858015610f335750610f1a600360026115cb565b610f26601460036115cb565b610f3091906119fa565b83115b15610f81575082610f556014610f4a6003826119fa565b610ec39060026115cb565b9150610f71610f66600360146119fa565b610ef09060036115cb565b9350610f7e818584610538565b95505b505b50505b9193909250565b6040517fd5c2f4860000000000000000000000000000000000000000000000000000000081526001600160a01b0382811660048301526000917f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c5613935569091169063d5c2f48690602401602060405180830381865afa158015611011573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110359190611581565b92915050565b6040517ffa30b30f0000000000000000000000000000000000000000000000000000000081526001600160a01b038381166004830152602482018390527f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c561393556169063fa30b30f90604401600060405180830381600087803b1580156110be57600080fd5b505af11580156110d2573d6000803e3d6000fd5b505050505050565b6040517f09c5eabe0000000000000000000000000000000000000000000000000000000081526060906001600160a01b037f0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c56139355616906309c5eabe90611142908590600401611a0d565b6000604051808303816000875af1158015611161573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f191682016040526110359190810190611a20565b6040517f5f259aba0000000000000000000000000000000000000000000000000000000081526001600160a01b0382811660048301526000917f000000000000000000000000523da3a8961e4dd4f6206dbf7e6c749f51796bb390911690635f259aba90602401602060405180830381865afa15801561120d573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110359190611a97565b600061123e8260146119fa565b835110156112935760405162461bcd60e51b815260206004820152601560248201527f746f416464726573735f6f75744f66426f756e6473000000000000000000000060448201526064015b60405180910390fd5b5001602001516c01000000000000000000000000900490565b6000816112ba8160036119fa565b10156113085760405162461bcd60e51b815260206004820152601160248201527f746f55696e7432345f6f766572666c6f77000000000000000000000000000000604482015260640161128a565b6113138260036119fa565b835110156113635760405162461bcd60e51b815260206004820152601460248201527f746f55696e7432345f6f75744f66426f756e6473000000000000000000000000604482015260640161128a565b50016003015190565b600060e0828403121561137e57600080fd5b50919050565b6000610100828403121561137e57600080fd5b600061010082840312156113aa57600080fd5b6113b48383611384565b9392505050565b6001600160a01b03811681146113d057600080fd5b50565b80356113de816113bb565b919050565b803562ffffff811681146113de57600080fd5b60008060006060848603121561140b57600080fd5b8335611416816113bb565b92506020840135611426816113bb565b9150611434604085016113e3565b90509250925092565b6000806020838503121561145057600080fd5b823567ffffffffffffffff8082111561146857600080fd5b818501915085601f83011261147c57600080fd5b81358181111561148b57600080fd5b8660208260071b85010111156114a057600080fd5b60209290920196919550909350505050565b6000602082840312156114c457600080fd5b813567ffffffffffffffff8111156114db57600080fd5b8201608081850312156113b457600080fd5b600060a0828403121561137e57600080fd5b60006020828403121561151157600080fd5b813567ffffffffffffffff81111561152857600080fd5b611534848285016114ed565b949350505050565b602081016016831061155e57634e487b7160e01b600052602160045260246000fd5b91905290565b60006020828403121561157657600080fd5b81356113b4816113bb565b60006020828403121561159357600080fd5b5051919050565b6000602082840312156115ac57600080fd5b6113b4826113e3565b634e487b7160e01b600052601160045260246000fd5b8082028115828204841417611035576110356115b5565b6000826115ff57634e487b7160e01b600052601260045260246000fd5b500490565b610100810161103582846001600160a01b0380825116835280602083015116602084015262ffffff60408301511660408401528060608301511660608401526080820151608084015260a082015160a084015260c082015160c08401528060e08301511660e0840152505050565b634e487b7160e01b600052604160045260246000fd5b60405160a0810167ffffffffffffffff811182821017156116ab576116ab611672565b60405290565b604051601f8201601f1916810167ffffffffffffffff811182821017156116da576116da611672565b604052919050565b60006101008083850312156116f657600080fd5b6040519081019067ffffffffffffffff8211818310171561171957611719611672565b816040528092508335915061172d826113bb565b81815261173c602085016113d3565b602082015261174d604085016113e3565b604082015261175e606085016113d3565b60608201526080840135608082015260a084013560a082015260c084013560c082015261178d60e085016113d3565b60e0820152505092915050565b600061010082840312156117ad57600080fd5b6113b483836116e2565b634e487b7160e01b600052603260045260246000fd5b80151581146113d057600080fd5b6000602082840312156117ed57600080fd5b81356113b4816117cd565b6000808335601e1984360301811261180f57600080fd5b83018035915067ffffffffffffffff82111561182a57600080fd5b602001915036819003821315610d7757600080fd5b60005b8381101561185a578181015183820152602001611842565b50506000910152565b6000815180845261187b81602086016020860161183f565b601f01601f19169290920160200192915050565b6000815160a084526118a460a0850182611863565b90506001600160a01b0360208401511660208501526040830151604085015260608301516060850152608083015160808501528091505092915050565b6020815260006113b4602083018461188f565b600067ffffffffffffffff82111561190e5761190e611672565b50601f01601f191660200190565b600060a0828403121561192e57600080fd5b611936611688565b9050813567ffffffffffffffff81111561194f57600080fd5b8201601f8101841361196057600080fd5b80356020611975611970836118f4565b6116b1565b828152868284860101111561198957600080fd5b8282850183830137600081840183015284526119a68582016113d3565b8185015250505060408201356040820152606082013560608201526080820135608082015292915050565b6000611035368361191c565b6000602082840312156119ef57600080fd5b81516113b4816113bb565b80820180821115611035576110356115b5565b6020815260006113b46020830184611863565b600060208284031215611a3257600080fd5b815167ffffffffffffffff811115611a4957600080fd5b8201601f81018413611a5a57600080fd5b8051611a68611970826118f4565b818152856020838501011115611a7d57600080fd5b611a8e82602083016020860161183f565b95945050505050565b600060208284031215611aa957600080fd5b81516113b4816117cd56fea264697066735822122048b7223ac9fa8452d0825db48b5764539a749bcde69b941f86b1d33c248dc09c64736f6c63430008110033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c561393556000000000000000000000000e592427a0aece92de3edee1f18e0157c05861564
-----Decoded View---------------
Arg [0] : _creditManager (address): 0x3EB95430FdB99439A86d3c6D7D01C3c561393556
Arg [1] : _router (address): 0xE592427A0AEce92De3Edee1F18E0157C05861564
-----Encoded View---------------
2 Constructor Arguments found :
Arg [0] : 0000000000000000000000003eb95430fdb99439a86d3c6d7d01c3c561393556
Arg [1] : 000000000000000000000000e592427a0aece92de3edee1f18e0157c05861564
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 35 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.