Source Code
Overview
ETH Balance
0 ETH
ETH Value
$0.00| Transaction Hash |
|
Block
|
From
|
To
|
|||||
|---|---|---|---|---|---|---|---|---|---|
Latest 1 internal transaction
Advanced mode:
| Parent Transaction Hash | Block | From | To | |||
|---|---|---|---|---|---|---|
| 22556095 | 6 hrs ago | Contract Creation | 0 ETH |
Cross-Chain Transactions
Loading...
Loading
Contract Name:
MLVSettersLib
Compiler Version
v0.8.26+commit.8a97fa7a
Optimization Enabled:
Yes with 1 runs
Other Settings:
cancun EvmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.26;
import {IBaseManagedLeveragedVault} from "src/interfaces/core/mlv/base/IBaseManagedLeveragedVault.sol";
import {IFeeHook} from "src/interfaces/utils/IFeeHook.sol";
import {ITargetICRHook} from "src/interfaces/utils/ITargetICRHook.sol";
import {IBaseManagedLeveragedVaultGetters} from "src/interfaces/core/mlv/helpers/base/IBaseManagedLeveragedVaultGetters.sol";
/**
* @title MLVSettersLib
* @author Everlong team
* @notice Library containing setter logic for BaseManagedLeveragedVault to reduce bytecode size.
*/
library MLVSettersLib {
uint16 constant BP = 1e4;
uint16 constant MAX_DEVIATION_ICR = 500; // 5%
uint16 constant MAX_DEVIATION_TA = 250; // 2.5%
uint16 constant MAX_SLIPPAGE_SWAP = 300; // 3%
function setMaxDeviationICRinBP(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
uint16 _maxDeviationICRinBP
) external {
if (_maxDeviationICRinBP > MAX_DEVIATION_ICR)
revert IBaseManagedLeveragedVault.SurpassedPrecision(MAX_DEVIATION_ICR);
$.maxDeviationICRinBP = _maxDeviationICRinBP;
emit IBaseManagedLeveragedVault.NewMaxDeviationICRInBP(_maxDeviationICRinBP);
}
function setMaxDeviationTotalAssetsInBP(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
uint16 _maxDeviationTotalAssetsInBP
) external {
if (_maxDeviationTotalAssetsInBP > MAX_DEVIATION_TA)
revert IBaseManagedLeveragedVault.SurpassedPrecision(MAX_DEVIATION_TA);
$.maxDeviationTotalAssetsInBP = _maxDeviationTotalAssetsInBP;
emit IBaseManagedLeveragedVault.NewMaxDeviationTotalAssetsInBP(_maxDeviationTotalAssetsInBP);
}
function setMaxSlippageSwapInBP(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
uint16 _maxSlippageSwapInBP
) external {
if (_maxSlippageSwapInBP > MAX_SLIPPAGE_SWAP)
revert IBaseManagedLeveragedVault.SurpassedPrecision(MAX_SLIPPAGE_SWAP);
$.maxSlippageSwapInBP = _maxSlippageSwapInBP;
emit IBaseManagedLeveragedVault.NewMaxSlippageSwapInBP(_maxSlippageSwapInBP);
}
function setPeakSharePriceInWad(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
uint96 _peakSharePriceInWad
) external {
$.peakSharePriceInWad = _peakSharePriceInWad;
emit IBaseManagedLeveragedVault.NewPeakSharePriceInWad(_peakSharePriceInWad);
}
function setPerformanceFeesInBP(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
uint16 _performanceFeesInBP
) external {
if (_performanceFeesInBP > BP) revert IBaseManagedLeveragedVault.SurpassedPrecision(BP);
$.performanceFeesInBP = _performanceFeesInBP;
emit IBaseManagedLeveragedVault.NewPerformanceFeesInBP(_performanceFeesInBP);
}
function setKeeper(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
address _keeper
) external {
if (_keeper == address(0)) revert IBaseManagedLeveragedVault.ZeroAddress();
$.keeper = _keeper;
emit IBaseManagedLeveragedVault.NewKeeper(_keeper);
}
function setTargetICRHook(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
address _targetICRHook
) external {
if (_targetICRHook == address(0)) revert IBaseManagedLeveragedVault.ZeroAddress();
$.targetICRHook = ITargetICRHook(_targetICRHook);
emit IBaseManagedLeveragedVault.NewTargetICRHook(_targetICRHook);
}
function setFeeHook(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
address _feeHook
) external {
if (_feeHook == address(0)) revert IBaseManagedLeveragedVault.ZeroAddress();
$.feeHook = IFeeHook(_feeHook);
emit IBaseManagedLeveragedVault.NewFeeHook(_feeHook);
}
function setGetters(
IBaseManagedLeveragedVault.BaseManagedLeveragedVaultStorage storage $,
address _getters
) external {
// Save bytecode size with same custom error
if (
_getters == address(0) ||
address(IBaseManagedLeveragedVaultGetters(_getters).vault()) !=
address(this)
) revert IBaseManagedLeveragedVault.ZeroAddress();
$.getters = IBaseManagedLeveragedVaultGetters(_getters);
emit IBaseManagedLeveragedVault.NewGetters(_getters);
}
}// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;
import {IERC20} from "lib/openzeppelin-contracts-upgradeable/lib/openzeppelin-contracts/contracts/token/ERC20/utils/SafeERC20.sol";
import {IEverlongCore} from "src/interfaces/core/IEverlongCore.sol";
import {ITargetICRHook} from "src/interfaces/utils/ITargetICRHook.sol";
import {IFeeHook} from "src/interfaces/utils/IFeeHook.sol";
import {IBaseManagedLeveragedVaultGetters} from "src/interfaces/core/mlv/helpers/base/IBaseManagedLeveragedVaultGetters.sol";
interface IBaseManagedLeveragedVault {
// --- Storage -----------------------------------------------
/// @custom:storage-location erc7201:openzeppelin.storage.ManagedLeveragedVault
struct BaseManagedLeveragedVaultStorage {
IEverlongCore everlongCore;
IERC20 debtToken;
IERC20 collateral;
uint16 maxDeviationICRinBP;
uint16 maxDeviationTotalAssetsInBP;
uint16 maxSlippageSwapInBP;
uint16 performanceFeesInBP;
address keeper;
ITargetICRHook targetICRHook;
IFeeHook feeHook;
IBaseManagedLeveragedVaultGetters getters;
uint96 peakSharePriceInWad;
}
// --- Enums ------------------------------------------------
enum Tolerance {
ABOVE,
BOTH
}
enum Operation {
LEVERAGE,
DELEVERAGE
}
struct BaseInitParams {
address asset;
string name;
string symbol;
address everlongCore;
address debtToken;
address collateral;
uint16 maxDeviationICRinBP;
uint16 maxDeviationTotalAssetsInBP;
uint16 maxSlippageSwapInBP;
uint16 performanceFeesInBP;
address keeper;
address targetICRHook;
address feeHook;
address getters;
uint96 peakSharePriceInWad;
}
// --- Errors ------------------------------------------------
error ZeroAmount();
error ZeroAddress();
error SurpassedPrecision(uint256 precision);
error AlreadyOpened();
error NotOwner(address caller);
error NotSupportedMethod();
error VaultSlippage(uint256 expected, uint256 actual);
// --- Events -----------------------------------------------
event NewTargetICRHook(address targetICRHook);
event NewKeeper(address keeper);
event NewMaxDeviationICRInBP(uint16 maxDeviationICRInBP);
event NewMaxDeviationTotalAssetsInBP(uint16 maxDeviationTotalAssetsInBP);
event NewMaxSlippageSwapInBP(uint16 maxSlippageSwapInBP);
event NewPeakSharePriceInWad(uint96 peakSharePriceInWad);
event NewPerformanceFeesInBP(uint16 performanceFeesInBP);
event NewFeeHook(address feeHook);
event NewGetters(address getters);
event PerformanceFeeCharged(
uint256 feeShares,
uint256 oldPeak,
uint256 newPeak
);
// --- Functions ---------------------------------------------
function totalAssets() external view returns (uint256);
function setMaxDeviationICRinBP(uint16 _maxDeviationICRinBP) external;
function setMaxDeviationTotalAssetsInBP(
uint16 _maxDeviationTotalAssetsInBP
) external;
function setMaxSlippageSwapInBP(uint16 _maxSlippageSwapInBP) external;
function setKeeper(address _keeper) external;
function setTargetICRHook(address _targetICRHook) external;
function setFeeHook(address _feeHook) external;
function setGetters(address _getters) external;
function getPrice(
address token
) external view returns (uint256 scaledPriceInUsdWad);
function extSloads(
bytes32[] memory slots
) external view returns (bytes32[] memory values);
}// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;
interface IFeeHook {
enum Action {
DEPOSIT,
MINT,
WITHDRAW,
REDEEM
}
function calcFee(address caller, address token, uint amount, Action action) external view returns (uint feeInBP);
}// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;
interface ITargetICRHook {
function calcTargetICR()
external
view
returns (uint256 targetICR);
}// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;
import {IBaseManagedLeveragedVault} from "src/interfaces/core/mlv/base/IBaseManagedLeveragedVault.sol";
interface IBaseManagedLeveragedVaultGetters {
error PositionOutOfTargetCR(uint256 currentICR, uint256 targetICR, uint256 maxDelta);
error TotalAssetsDeviation(uint256 prevTotalAssets, uint256 newTotalAssets, uint256 maxDelta);
error VaultSlippage(uint256 expected, uint256 actual);
function getPrice(address token) external view returns (uint256);
function vault() external view returns (IBaseManagedLeveragedVault);
function getCollateralBalance() external view returns (uint256);
function getCollateralValue() external view returns (uint256);
function getCollateralValue(uint256 amount) external view returns (uint256);
function getDebtBalance() external view returns (uint256);
function getDebtValue() external view returns (uint256);
function getDebtValue(uint256 amount) external view returns (uint256);
function getCurrentPositionICR() external view returns (uint256);
function getTargetICR() external view returns (uint256);
function entryFeeInBP(uint256 amount, address caller) external view returns (uint256);
function exitFeeInBP(uint256 amount, address caller) external view returns (uint256);
function checkInvariantICR(uint256 currentICR, uint256 targetICR, IBaseManagedLeveragedVault.Tolerance tolerance) external view;
function checkMaxOperationCost(address inputToken, uint256 amountToSwap, uint256 prevTotalAssets) external view;
function computeNetColl(uint256 nectSurplusInAssets, uint256 collToReceive, uint256 prevTotalAssets) external view returns (uint256 netColl);
function collateral() external view returns (address);
function asset() external view returns (address);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (token/ERC20/utils/SafeERC20.sol)
pragma solidity ^0.8.20;
import {IERC20} from "../IERC20.sol";
import {IERC1363} from "../../../interfaces/IERC1363.sol";
import {Address} from "../../../utils/Address.sol";
/**
* @title SafeERC20
* @dev Wrappers around ERC-20 operations that throw on failure (when the token
* contract returns false). Tokens that return no value (and instead revert or
* throw on failure) are also supported, non-reverting calls are assumed to be
* successful.
* To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,
* which allows you to call the safe operations as `token.safeTransfer(...)`, etc.
*/
library SafeERC20 {
/**
* @dev An operation with an ERC-20 token failed.
*/
error SafeERC20FailedOperation(address token);
/**
* @dev Indicates a failed `decreaseAllowance` request.
*/
error SafeERC20FailedDecreaseAllowance(address spender, uint256 currentAllowance, uint256 requestedDecrease);
/**
* @dev Transfer `value` amount of `token` from the calling contract to `to`. If `token` returns no value,
* non-reverting calls are assumed to be successful.
*/
function safeTransfer(IERC20 token, address to, uint256 value) internal {
_callOptionalReturn(token, abi.encodeCall(token.transfer, (to, value)));
}
/**
* @dev Transfer `value` amount of `token` from `from` to `to`, spending the approval given by `from` to the
* calling contract. If `token` returns no value, non-reverting calls are assumed to be successful.
*/
function safeTransferFrom(IERC20 token, address from, address to, uint256 value) internal {
_callOptionalReturn(token, abi.encodeCall(token.transferFrom, (from, to, value)));
}
/**
* @dev Increase the calling contract's allowance toward `spender` by `value`. If `token` returns no value,
* non-reverting calls are assumed to be successful.
*/
function safeIncreaseAllowance(IERC20 token, address spender, uint256 value) internal {
uint256 oldAllowance = token.allowance(address(this), spender);
forceApprove(token, spender, oldAllowance + value);
}
/**
* @dev Decrease the calling contract's allowance toward `spender` by `requestedDecrease`. If `token` returns no
* value, non-reverting calls are assumed to be successful.
*/
function safeDecreaseAllowance(IERC20 token, address spender, uint256 requestedDecrease) internal {
unchecked {
uint256 currentAllowance = token.allowance(address(this), spender);
if (currentAllowance < requestedDecrease) {
revert SafeERC20FailedDecreaseAllowance(spender, currentAllowance, requestedDecrease);
}
forceApprove(token, spender, currentAllowance - requestedDecrease);
}
}
/**
* @dev Set the calling contract's allowance toward `spender` to `value`. If `token` returns no value,
* non-reverting calls are assumed to be successful. Meant to be used with tokens that require the approval
* to be set to zero before setting it to a non-zero value, such as USDT.
*/
function forceApprove(IERC20 token, address spender, uint256 value) internal {
bytes memory approvalCall = abi.encodeCall(token.approve, (spender, value));
if (!_callOptionalReturnBool(token, approvalCall)) {
_callOptionalReturn(token, abi.encodeCall(token.approve, (spender, 0)));
_callOptionalReturn(token, approvalCall);
}
}
/**
* @dev Performs an {ERC1363} transferAndCall, with a fallback to the simple {ERC20} transfer if the target has no
* code. This can be used to implement an {ERC721}-like safe transfer that rely on {ERC1363} checks when
* targeting contracts.
*
* Reverts if the returned value is other than `true`.
*/
function transferAndCallRelaxed(IERC1363 token, address to, uint256 value, bytes memory data) internal {
if (to.code.length == 0) {
safeTransfer(token, to, value);
} else if (!token.transferAndCall(to, value, data)) {
revert SafeERC20FailedOperation(address(token));
}
}
/**
* @dev Performs an {ERC1363} transferFromAndCall, with a fallback to the simple {ERC20} transferFrom if the target
* has no code. This can be used to implement an {ERC721}-like safe transfer that rely on {ERC1363} checks when
* targeting contracts.
*
* Reverts if the returned value is other than `true`.
*/
function transferFromAndCallRelaxed(
IERC1363 token,
address from,
address to,
uint256 value,
bytes memory data
) internal {
if (to.code.length == 0) {
safeTransferFrom(token, from, to, value);
} else if (!token.transferFromAndCall(from, to, value, data)) {
revert SafeERC20FailedOperation(address(token));
}
}
/**
* @dev Performs an {ERC1363} approveAndCall, with a fallback to the simple {ERC20} approve if the target has no
* code. This can be used to implement an {ERC721}-like safe transfer that rely on {ERC1363} checks when
* targeting contracts.
*
* NOTE: When the recipient address (`to`) has no code (i.e. is an EOA), this function behaves as {forceApprove}.
* Opposedly, when the recipient address (`to`) has code, this function only attempts to call {ERC1363-approveAndCall}
* once without retrying, and relies on the returned value to be true.
*
* Reverts if the returned value is other than `true`.
*/
function approveAndCallRelaxed(IERC1363 token, address to, uint256 value, bytes memory data) internal {
if (to.code.length == 0) {
forceApprove(token, to, value);
} else if (!token.approveAndCall(to, value, data)) {
revert SafeERC20FailedOperation(address(token));
}
}
/**
* @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
* on the return value: the return value is optional (but if data is returned, it must not be false).
* @param token The token targeted by the call.
* @param data The call data (encoded using abi.encode or one of its variants).
*
* This is a variant of {_callOptionalReturnBool} that reverts if call fails to meet the requirements.
*/
function _callOptionalReturn(IERC20 token, bytes memory data) private {
uint256 returnSize;
uint256 returnValue;
assembly ("memory-safe") {
let success := call(gas(), token, 0, add(data, 0x20), mload(data), 0, 0x20)
// bubble errors
if iszero(success) {
let ptr := mload(0x40)
returndatacopy(ptr, 0, returndatasize())
revert(ptr, returndatasize())
}
returnSize := returndatasize()
returnValue := mload(0)
}
if (returnSize == 0 ? address(token).code.length == 0 : returnValue != 1) {
revert SafeERC20FailedOperation(address(token));
}
}
/**
* @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
* on the return value: the return value is optional (but if data is returned, it must not be false).
* @param token The token targeted by the call.
* @param data The call data (encoded using abi.encode or one of its variants).
*
* This is a variant of {_callOptionalReturn} that silently catches all reverts and returns a bool instead.
*/
function _callOptionalReturnBool(IERC20 token, bytes memory data) private returns (bool) {
bool success;
uint256 returnSize;
uint256 returnValue;
assembly ("memory-safe") {
success := call(gas(), token, 0, add(data, 0x20), mload(data), 0, 0x20)
returnSize := returndatasize()
returnValue := mload(0)
}
return success && (returnSize == 0 ? address(token).code.length > 0 : returnValue == 1);
}
}// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;
/**
* @title EverlongCore
* @author Everlong Labs
* @notice Single source of truth across all Everlong contracts for key administrative data
*/
interface IEverlongCore {
function owner() external view returns (address);
function feeReceiver() external view returns (address);
function priceFeed() external view returns (address);
function setFeeReceiver(address _feeReceiver) external;
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (token/ERC20/IERC20.sol)
pragma solidity ^0.8.20;
/**
* @dev Interface of the ERC-20 standard as defined in the ERC.
*/
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 value of tokens in existence.
*/
function totalSupply() external view returns (uint256);
/**
* @dev Returns the value of tokens owned by `account`.
*/
function balanceOf(address account) external view returns (uint256);
/**
* @dev Moves a `value` amount of 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 value) 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 a `value` amount of tokens 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 value) external returns (bool);
/**
* @dev Moves a `value` amount of tokens from `from` to `to` using the
* allowance mechanism. `value` 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 value) external returns (bool);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (interfaces/IERC1363.sol)
pragma solidity ^0.8.20;
import {IERC20} from "./IERC20.sol";
import {IERC165} from "./IERC165.sol";
/**
* @title IERC1363
* @dev Interface of the ERC-1363 standard as defined in the https://eips.ethereum.org/EIPS/eip-1363[ERC-1363].
*
* Defines an extension interface for ERC-20 tokens that supports executing code on a recipient contract
* after `transfer` or `transferFrom`, or code on a spender contract after `approve`, in a single transaction.
*/
interface IERC1363 is IERC20, IERC165 {
/*
* Note: the ERC-165 identifier for this interface is 0xb0202a11.
* 0xb0202a11 ===
* bytes4(keccak256('transferAndCall(address,uint256)')) ^
* bytes4(keccak256('transferAndCall(address,uint256,bytes)')) ^
* bytes4(keccak256('transferFromAndCall(address,address,uint256)')) ^
* bytes4(keccak256('transferFromAndCall(address,address,uint256,bytes)')) ^
* bytes4(keccak256('approveAndCall(address,uint256)')) ^
* bytes4(keccak256('approveAndCall(address,uint256,bytes)'))
*/
/**
* @dev Moves a `value` amount of tokens from the caller's account to `to`
* and then calls {IERC1363Receiver-onTransferReceived} on `to`.
* @param to The address which you want to transfer to.
* @param value The amount of tokens to be transferred.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function transferAndCall(address to, uint256 value) external returns (bool);
/**
* @dev Moves a `value` amount of tokens from the caller's account to `to`
* and then calls {IERC1363Receiver-onTransferReceived} on `to`.
* @param to The address which you want to transfer to.
* @param value The amount of tokens to be transferred.
* @param data Additional data with no specified format, sent in call to `to`.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function transferAndCall(address to, uint256 value, bytes calldata data) external returns (bool);
/**
* @dev Moves a `value` amount of tokens from `from` to `to` using the allowance mechanism
* and then calls {IERC1363Receiver-onTransferReceived} on `to`.
* @param from The address which you want to send tokens from.
* @param to The address which you want to transfer to.
* @param value The amount of tokens to be transferred.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function transferFromAndCall(address from, address to, uint256 value) external returns (bool);
/**
* @dev Moves a `value` amount of tokens from `from` to `to` using the allowance mechanism
* and then calls {IERC1363Receiver-onTransferReceived} on `to`.
* @param from The address which you want to send tokens from.
* @param to The address which you want to transfer to.
* @param value The amount of tokens to be transferred.
* @param data Additional data with no specified format, sent in call to `to`.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function transferFromAndCall(address from, address to, uint256 value, bytes calldata data) external returns (bool);
/**
* @dev Sets a `value` amount of tokens as the allowance of `spender` over the
* caller's tokens and then calls {IERC1363Spender-onApprovalReceived} on `spender`.
* @param spender The address which will spend the funds.
* @param value The amount of tokens to be spent.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function approveAndCall(address spender, uint256 value) external returns (bool);
/**
* @dev Sets a `value` amount of tokens as the allowance of `spender` over the
* caller's tokens and then calls {IERC1363Spender-onApprovalReceived} on `spender`.
* @param spender The address which will spend the funds.
* @param value The amount of tokens to be spent.
* @param data Additional data with no specified format, sent in call to `spender`.
* @return A boolean value indicating whether the operation succeeded unless throwing.
*/
function approveAndCall(address spender, uint256 value, bytes calldata data) external returns (bool);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/Address.sol)
pragma solidity ^0.8.20;
import {Errors} from "./Errors.sol";
/**
* @dev Collection of functions related to the address type
*/
library Address {
/**
* @dev There's no code at `target` (it is not a contract).
*/
error AddressEmptyCode(address target);
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://consensys.net/diligence/blog/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.8.20/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
if (address(this).balance < amount) {
revert Errors.InsufficientBalance(address(this).balance, amount);
}
(bool success, ) = recipient.call{value: amount}("");
if (!success) {
revert Errors.FailedCall();
}
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason or custom error, it is bubbled
* up by this function (like regular Solidity function calls). However, if
* the call reverted with no returned reason, this function reverts with a
* {Errors.FailedCall} error.
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*/
function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) {
if (address(this).balance < value) {
revert Errors.InsufficientBalance(address(this).balance, value);
}
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResultFromTarget(target, success, returndata);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResultFromTarget(target, success, returndata);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a delegate call.
*/
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResultFromTarget(target, success, returndata);
}
/**
* @dev Tool to verify that a low level call to smart-contract was successful, and reverts if the target
* was not a contract or bubbling up the revert reason (falling back to {Errors.FailedCall}) in case
* of an unsuccessful call.
*/
function verifyCallResultFromTarget(
address target,
bool success,
bytes memory returndata
) internal view returns (bytes memory) {
if (!success) {
_revert(returndata);
} else {
// only check if target is a contract if the call was successful and the return data is empty
// otherwise we already know that it was a contract
if (returndata.length == 0 && target.code.length == 0) {
revert AddressEmptyCode(target);
}
return returndata;
}
}
/**
* @dev Tool to verify that a low level call was successful, and reverts if it wasn't, either by bubbling the
* revert reason or with a default {Errors.FailedCall} error.
*/
function verifyCallResult(bool success, bytes memory returndata) internal pure returns (bytes memory) {
if (!success) {
_revert(returndata);
} else {
return returndata;
}
}
/**
* @dev Reverts with returndata if present. Otherwise reverts with {Errors.FailedCall}.
*/
function _revert(bytes memory returndata) private pure {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
/// @solidity memory-safe-assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert Errors.FailedCall();
}
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (interfaces/IERC20.sol)
pragma solidity ^0.8.20;
import {IERC20} from "../token/ERC20/IERC20.sol";// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (interfaces/IERC165.sol)
pragma solidity ^0.8.20;
import {IERC165} from "../utils/introspection/IERC165.sol";// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
/**
* @dev Collection of common custom errors used in multiple contracts
*
* IMPORTANT: Backwards compatibility is not guaranteed in future versions of the library.
* It is recommended to avoid relying on the error API for critical functionality.
*/
library Errors {
/**
* @dev The ETH balance of the account is not enough to perform the operation.
*/
error InsufficientBalance(uint256 balance, uint256 needed);
/**
* @dev A call to an address target failed. The target may have reverted.
*/
error FailedCall();
/**
* @dev The deployment failed.
*/
error FailedDeployment();
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/introspection/IERC165.sol)
pragma solidity ^0.8.20;
/**
* @dev Interface of the ERC-165 standard, as defined in the
* https://eips.ethereum.org/EIPS/eip-165[ERC].
*
* Implementers can declare support of contract interfaces, which can then be
* queried by others ({ERC165Checker}).
*
* For an implementation, see {ERC165}.
*/
interface IERC165 {
/**
* @dev Returns true if this contract implements the interface defined by
* `interfaceId`. See the corresponding
* https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[ERC section]
* to learn more about how these ids are created.
*
* This function call must use less than 30 000 gas.
*/
function supportsInterface(bytes4 interfaceId) external view returns (bool);
}{
"remappings": [
"@openzeppelin/contracts/=lib/openzeppelin-contracts/contracts/",
"@openzeppelin-upgradeable/contracts/=lib/openzeppelin-contracts-upgradeable/contracts/",
"forge-std/=lib/forge-std/src/",
"@uniswap/v3-core/=lib/v3-core/",
"@uniswap/v3-periphery/=lib/v3-periphery/",
"@openzeppelin/contracts-upgradeable/=lib/openzeppelin-contracts-upgradeable/contracts/",
"ds-test/=lib/openzeppelin-contracts-upgradeable/lib/forge-std/lib/ds-test/src/",
"erc4626-tests/=lib/openzeppelin-contracts-upgradeable/lib/erc4626-tests/",
"halmos-cheatcodes/=lib/openzeppelin-contracts-upgradeable/lib/halmos-cheatcodes/src/",
"openzeppelin-contracts-upgradeable/=lib/openzeppelin-contracts-upgradeable/",
"openzeppelin-contracts/=lib/openzeppelin-contracts/",
"v3-core/=lib/v3-core/contracts/",
"v3-periphery/=lib/v3-periphery/contracts/"
],
"optimizer": {
"enabled": true,
"runs": 1
},
"metadata": {
"useLiteralContent": false,
"bytecodeHash": "ipfs",
"appendCBOR": true
},
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
},
"evmVersion": "cancun",
"viaIR": false
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"uint256","name":"precision","type":"uint256"}],"name":"SurpassedPrecision","type":"error"},{"inputs":[],"name":"ZeroAddress","type":"error"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"feeHook","type":"address"}],"name":"NewFeeHook","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"getters","type":"address"}],"name":"NewGetters","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"keeper","type":"address"}],"name":"NewKeeper","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"maxDeviationICRInBP","type":"uint16"}],"name":"NewMaxDeviationICRInBP","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"maxDeviationTotalAssetsInBP","type":"uint16"}],"name":"NewMaxDeviationTotalAssetsInBP","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"maxSlippageSwapInBP","type":"uint16"}],"name":"NewMaxSlippageSwapInBP","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint96","name":"peakSharePriceInWad","type":"uint96"}],"name":"NewPeakSharePriceInWad","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"performanceFeesInBP","type":"uint16"}],"name":"NewPerformanceFeesInBP","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"targetICRHook","type":"address"}],"name":"NewTargetICRHook","type":"event"}]Contract Creation Code
610755610034600b8282823980515f1a607314602857634e487b7160e01b5f525f60045260245ffd5b305f52607381538281f3fe730000000000000000000000000000000000000000301460806040526004361061008c575f3560e01c8063267de4ff1461009057806331abc44c146100b157806372569629146100d0578063b23cf1f8146100ef578063c9cac7571461010e578063ce0f20b01461012d578063d8fbf9301461014c578063daae96d21461016b578063e2be20bf1461018a575b5f80fd5b81801561009b575f80fd5b506100af6100aa366004610655565b6101a9565b005b8180156100bc575f80fd5b506100af6100cb366004610683565b610229565b8180156100db575f80fd5b506100af6100ea366004610683565b6102a9565b8180156100fa575f80fd5b506100af610109366004610655565b610320565b818015610119575f80fd5b506100af610128366004610655565b610394565b818015610138575f80fd5b506100af610147366004610683565b610408565b818015610157575f80fd5b506100af610166366004610683565b61047d565b818015610176575f80fd5b506100af610185366004610655565b6104f4565b818015610195575f80fd5b506100af6101a43660046106ac565b6105e6565b6001600160a01b0381166101d05760405163d92e233d60e01b815260040160405180910390fd5b6004820180546001600160a01b0319166001600160a01b0383161790556040517f42bbfb4743223617630fbe3734cfffc55d280da085acdb2426e843716cd555229061021d9083906106da565b60405180910390a15050565b61271061ffff8216111561025d57612710604051638abdc12960e01b815260040161025491906106ee565b60405180910390fd5b60028201805461ffff60d01b1916600160d01b61ffff8416021790556040517fcdea10fadc9dc021d935c15eb1fd103fea4cea7d1942278c1d8d2840c40106ed9061021d9083906106ee565b6101f461ffff821611156102d4576101f4604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60a01b1916600160a01b61ffff8416021790556040517fd76d222a1569878be0d02545c0819a8399c91999f0d8565d9d1dbfa1c2524df29061021d9083906106ee565b6001600160a01b0381166103475760405163d92e233d60e01b815260040160405180910390fd5b6005820180546001600160a01b0319166001600160a01b0383161790556040517fcba8f51815ef6b4d9d58f668351b97323a16a5ce5c9186a17d27fa45c3e8e4269061021d9083906106da565b6001600160a01b0381166103bb5760405163d92e233d60e01b815260040160405180910390fd5b6003820180546001600160a01b0319166001600160a01b0383161790556040517f8b67cf08b3b4a582cdf414f29895fde3e3f03a3bf26373a22a8b9bd89e7574889061021d9083906106da565b60fa61ffff821611156104315760fa604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60b01b1916600160b01b61ffff8416021790556040517fad9f7bb2fb869a89410ed22cba28ce6ddb3d518ddb06ec79d90eef53e43d099a9061021d9083906106ee565b61012c61ffff821611156104a85761012c604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60c01b1916600160c01b61ffff8416021790556040517f78d7b33b806f8dd6d1be0926097e8fd70795eef7a373ab8bdbc1f49e9b24347f9061021d9083906106ee565b6001600160a01b038116158061057b5750306001600160a01b0316816001600160a01b031663fbfa77cf6040518163ffffffff1660e01b8152600401602060405180830381865afa15801561054b573d5f803e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061056f91906106fd565b6001600160a01b031614155b156105995760405163d92e233d60e01b815260040160405180910390fd5b6006820180546001600160a01b0319166001600160a01b0383161790556040517ffdf2c3daba11b29cf3b43a19b2f0d11e4755d15d15436ee5a82635ef0ca00a9b9061021d9083906106da565b6006820180546001600160a01b0316600160a01b6001600160601b038416908102919091179091556040519081527fd393ee7eaab205f61120b914cb9f4f07a94a2c4de109f4a5e739420de1ac18e49060200161021d565b6001600160a01b0381168114610652575f80fd5b50565b5f8060408385031215610666575f80fd5b8235915060208301356106788161063e565b809150509250929050565b5f8060408385031215610694575f80fd5b82359150602083013561ffff81168114610678575f80fd5b5f80604083850312156106bd575f80fd5b8235915060208301356001600160601b0381168114610678575f80fd5b6001600160a01b0391909116815260200190565b61ffff91909116815260200190565b5f6020828403121561070d575f80fd5b81516107188161063e565b939250505056fea26469706673582212200a22515e7a00c6b894cd6362360a7790228cb3510c40f8ac11bccac4c1331a6164736f6c634300081a0033
Deployed Bytecode
0x738687b187d413763818679afa4e23ef58da8ba31f301460806040526004361061008c575f3560e01c8063267de4ff1461009057806331abc44c146100b157806372569629146100d0578063b23cf1f8146100ef578063c9cac7571461010e578063ce0f20b01461012d578063d8fbf9301461014c578063daae96d21461016b578063e2be20bf1461018a575b5f80fd5b81801561009b575f80fd5b506100af6100aa366004610655565b6101a9565b005b8180156100bc575f80fd5b506100af6100cb366004610683565b610229565b8180156100db575f80fd5b506100af6100ea366004610683565b6102a9565b8180156100fa575f80fd5b506100af610109366004610655565b610320565b818015610119575f80fd5b506100af610128366004610655565b610394565b818015610138575f80fd5b506100af610147366004610683565b610408565b818015610157575f80fd5b506100af610166366004610683565b61047d565b818015610176575f80fd5b506100af610185366004610655565b6104f4565b818015610195575f80fd5b506100af6101a43660046106ac565b6105e6565b6001600160a01b0381166101d05760405163d92e233d60e01b815260040160405180910390fd5b6004820180546001600160a01b0319166001600160a01b0383161790556040517f42bbfb4743223617630fbe3734cfffc55d280da085acdb2426e843716cd555229061021d9083906106da565b60405180910390a15050565b61271061ffff8216111561025d57612710604051638abdc12960e01b815260040161025491906106ee565b60405180910390fd5b60028201805461ffff60d01b1916600160d01b61ffff8416021790556040517fcdea10fadc9dc021d935c15eb1fd103fea4cea7d1942278c1d8d2840c40106ed9061021d9083906106ee565b6101f461ffff821611156102d4576101f4604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60a01b1916600160a01b61ffff8416021790556040517fd76d222a1569878be0d02545c0819a8399c91999f0d8565d9d1dbfa1c2524df29061021d9083906106ee565b6001600160a01b0381166103475760405163d92e233d60e01b815260040160405180910390fd5b6005820180546001600160a01b0319166001600160a01b0383161790556040517fcba8f51815ef6b4d9d58f668351b97323a16a5ce5c9186a17d27fa45c3e8e4269061021d9083906106da565b6001600160a01b0381166103bb5760405163d92e233d60e01b815260040160405180910390fd5b6003820180546001600160a01b0319166001600160a01b0383161790556040517f8b67cf08b3b4a582cdf414f29895fde3e3f03a3bf26373a22a8b9bd89e7574889061021d9083906106da565b60fa61ffff821611156104315760fa604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60b01b1916600160b01b61ffff8416021790556040517fad9f7bb2fb869a89410ed22cba28ce6ddb3d518ddb06ec79d90eef53e43d099a9061021d9083906106ee565b61012c61ffff821611156104a85761012c604051638abdc12960e01b815260040161025491906106ee565b60028201805461ffff60c01b1916600160c01b61ffff8416021790556040517f78d7b33b806f8dd6d1be0926097e8fd70795eef7a373ab8bdbc1f49e9b24347f9061021d9083906106ee565b6001600160a01b038116158061057b5750306001600160a01b0316816001600160a01b031663fbfa77cf6040518163ffffffff1660e01b8152600401602060405180830381865afa15801561054b573d5f803e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061056f91906106fd565b6001600160a01b031614155b156105995760405163d92e233d60e01b815260040160405180910390fd5b6006820180546001600160a01b0319166001600160a01b0383161790556040517ffdf2c3daba11b29cf3b43a19b2f0d11e4755d15d15436ee5a82635ef0ca00a9b9061021d9083906106da565b6006820180546001600160a01b0316600160a01b6001600160601b038416908102919091179091556040519081527fd393ee7eaab205f61120b914cb9f4f07a94a2c4de109f4a5e739420de1ac18e49060200161021d565b6001600160a01b0381168114610652575f80fd5b50565b5f8060408385031215610666575f80fd5b8235915060208301356106788161063e565b809150509250929050565b5f8060408385031215610694575f80fd5b82359150602083013561ffff81168114610678575f80fd5b5f80604083850312156106bd575f80fd5b8235915060208301356001600160601b0381168114610678575f80fd5b6001600160a01b0391909116815260200190565b61ffff91909116815260200190565b5f6020828403121561070d575f80fd5b81516107188161063e565b939250505056fea26469706673582212200a22515e7a00c6b894cd6362360a7790228cb3510c40f8ac11bccac4c1331a6164736f6c634300081a0033
Loading...
Loading
Loading...
Loading
Loading...
Loading
Net Worth in USD
$0.00
Net Worth in ETH
0
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.