Source Code
| Transaction Hash |
|
Block
|
From
|
To
|
|||||
|---|---|---|---|---|---|---|---|---|---|
Latest 25 internal transactions (View All)
| Parent Transaction Hash | Block | From | To | |||
|---|---|---|---|---|---|---|
| 13620576 | 47 days ago | 300 GLMR | ||||
| 13619335 | 47 days ago | 1,000 GLMR | ||||
| 13556889 | 53 days ago | 2.1 GLMR | ||||
| 13546588 | 53 days ago | 48,611.0640875 GLMR | ||||
| 13493000 | 58 days ago | 10 GLMR | ||||
| 13492918 | 58 days ago | 10 GLMR | ||||
| 13490063 | 58 days ago | 1 GLMR | ||||
| 13488367 | 58 days ago | 0.5 GLMR | ||||
| 13483758 | 59 days ago | 0.04 GLMR | ||||
| 13476135 | 59 days ago | 200 GLMR | ||||
| 13469322 | 60 days ago | 0.5 GLMR | ||||
| 13463525 | 60 days ago | 1.5 GLMR | ||||
| 13461691 | 61 days ago | 50 GLMR | ||||
| 13461687 | 61 days ago | 50 GLMR | ||||
| 13461682 | 61 days ago | 50 GLMR | ||||
| 13461036 | 61 days ago | 50 GLMR | ||||
| 13460785 | 61 days ago | 100 GLMR | ||||
| 13459978 | 61 days ago | 0.05 GLMR | ||||
| 13459840 | 61 days ago | 5 GLMR | ||||
| 13453121 | 61 days ago | 0.5 GLMR | ||||
| 13452957 | 61 days ago | 0.004 GLMR | ||||
| 13452947 | 61 days ago | 0.00403 GLMR | ||||
| 13450785 | 62 days ago | 70,896.1714595 GLMR | ||||
| 13450642 | 62 days ago | 57,999.28363827 GLMR | ||||
| 13448028 | 62 days ago | 200 GLMR |
Cross-Chain Transactions
Loading...
Loading
Contract Name:
AggregatorV3
Compiler Version
v0.8.17+commit.8df45f5f
Optimization Enabled:
Yes with 500 runs
Other Settings:
default evmVersion
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: BUSL-1.1
pragma solidity ^0.8.9;
import "./base/AggregatorBase.sol";
import "./helpers/TransferHelper.sol";
import "./interfaces/IAlgebraSwapRouter.sol";
import "./helpers/Path.sol";
import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";
contract AggregatorV3 is AggregatorBase {
using Path for bytes;
function initialize(RouterParameters memory params) public initializer {
AggregatorBase.initializerr(params);
}
function execute(
Command[] calldata commands,
bytes[] calldata inputs // with abi.encode it gives InvalidSignatureLength(), so we pass here
) public payable {
require(commands.length <= 15, "Too many commands for executor.");
require(
commands.length == inputs.length,
"Amount of commands must match inputs."
);
for (uint256 i = 0; i < commands.length; ++i) {
if (commands[i].instruction == InstructionType.V3_EXACT_IN) {
(
bytes memory path,
address recipient,
uint256 deadline,
uint256 amountIn,
uint256 amountOutMinimum
) = abi.decode(
inputs[i],
(bytes, address, uint256, uint256, uint256)
);
require(recipient != address(0), "Zero Address");
//fetch the first token
(address tokenA,) = path.decodeFirstPool();
IStellaSwapV2ERC20(tokenA).approve(address(v3Router),amountIn);
IAlgebraSwapRouter(v3Router).exactInput(
IAlgebraSwapRouter.ExactInputParams({
path: path,
recipient: recipient,
deadline: deadline,
amountIn: amountIn,
amountOutMinimum: amountOutMinimum
})
);
}
if (commands[i].instruction == InstructionType.V3_EXACT_OUT) {
(
bytes memory path,
address recipient,
uint256 deadline,
uint256 amountOut,
uint256 amountInMaximum
) = abi.decode(
inputs[i],
(bytes, address, uint256, uint256, uint256)
);
require(recipient != address(0), "Zero Address");
//approve last token in the reversed path in v3_exact_out
address lastToken = path.getLastPoolToken();
IStellaSwapV2ERC20(lastToken).approve(address(v3Router), amountInMaximum);
//need to encode path
IAlgebraSwapRouter(v3Router).exactOutput(
IAlgebraSwapRouter.ExactOutputParams({
path: path,
recipient: recipient,
deadline: deadline,
amountOut: amountOut,
amountInMaximum: amountInMaximum
})
);
}
if (commands[i].instruction == InstructionType.V2_EXACT_IN) {
(
uint256 amountIn,
uint256 amountOutMin,
address[] memory path,
address to,
uint256 deadline
) = abi.decode(
inputs[i],
(uint256, uint256, address[], address, uint256)
);
require(to != address(0), "Zero Address");
IStellaSwapV2ERC20(path[0]).approve(address(v2router), amountIn);
v2router.swapExactTokensForTokens(amountIn, amountOutMin, path, to, deadline);
}
if (commands[i].instruction == InstructionType.V2_EXACT_OUT) {
(
uint256 amountOut,
uint256 amountInMax,
address[] memory path,
address to,
uint256 deadline
) = abi.decode(
inputs[i],
(uint256, uint256, address[], address, uint256)
);
require(to != address(0), "Zero Address");
IStellaSwapV2ERC20(path[0]).approve(address(v2router), amountInMax);
v2router.swapTokensForExactTokens(amountOut, amountInMax, path, to, deadline);
}
if (commands[i].instruction == InstructionType.STABLE_SIMPLE) {
(
address basepool,
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) = abi.decode(
inputs[i],
(address, uint8, uint8, uint256, uint256, uint256)
);
_stableApproval(basepool, tokenIndexFrom, dx);
IStableSwap(basepool).swap(tokenIndexFrom, tokenIndexTo, dx, minDy, deadline);
}
if (commands[i].instruction == InstructionType.STABLE_FROM_BASE) {
(
address pool,
address basePool,
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) = abi.decode(
inputs[i],
(
address,
address,
uint8,
uint8,
uint256,
uint256,
uint256
)
);
_stableApproval(basePool, tokenIndexFrom, dx);
stableRouter.swapFromBase(IStableSwap(pool), IStableSwap(basePool), tokenIndexFrom, tokenIndexTo, dx, minDy, deadline);
}
if (commands[i].instruction == InstructionType.STABLE_TO_BASE) {
(
address pool,
address basePool,
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) = abi.decode(
inputs[i],
(
address,
address,
uint8,
uint8,
uint256,
uint256,
uint256
)
);
address poolToken = IStableSwap(pool).getToken(tokenIndexFrom);
IStellaSwapV2ERC20(poolToken).approve(address(stableRouter), dx);
stableRouter.swapToBase(IStableSwap(pool), IStableSwap(basePool), tokenIndexFrom, tokenIndexTo, dx, minDy, deadline);
}
if (commands[i].instruction == InstructionType.PERMIT2_TRANSFER) {
(
uint256 _amount,
address _owner,
address _user,
address _token,
uint256 _nonce,
uint256 _deadline,
bytes memory _signature
) = abi.decode(
inputs[i],
(
uint256,
address,
address,
address,
uint256,
uint256,
bytes
)
);
address permit2addr = address(permit2);
ISignatureTransfer.TokenPermissions
memory permitted = ISignatureTransfer.TokenPermissions({
amount: _amount,
token: _token
});
ISignatureTransfer(permit2addr).permitWitnessTransferFrom(
ISignatureTransfer.PermitTransferFrom({
permitted: permitted,
nonce: _nonce,
deadline: _deadline
}),
ISignatureTransfer.SignatureTransferDetails({
to: address(this),
requestedAmount: _amount
}),
msg.sender,
// witness
keccak256(abi.encode(WITNESS_TYPEHASH, Witness(_user))),
// witnessTypeString,
WITNESS_TYPE_STRING,
_signature
);
}
if (commands[i].instruction == InstructionType.WRAP_ETH) {
uint256 amount = abi.decode(inputs[i], (uint256));
require(
address(this).balance >= amount,
"Insufficient ETH balance"
);
weth.deposit{value: amount}();
}
if (commands[i].instruction == InstructionType.UNWRAP_ETH) {
//wglmr.withdraw (with users permit signature)
uint256 amount = abi.decode(inputs[i], (uint256));
weth.withdraw(amount);
}
if (commands[i].instruction == InstructionType.TRANSFER) {
(
address token,
address recipient,
uint256 value,
bool isEth
) = abi.decode(inputs[i], (address, address, uint256, bool));
require(recipient != address(0), "Zero Address");
if (isEth) {
TransferHelper.safeTransferETH(recipient, value);
} else {
TransferHelper.safeTransfer(token, recipient, value);
}
}
if (commands[i].instruction == InstructionType.SWEEP) {
(
address token,
address recipient,
bool isEth
) = abi.decode(inputs[i], (address, address, bool));
require(recipient != address(0), "Zero Address");
if (isEth) {
uint256 balance = address(this).balance;
TransferHelper.safeTransferETH(recipient, balance);
} else {
uint256 balance = IStellaSwapV2ERC20(token).balanceOf(address(this));
TransferHelper.safeTransfer(token, recipient, balance);
}
}
}
}
function _stableApproval(address pool, uint8 tokenIndex, uint256 amount) internal {
address poolToken = IStableSwap(pool).getToken(tokenIndex);
IStellaSwapV2ERC20(poolToken).approve(address(pool), amount);
IStellaSwapV2ERC20(poolToken).approve(address(stableRouter), amount);
}
receive() external payable {}
}pragma solidity ^0.8.17;
import "../interfaces/IWETH.sol";
import "../interfaces/IAlgebraSwapRouter.sol";
import "../interfaces/IStellaSwapV2Router02.sol";
import "../interfaces/ISignatureTransfer.sol";
import "../interfaces/IStableSwapRouter.sol";
import "../interfaces/IStellaSwapV2ERC20.sol";
import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";
struct RouterParameters {
IAlgebraSwapRouter v3router;
IStellaSwapV2Router02 v2router;
IStableSwapRouter stableRouter;
ISignatureTransfer permit2;
IWETH weth;
}
contract AggregatorBase is Initializable {
//Aggregator is a contract that takes commands, data, and a signature from the user
//to transfer their tokens to operate on them.
ISignatureTransfer public permit2;
IAlgebraSwapRouter public v3Router;
IStellaSwapV2Router02 public v2router;
IStableSwapRouter public stableRouter;
IWETH public weth;
string public constant WITNESS_TYPE_STRING =
"Witness witness)TokenPermissions(address token,uint256 amount)Witness(address user)";
bytes32 public constant WITNESS_TYPEHASH =
keccak256("Witness(address user)");
enum AMM {
V2,
V3,
STABLE
}
//will the tokens stay in the router for the next command to use or go to user?
enum Destination {
ROUTER,
MSG_SENDER
}
//v2 v3 stable etc all use the same commands for simplifying the API
enum InstructionType {
V3_EXACT_IN,
V3_EXACT_OUT,
V2_EXACT_IN,
V2_EXACT_OUT,
PERMIT2_TRANSFER, //giving tokens for aggregator to trade with
WRAP_ETH, //turn users GLMR to WGLMR
UNWRAP_ETH, //reverse
SWEEP, //say user had negative slippage, send the remaining funds back
TRANSFER, // simple transfer helper
STABLE_SIMPLE, // simple transfer helper
STABLE_TO_BASE,// simple transfer helper
STABLE_FROM_BASE // simple transfer helper
}
struct SwapArguments {
uint256 inputAmount;
uint256 outputAmount;
uint256 desiredInput;
uint256 desiredOutput;
}
struct Command {
InstructionType instruction;
}
struct Witness {
// Address of the user that signer is giving the tokens to
address user;
}
function initializerr(RouterParameters memory params) public onlyInitializing {
permit2 = params.permit2;
v3Router = params.v3router;
v2router = params.v2router;
stableRouter = params.stableRouter;
weth = params.weth;
}
}// SPDX-License-Identifier: GPL-2.0-or-later
pragma solidity >=0.7.5;
pragma abicoder v2;
import './IAlgebraSwapCallback.sol';
/// @title Router token swapping functionality
/// @notice Functions for swapping tokens via Algebra
/// @dev Credit to Uniswap Labs under GPL-2.0-or-later license:
/// https://github.com/Uniswap/v3-periphery
interface IAlgebraSwapRouter is IAlgebraSwapCallback {
struct ExactInputSingleParams {
address tokenIn;
address tokenOut;
address recipient;
uint256 deadline;
uint256 amountIn;
uint256 amountOutMinimum;
uint160 limitSqrtPrice;
}
/// @notice Swaps `amountIn` of one token for as much as possible of another token
/// @param params The parameters necessary for the swap, encoded as `ExactInputSingleParams` in calldata
/// @return amountOut The amount of the received token
function exactInputSingle(ExactInputSingleParams calldata params) external payable returns (uint256 amountOut);
struct ExactInputParams {
bytes path;
address recipient;
uint256 deadline;
uint256 amountIn;
uint256 amountOutMinimum;
}
/// @notice Swaps `amountIn` of one token for as much as possible of another along the specified path
/// @param params The parameters necessary for the multi-hop swap, encoded as `ExactInputParams` in calldata
/// @return amountOut The amount of the received token
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 limitSqrtPrice;
}
/// @notice Swaps as little as possible of one token for `amountOut` of another token
/// @param params The parameters necessary for the swap, encoded as `ExactOutputSingleParams` in calldata
/// @return amountIn The amount of the input token
function exactOutputSingle(ExactOutputSingleParams calldata params) external payable returns (uint256 amountIn);
struct ExactOutputParams {
bytes path;
address recipient;
uint256 deadline;
uint256 amountOut;
uint256 amountInMaximum;
}
/// @notice Swaps as little as possible of one token for `amountOut` of another along the specified path (reversed)
/// @param params The parameters necessary for the multi-hop swap, encoded as `ExactOutputParams` in calldata
/// @return amountIn The amount of the input token
function exactOutput(ExactOutputParams calldata params) external payable returns (uint256 amountIn);
/// @notice Swaps `amountIn` of one token for as much as possible of another along the specified path
/// @dev Unlike standard swaps, handles transferring from user before the actual swap.
/// @param params The parameters necessary for the multi-hop swap, encoded as `ExactInputParams` in calldata
/// @return amountOut The amount of the received token
function exactInputSingleSupportingFeeOnTransferTokens(ExactInputSingleParams calldata params)
external
returns (uint256 amountOut);
}// SPDX-License-Identifier: GPL-2.0-or-later
pragma solidity >=0.6.0;
import './BytesLib.sol';
/// @title Functions for manipulating path data for multihop swaps
/// @dev Credit to Uniswap Labs under GPL-2.0-or-later license:
/// https://github.com/Uniswap/v3-periphery
library Path {
using BytesLib for bytes;
/// @dev The length of the bytes encoded address
uint256 private constant ADDR_SIZE = 20;
/// @dev The length of the bytes encoded fee
uint256 private constant FEE_SIZE = 3;
/// @dev The offset of a single token address and pool fee
uint256 private constant NEXT_OFFSET = ADDR_SIZE;
/// @dev The offset of an encoded pool key
uint256 private constant POP_OFFSET = NEXT_OFFSET + ADDR_SIZE;
/// @dev The minimum length of an encoding that contains 2 or more pools
uint256 private constant MULTIPLE_POOLS_MIN_LENGTH = POP_OFFSET + NEXT_OFFSET;
/// @notice Returns true iff the path contains two or more pools
/// @param path The encoded swap path
/// @return True if path contains two or more pools, otherwise false
function hasMultiplePools(bytes memory path) internal pure returns (bool) {
return path.length >= MULTIPLE_POOLS_MIN_LENGTH;
}
/// @notice Returns the number of pools in the path
/// @param path The encoded swap path
/// @return The number of pools in the path
function numPools(bytes memory path) internal pure returns (uint256) {
// Ignore the first token address. From then on every fee and token offset indicates a pool.
return ((path.length - ADDR_SIZE) / NEXT_OFFSET);
}
/// @notice Decodes the first pool in path
/// @param path The bytes encoded swap path
/// @return tokenA The first token of the given pool
/// @return tokenB The second token of the given pool
function decodeFirstPool(bytes memory path) internal pure returns (address tokenA, address tokenB) {
tokenA = path.toAddress(0);
tokenB = path.toAddress(NEXT_OFFSET);
}
/// @notice Gets the segment corresponding to the first pool in the path
/// @param path The bytes encoded swap path
/// @return The segment containing all data necessary to target the first pool in the path
function getFirstPool(bytes memory path) internal pure returns (bytes memory) {
return path.slice(0, POP_OFFSET);
}
function getLastPoolToken(bytes memory path) internal pure returns (address lastPool) {
lastPool = path.toAddress(path.length - 20);
}
/// @notice Skips a token + fee element from the buffer and returns the remainder
/// @param path The swap path
/// @return The remaining token + fee elements in the path
function skipToken(bytes memory path) internal pure returns (bytes memory) {
return path.slice(NEXT_OFFSET, path.length - NEXT_OFFSET);
}
}// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.6.0;
// helper methods for interacting with ERC20 tokens and sending ETH that do not consistently return true/false
library TransferHelper {
function safeApprove(address token, address to, uint value) internal {
// bytes4(keccak256(bytes('approve(address,uint256)')));
(bool success, bytes memory data) = token.call(abi.encodeWithSelector(0x095ea7b3, to, value));
require(success && (data.length == 0 || abi.decode(data, (bool))), 'TransferHelper: APPROVE_FAILED');
}
function safeTransfer(address token, address to, uint value) internal {
// bytes4(keccak256(bytes('transfer(address,uint256)')));
(bool success, bytes memory data) = token.call(abi.encodeWithSelector(0xa9059cbb, to, value));
require(success && (data.length == 0 || abi.decode(data, (bool))), 'TransferHelper: TRANSFER_FAILED');
}
function safeTransferFrom(address token, address from, address to, uint value) internal {
// bytes4(keccak256(bytes('transferFrom(address,address,uint256)')));
(bool success, bytes memory data) = token.call(abi.encodeWithSelector(0x23b872dd, from, to, value));
require(success && (data.length == 0 || abi.decode(data, (bool))), 'TransferHelper: TRANSFER_FROM_FAILED');
}
function safeTransferETH(address to, uint value) internal {
(bool success,) = to.call{value:value}(new bytes(0));
require(success, 'TransferHelper: ETH_TRANSFER_FAILED');
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.1) (proxy/utils/Initializable.sol)
pragma solidity ^0.8.2;
import "../../utils/AddressUpgradeable.sol";
/**
* @dev This is a base contract to aid in writing upgradeable contracts, or any kind of contract that will be deployed
* behind a proxy. Since proxied contracts do not make use of a constructor, it's common to move constructor logic to an
* external initializer function, usually called `initialize`. It then becomes necessary to protect this initializer
* function so it can only be called once. The {initializer} modifier provided by this contract will have this effect.
*
* The initialization functions use a version number. Once a version number is used, it is consumed and cannot be
* reused. This mechanism prevents re-execution of each "step" but allows the creation of new initialization steps in
* case an upgrade adds a module that needs to be initialized.
*
* For example:
*
* [.hljs-theme-light.nopadding]
* ```
* contract MyToken is ERC20Upgradeable {
* function initialize() initializer public {
* __ERC20_init("MyToken", "MTK");
* }
* }
* contract MyTokenV2 is MyToken, ERC20PermitUpgradeable {
* function initializeV2() reinitializer(2) public {
* __ERC20Permit_init("MyToken");
* }
* }
* ```
*
* TIP: To avoid leaving the proxy in an uninitialized state, the initializer function should be called as early as
* possible by providing the encoded function call as the `_data` argument to {ERC1967Proxy-constructor}.
*
* CAUTION: When used with inheritance, manual care must be taken to not invoke a parent initializer twice, or to ensure
* that all initializers are idempotent. This is not verified automatically as constructors are by Solidity.
*
* [CAUTION]
* ====
* Avoid leaving a contract uninitialized.
*
* An uninitialized contract can be taken over by an attacker. This applies to both a proxy and its implementation
* contract, which may impact the proxy. To prevent the implementation contract from being used, you should invoke
* the {_disableInitializers} function in the constructor to automatically lock it when it is deployed:
*
* [.hljs-theme-light.nopadding]
* ```
* /// @custom:oz-upgrades-unsafe-allow constructor
* constructor() {
* _disableInitializers();
* }
* ```
* ====
*/
abstract contract Initializable {
/**
* @dev Indicates that the contract has been initialized.
* @custom:oz-retyped-from bool
*/
uint8 private _initialized;
/**
* @dev Indicates that the contract is in the process of being initialized.
*/
bool private _initializing;
/**
* @dev Triggered when the contract has been initialized or reinitialized.
*/
event Initialized(uint8 version);
/**
* @dev A modifier that defines a protected initializer function that can be invoked at most once. In its scope,
* `onlyInitializing` functions can be used to initialize parent contracts.
*
* Similar to `reinitializer(1)`, except that functions marked with `initializer` can be nested in the context of a
* constructor.
*
* Emits an {Initialized} event.
*/
modifier initializer() {
bool isTopLevelCall = !_initializing;
require(
(isTopLevelCall && _initialized < 1) || (!AddressUpgradeable.isContract(address(this)) && _initialized == 1),
"Initializable: contract is already initialized"
);
_initialized = 1;
if (isTopLevelCall) {
_initializing = true;
}
_;
if (isTopLevelCall) {
_initializing = false;
emit Initialized(1);
}
}
/**
* @dev A modifier that defines a protected reinitializer function that can be invoked at most once, and only if the
* contract hasn't been initialized to a greater version before. In its scope, `onlyInitializing` functions can be
* used to initialize parent contracts.
*
* A reinitializer may be used after the original initialization step. This is essential to configure modules that
* are added through upgrades and that require initialization.
*
* When `version` is 1, this modifier is similar to `initializer`, except that functions marked with `reinitializer`
* cannot be nested. If one is invoked in the context of another, execution will revert.
*
* Note that versions can jump in increments greater than 1; this implies that if multiple reinitializers coexist in
* a contract, executing them in the right order is up to the developer or operator.
*
* WARNING: setting the version to 255 will prevent any future reinitialization.
*
* Emits an {Initialized} event.
*/
modifier reinitializer(uint8 version) {
require(!_initializing && _initialized < version, "Initializable: contract is already initialized");
_initialized = version;
_initializing = true;
_;
_initializing = false;
emit Initialized(version);
}
/**
* @dev Modifier to protect an initialization function so that it can only be invoked by functions with the
* {initializer} and {reinitializer} modifiers, directly or indirectly.
*/
modifier onlyInitializing() {
require(_initializing, "Initializable: contract is not initializing");
_;
}
/**
* @dev Locks the contract, preventing any future reinitialization. This cannot be part of an initializer call.
* Calling this in the constructor of a contract will prevent that contract from being initialized or reinitialized
* to any version. It is recommended to use this to lock implementation contracts that are designed to be called
* through proxies.
*
* Emits an {Initialized} event the first time it is successfully executed.
*/
function _disableInitializers() internal virtual {
require(!_initializing, "Initializable: contract is initializing");
if (_initialized < type(uint8).max) {
_initialized = type(uint8).max;
emit Initialized(type(uint8).max);
}
}
/**
* @dev Returns the highest version that has been initialized. See {reinitializer}.
*/
function _getInitializedVersion() internal view returns (uint8) {
return _initialized;
}
/**
* @dev Returns `true` if the contract is currently initializing. See {onlyInitializing}.
*/
function _isInitializing() internal view returns (bool) {
return _initializing;
}
}// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.5.0;
interface IWETH {
function deposit() external payable;
function transfer(address to, uint value) external returns (bool);
function withdraw(uint) external;
}// SPDX-License-Identifier: MIT
pragma solidity ^0.8.17;
/// @title SignatureTransfer
/// @notice Handles ERC20 token transfers through signature based actions
/// @dev Requires user's token approval on the Permit2 contract
interface ISignatureTransfer {
/// @notice Thrown when the requested amount for a transfer is larger than the permissioned amount
/// @param maxAmount The maximum amount a spender can request to transfer
error InvalidAmount(uint256 maxAmount);
/// @notice Thrown when the number of tokens permissioned to a spender does not match the number of tokens being transferred
/// @dev If the spender does not need to transfer the number of tokens permitted, the spender can request amount 0 to be transferred
error LengthMismatch();
/// @notice Emits an event when the owner successfully invalidates an unordered nonce.
event UnorderedNonceInvalidation(address indexed owner, uint256 word, uint256 mask);
/// @notice The token and amount details for a transfer signed in the permit transfer signature
struct TokenPermissions {
// ERC20 token address
address token;
// the maximum amount that can be spent
uint256 amount;
}
/// @notice The signed permit message for a single token transfer
struct PermitTransferFrom {
TokenPermissions permitted;
// a unique value for every token owner's signature to prevent signature replays
uint256 nonce;
// deadline on the permit signature
uint256 deadline;
}
/// @notice Specifies the recipient address and amount for batched transfers.
/// @dev Recipients and amounts correspond to the index of the signed token permissions array.
/// @dev Reverts if the requested amount is greater than the permitted signed amount.
struct SignatureTransferDetails {
// recipient address
address to;
// spender requested amount
uint256 requestedAmount;
}
/// @notice Used to reconstruct the signed permit message for multiple token transfers
/// @dev Do not need to pass in spender address as it is required that it is msg.sender
/// @dev Note that a user still signs over a spender address
struct PermitBatchTransferFrom {
// the tokens and corresponding amounts permitted for a transfer
TokenPermissions[] permitted;
// a unique value for every token owner's signature to prevent signature replays
uint256 nonce;
// deadline on the permit signature
uint256 deadline;
}
/// @notice A map from token owner address and a caller specified word index to a bitmap. Used to set bits in the bitmap to prevent against signature replay protection
/// @dev Uses unordered nonces so that permit messages do not need to be spent in a certain order
/// @dev The mapping is indexed first by the token owner, then by an index specified in the nonce
/// @dev It returns a uint256 bitmap
/// @dev The index, or wordPosition is capped at type(uint248).max
function nonceBitmap(address, uint256) external view returns (uint256);
/// @notice Transfers a token using a signed permit message
/// @dev Reverts if the requested amount is greater than the permitted signed amount
/// @param permit The permit data signed over by the owner
/// @param owner The owner of the tokens to transfer
/// @param transferDetails The spender's requested transfer details for the permitted token
/// @param signature The signature to verify
function permitTransferFrom(
PermitTransferFrom memory permit,
SignatureTransferDetails calldata transferDetails,
address owner,
bytes calldata signature
) external;
/// @notice Transfers a token using a signed permit message
/// @notice Includes extra data provided by the caller to verify signature over
/// @dev The witness type string must follow EIP712 ordering of nested structs and must include the TokenPermissions type definition
/// @dev Reverts if the requested amount is greater than the permitted signed amount
/// @param permit The permit data signed over by the owner
/// @param owner The owner of the tokens to transfer
/// @param transferDetails The spender's requested transfer details for the permitted token
/// @param witness Extra data to include when checking the user signature
/// @param witnessTypeString The EIP-712 type definition for remaining string stub of the typehash
/// @param signature The signature to verify
function permitWitnessTransferFrom(
PermitTransferFrom memory permit,
SignatureTransferDetails calldata transferDetails,
address owner,
bytes32 witness,
string calldata witnessTypeString,
bytes calldata signature
) external;
/// @notice Transfers multiple tokens using a signed permit message
/// @param permit The permit data signed over by the owner
/// @param owner The owner of the tokens to transfer
/// @param transferDetails Specifies the recipient and requested amount for the token transfer
/// @param signature The signature to verify
function permitTransferFrom(
PermitBatchTransferFrom memory permit,
SignatureTransferDetails[] calldata transferDetails,
address owner,
bytes calldata signature
) external;
/// @notice Transfers multiple tokens using a signed permit message
/// @dev The witness type string must follow EIP712 ordering of nested structs and must include the TokenPermissions type definition
/// @notice Includes extra data provided by the caller to verify signature over
/// @param permit The permit data signed over by the owner
/// @param owner The owner of the tokens to transfer
/// @param transferDetails Specifies the recipient and requested amount for the token transfer
/// @param witness Extra data to include when checking the user signature
/// @param witnessTypeString The EIP-712 type definition for remaining string stub of the typehash
/// @param signature The signature to verify
function permitWitnessTransferFrom(
PermitBatchTransferFrom memory permit,
SignatureTransferDetails[] calldata transferDetails,
address owner,
bytes32 witness,
string calldata witnessTypeString,
bytes calldata signature
) external;
/// @notice Invalidates the bits specified in mask for the bitmap at the word position
/// @dev The wordPos is maxed at type(uint248).max
/// @param wordPos A number to index the nonceBitmap at
/// @param mask A bitmap masked against msg.sender's current bitmap at the word position
function invalidateUnorderedNonces(uint256 wordPos, uint256 mask) external;
}// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.6.2;
import './IStellaSwapV2Router01.sol';
interface IStellaSwapV2Router02 is IStellaSwapV2Router01 {
function removeLiquidityETHSupportingFeeOnTransferTokens(
address token,
uint liquidity,
uint amountTokenMin,
uint amountETHMin,
address to,
uint deadline
) external returns (uint amountETH);
function removeLiquidityETHWithPermitSupportingFeeOnTransferTokens(
address token,
uint liquidity,
uint amountTokenMin,
uint amountETHMin,
address to,
uint deadline,
bool approveMax, uint8 v, bytes32 r, bytes32 s
) external returns (uint amountETH);
function swapExactTokensForTokensSupportingFeeOnTransferTokens(
uint amountIn,
uint amountOutMin,
address[] calldata path,
address to,
uint deadline
) external;
function swapExactETHForTokensSupportingFeeOnTransferTokens(
uint amountOutMin,
address[] calldata path,
address to,
uint deadline
) external payable;
function swapExactTokensForETHSupportingFeeOnTransferTokens(
uint amountIn,
uint amountOutMin,
address[] calldata path,
address to,
uint deadline
) external;
}// SPDX-License-Identifier: MIT
pragma solidity >=0.6.0;
import "./IStableSwap.sol";
interface IStableSwapRouter {
function swapFromBase(
IStableSwap pool,
IStableSwap basePool,
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) external returns (uint256);
function swapToBase(
IStableSwap pool,
IStableSwap basePool,
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) external returns (uint256);
}// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.5.0;
interface IStellaSwapV2ERC20 {
event Approval(address indexed owner, address indexed spender, uint value);
event Transfer(address indexed from, address indexed to, uint value);
function name() external pure returns (string memory);
function symbol() external pure returns (string memory);
function decimals() external pure returns (uint8);
function totalSupply() external view returns (uint);
function balanceOf(address owner) external view returns (uint);
function allowance(address owner, address spender) external view returns (uint);
function approve(address spender, uint value) external returns (bool);
function transfer(address to, uint value) external returns (bool);
function transferFrom(address from, address to, uint value) external returns (bool);
function DOMAIN_SEPARATOR() external view returns (bytes32);
function PERMIT_TYPEHASH() external pure returns (bytes32);
function nonces(address owner) external view returns (uint);
function permit(address owner, address spender, uint value, uint deadline, uint8 v, bytes32 r, bytes32 s) external;
}// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.6.2;
interface IStellaSwapV2Router01 {
function factory() external pure returns (address);
function WETH() external pure returns (address);
function addLiquidity(
address tokenA,
address tokenB,
uint amountADesired,
uint amountBDesired,
uint amountAMin,
uint amountBMin,
address to,
uint deadline
) external returns (uint amountA, uint amountB, uint liquidity);
function addLiquidityETH(
address token,
uint amountTokenDesired,
uint amountTokenMin,
uint amountETHMin,
address to,
uint deadline
) external payable returns (uint amountToken, uint amountETH, uint liquidity);
function removeLiquidity(
address tokenA,
address tokenB,
uint liquidity,
uint amountAMin,
uint amountBMin,
address to,
uint deadline
) external returns (uint amountA, uint amountB);
function removeLiquidityETH(
address token,
uint liquidity,
uint amountTokenMin,
uint amountETHMin,
address to,
uint deadline
) external returns (uint amountToken, uint amountETH);
function removeLiquidityWithPermit(
address tokenA,
address tokenB,
uint liquidity,
uint amountAMin,
uint amountBMin,
address to,
uint deadline,
bool approveMax, uint8 v, bytes32 r, bytes32 s
) external returns (uint amountA, uint amountB);
function removeLiquidityETHWithPermit(
address token,
uint liquidity,
uint amountTokenMin,
uint amountETHMin,
address to,
uint deadline,
bool approveMax, uint8 v, bytes32 r, bytes32 s
) external returns (uint amountToken, uint amountETH);
function swapExactTokensForTokens(
uint amountIn,
uint amountOutMin,
address[] calldata path,
address to,
uint deadline
) external returns (uint[] memory amounts);
function swapTokensForExactTokens(
uint amountOut,
uint amountInMax,
address[] calldata path,
address to,
uint deadline
) external returns (uint[] memory amounts);
function swapExactETHForTokens(uint amountOutMin, address[] calldata path, address to, uint deadline)
external
payable
returns (uint[] memory amounts);
function swapTokensForExactETH(uint amountOut, uint amountInMax, address[] calldata path, address to, uint deadline)
external
returns (uint[] memory amounts);
function swapExactTokensForETH(uint amountIn, uint amountOutMin, address[] calldata path, address to, uint deadline)
external
returns (uint[] memory amounts);
function swapETHForExactTokens(uint amountOut, address[] calldata path, address to, uint deadline)
external
payable
returns (uint[] memory amounts);
function quote(uint amountA, uint reserveA, uint reserveB) external pure returns (uint amountB);
function getAmountOut(uint amountIn, uint reserveIn, uint reserveOut) external pure returns (uint amountOut);
function getAmountIn(uint amountOut, uint reserveIn, uint reserveOut) external pure returns (uint amountIn);
function getAmountsOut(uint amountIn, address[] calldata path) external view returns (uint[] memory amounts);
function getAmountsIn(uint amountOut, address[] calldata path) external view returns (uint[] memory amounts);
}// SPDX-License-Identifier: GPL-2.0-or-later
pragma solidity >=0.5.0;
/// @title Callback for IAlgebraPoolActions#swap
/// @notice Any contract that calls IAlgebraPoolActions#swap must implement this interface
/// @dev Credit to Uniswap Labs under GPL-2.0-or-later license:
/// https://github.com/Uniswap/v3-core/tree/main/contracts/interfaces
interface IAlgebraSwapCallback {
/// @notice Called to `msg.sender` after executing a swap via IAlgebraPool#swap.
/// @dev In the implementation you must pay the pool tokens owed for the swap.
/// The caller of this method must be checked to be a AlgebraPool deployed by the canonical AlgebraFactory.
/// amount0Delta and amount1Delta can both be 0 if no tokens were swapped.
/// @param amount0Delta The amount of token0 that was sent (negative) or must be received (positive) by the pool by
/// the end of the swap. If positive, the callback must send that amount of token0 to the pool.
/// @param amount1Delta The amount of token1 that was sent (negative) or must be received (positive) by the pool by
/// the end of the swap. If positive, the callback must send that amount of token1 to the pool.
/// @param data Any data passed through by the caller via the IAlgebraPoolActions#swap call
function algebraSwapCallback(
int256 amount0Delta,
int256 amount1Delta,
bytes calldata data
) external;
}// SPDX-License-Identifier: MIT
pragma solidity >=0.6.0;
interface IStableSwap {
function swap(
uint8 tokenIndexFrom,
uint8 tokenIndexTo,
uint256 dx,
uint256 minDy,
uint256 deadline
) external returns (uint256);
function getLpToken() external returns (address);
function getToken(uint8 index) external returns (address);
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (utils/Address.sol)
pragma solidity ^0.8.1;
/**
* @dev Collection of functions related to the address type
*/
library AddressUpgradeable {
/**
* @dev Returns true if `account` is a contract.
*
* [IMPORTANT]
* ====
* It is unsafe to assume that an address for which this function returns
* false is an externally-owned account (EOA) and not a contract.
*
* Among others, `isContract` will return false for the following
* types of addresses:
*
* - an externally-owned account
* - a contract in construction
* - an address where a contract will be created
* - an address where a contract lived, but was destroyed
* ====
*
* [IMPORTANT]
* ====
* You shouldn't rely on `isContract` to protect against flash loan attacks!
*
* Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
* constructor.
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize/address.code.length, which returns 0
// for contracts in construction, since the code is only stored at the end
// of the constructor execution.
return account.code.length > 0;
}
/**
* @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://diligence.consensys.net/posts/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.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
/**
* @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, it is bubbled up by this
* function (like regular Solidity function calls).
*
* 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.
*
* _Available since v3.1._
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @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`.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value
) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
/**
* @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling
* the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract.
*
* _Available since v4.8._
*/
function verifyCallResultFromTarget(
address target,
bool success,
bytes memory returndata,
string memory errorMessage
) internal view returns (bytes memory) {
if (success) {
if (returndata.length == 0) {
// only check isContract if the call was successful and the return data is empty
// otherwise we already know that it was a contract
require(isContract(target), "Address: call to non-contract");
}
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
/**
* @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason or using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
function _revert(bytes memory returndata, string memory errorMessage) 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(errorMessage);
}
}
}// SPDX-License-Identifier: Unlicense /* * @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 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 concatStorage(bytes storage _preBytes, bytes memory _postBytes) internal { assembly { // Read the first 32 bytes of _preBytes storage, which is the length // of the array. (We don't need to use the offset into the slot // because arrays use the entire slot.) let fslot := sload(_preBytes.slot) // Arrays of 31 bytes or less have an even value in their slot, // while longer arrays have an odd value. The actual length is // the slot divided by two for odd values, and the lowest order // byte divided by two for even values. // If the slot is even, bitwise and the slot with 255 and divide by // two to get the length. If the slot is odd, bitwise and the slot // with -1 and divide by two. let slength := div(and(fslot, sub(mul(0x100, iszero(and(fslot, 1))), 1)), 2) let mlength := mload(_postBytes) let newlength := add(slength, mlength) // slength can contain both the length and contents of the array // if length < 32 bytes so let's prepare for that // v. http://solidity.readthedocs.io/en/latest/miscellaneous.html#layout-of-state-variables-in-storage switch add(lt(slength, 32), lt(newlength, 32)) case 2 { // Since the new array still fits in the slot, we just need to // update the contents of the slot. // uint256(bytes_storage) = uint256(bytes_storage) + uint256(bytes_memory) + new_length sstore( _preBytes.slot, // all the modifications to the slot are inside this // next block add( // we can just add to the slot contents because the // bytes we want to change are the LSBs fslot, add( mul( div( // load the bytes from memory mload(add(_postBytes, 0x20)), // zero all bytes to the right exp(0x100, sub(32, mlength)) ), // and now shift left the number of bytes to // leave space for the length in the slot exp(0x100, sub(32, newlength)) ), // increase length by the double of the memory // bytes length mul(mlength, 2) ) ) ) } case 1 { // The stored value fits in the slot, but the combined value // will exceed it. // get the keccak hash to get the contents of the array mstore(0x0, _preBytes.slot) let sc := add(keccak256(0x0, 0x20), div(slength, 32)) // save new length sstore(_preBytes.slot, add(mul(newlength, 2), 1)) // The contents of the _postBytes array start 32 bytes into // the structure. Our first read should obtain the `submod` // bytes that can fit into the unused space in the last word // of the stored array. To get this, we read 32 bytes starting // from `submod`, so the data we read overlaps with the array // contents by `submod` bytes. Masking the lowest-order // `submod` bytes allows us to add that value directly to the // stored value. let submod := sub(32, slength) let mc := add(_postBytes, submod) let end := add(_postBytes, mlength) let mask := sub(exp(0x100, submod), 1) sstore( sc, add( and( fslot, 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00 ), and(mload(mc), mask) ) ) for { mc := add(mc, 0x20) sc := add(sc, 1) } lt(mc, end) { sc := add(sc, 1) mc := add(mc, 0x20) } { sstore(sc, mload(mc)) } mask := exp(0x100, sub(mc, end)) sstore(sc, mul(div(mload(mc), mask), mask)) } default { // get the keccak hash to get the contents of the array mstore(0x0, _preBytes.slot) // Start copying to the last used word of the stored array. let sc := add(keccak256(0x0, 0x20), div(slength, 32)) // save new length sstore(_preBytes.slot, add(mul(newlength, 2), 1)) // Copy over the first `submod` bytes of the new data as in // case 1 above. let slengthmod := mod(slength, 32) let mlengthmod := mod(mlength, 32) let submod := sub(32, slengthmod) let mc := add(_postBytes, submod) let end := add(_postBytes, mlength) let mask := sub(exp(0x100, submod), 1) sstore(sc, add(sload(sc), and(mload(mc), mask))) for { sc := add(sc, 1) mc := add(mc, 0x20) } lt(mc, end) { sc := add(sc, 1) mc := add(mc, 0x20) } { sstore(sc, mload(mc)) } mask := exp(0x100, sub(mc, end)) sstore(sc, mul(div(mload(mc), mask), mask)) } } } 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; } 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 toUint8(bytes memory _bytes, uint256 _start) internal pure returns (uint8) { require(_bytes.length >= _start + 1 , "toUint8_outOfBounds"); uint8 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x1), _start)) } return tempUint; } function toUint16(bytes memory _bytes, uint256 _start) internal pure returns (uint16) { require(_bytes.length >= _start + 2, "toUint16_outOfBounds"); uint16 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x2), _start)) } return tempUint; } function toUint32(bytes memory _bytes, uint256 _start) internal pure returns (uint32) { require(_bytes.length >= _start + 4, "toUint32_outOfBounds"); uint32 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x4), _start)) } return tempUint; } function toUint64(bytes memory _bytes, uint256 _start) internal pure returns (uint64) { require(_bytes.length >= _start + 8, "toUint64_outOfBounds"); uint64 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x8), _start)) } return tempUint; } function toUint96(bytes memory _bytes, uint256 _start) internal pure returns (uint96) { require(_bytes.length >= _start + 12, "toUint96_outOfBounds"); uint96 tempUint; assembly { tempUint := mload(add(add(_bytes, 0xc), _start)) } return tempUint; } function toUint128(bytes memory _bytes, uint256 _start) internal pure returns (uint128) { require(_bytes.length >= _start + 16, "toUint128_outOfBounds"); uint128 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x10), _start)) } return tempUint; } function toUint256(bytes memory _bytes, uint256 _start) internal pure returns (uint256) { require(_bytes.length >= _start + 32, "toUint256_outOfBounds"); uint256 tempUint; assembly { tempUint := mload(add(add(_bytes, 0x20), _start)) } return tempUint; } function toBytes32(bytes memory _bytes, uint256 _start) internal pure returns (bytes32) { require(_bytes.length >= _start + 32, "toBytes32_outOfBounds"); bytes32 tempBytes32; assembly { tempBytes32 := mload(add(add(_bytes, 0x20), _start)) } return tempBytes32; } function equal(bytes memory _preBytes, bytes memory _postBytes) internal pure returns (bool) { bool success = true; assembly { let length := mload(_preBytes) // if lengths don't match the arrays are not equal switch eq(length, mload(_postBytes)) case 1 { // cb is a circuit breaker in the for loop since there's // no said feature for inline assembly loops // cb = 1 - don't breaker // cb = 0 - break let cb := 1 let mc := add(_preBytes, 0x20) let end := add(mc, length) for { let cc := add(_postBytes, 0x20) // the next line is the loop condition: // while(uint256(mc < end) + cb == 2) } eq(add(lt(mc, end), cb), 2) { mc := add(mc, 0x20) cc := add(cc, 0x20) } { // if any of these checks fails then arrays are not equal if iszero(eq(mload(mc), mload(cc))) { // unsuccess: success := 0 cb := 0 } } } default { // unsuccess: success := 0 } } return success; } function equalStorage( bytes storage _preBytes, bytes memory _postBytes ) internal view returns (bool) { bool success = true; assembly { // we know _preBytes_offset is 0 let fslot := sload(_preBytes.slot) // Decode the length of the stored array like in concatStorage(). let slength := div(and(fslot, sub(mul(0x100, iszero(and(fslot, 1))), 1)), 2) let mlength := mload(_postBytes) // if lengths don't match the arrays are not equal switch eq(slength, mlength) case 1 { // slength can contain both the length and contents of the array // if length < 32 bytes so let's prepare for that // v. http://solidity.readthedocs.io/en/latest/miscellaneous.html#layout-of-state-variables-in-storage if iszero(iszero(slength)) { switch lt(slength, 32) case 1 { // blank the last byte which is the length fslot := mul(div(fslot, 0x100), 0x100) if iszero(eq(fslot, mload(add(_postBytes, 0x20)))) { // unsuccess: success := 0 } } default { // cb is a circuit breaker in the for loop since there's // no said feature for inline assembly loops // cb = 1 - don't breaker // cb = 0 - break let cb := 1 // get the keccak hash to get the contents of the array mstore(0x0, _preBytes.slot) let sc := keccak256(0x0, 0x20) let mc := add(_postBytes, 0x20) let end := add(mc, mlength) // the next line is the loop condition: // while(uint256(mc < end) + cb == 2) for {} eq(add(lt(mc, end), cb), 2) { sc := add(sc, 1) mc := add(mc, 0x20) } { if iszero(eq(sload(sc), mload(mc))) { // unsuccess: success := 0 cb := 0 } } } } } default { // unsuccess: success := 0 } } return success; } }
{
"viaIR": true,
"optimizer": {
"enabled": true,
"runs": 500
},
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
},
"libraries": {}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint8","name":"version","type":"uint8"}],"name":"Initialized","type":"event"},{"inputs":[],"name":"WITNESS_TYPEHASH","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"WITNESS_TYPE_STRING","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"components":[{"internalType":"enum AggregatorBase.InstructionType","name":"instruction","type":"uint8"}],"internalType":"struct AggregatorBase.Command[]","name":"commands","type":"tuple[]"},{"internalType":"bytes[]","name":"inputs","type":"bytes[]"}],"name":"execute","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"components":[{"internalType":"contract IAlgebraSwapRouter","name":"v3router","type":"address"},{"internalType":"contract IStellaSwapV2Router02","name":"v2router","type":"address"},{"internalType":"contract IStableSwapRouter","name":"stableRouter","type":"address"},{"internalType":"contract ISignatureTransfer","name":"permit2","type":"address"},{"internalType":"contract IWETH","name":"weth","type":"address"}],"internalType":"struct RouterParameters","name":"params","type":"tuple"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"contract IAlgebraSwapRouter","name":"v3router","type":"address"},{"internalType":"contract IStellaSwapV2Router02","name":"v2router","type":"address"},{"internalType":"contract IStableSwapRouter","name":"stableRouter","type":"address"},{"internalType":"contract ISignatureTransfer","name":"permit2","type":"address"},{"internalType":"contract IWETH","name":"weth","type":"address"}],"internalType":"struct RouterParameters","name":"params","type":"tuple"}],"name":"initializerr","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"permit2","outputs":[{"internalType":"contract ISignatureTransfer","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"stableRouter","outputs":[{"internalType":"contract IStableSwapRouter","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"v2router","outputs":[{"internalType":"contract IStellaSwapV2Router02","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"v3Router","outputs":[{"internalType":"contract IAlgebraSwapRouter","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"weth","outputs":[{"internalType":"contract IWETH","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"stateMutability":"payable","type":"receive"}]Contract Creation Code
60808060405234610016576120e5908161001c8239f35b600080fdfe6080604052600436101561001b575b361561001957600080fd5b005b60003560e01c80630dc91306146100e357806312261ee7146100da578063156e2152146100d15780632c03ae6a146100c85780633fc8cef3146100bf5780634c3677c8146100b65780638f656d22146100ad5780638f8dc10a146100a4578063d7f478ee1461009b5763ff08da6e0361000e57610096610775565b61000e565b506100966105f2565b506100966105ca565b50610096610482565b506100966103dc565b506100966103b4565b50610096610378565b50610096610343565b50610096610124565b506100966100fc565b60009103126100f757565b600080fd5b50346100f75760003660031901126100f75760206001600160a01b0360015416604051908152f35b50346100f75760003660031901126100f75760206001600160a01b0360005460101c16604051908152f35b50634e487b7160e01b600052604160045260246000fd5b60a0810190811067ffffffffffffffff82111761018257604052565b61018a61014f565b604052565b67ffffffffffffffff811161018257604052565b90601f8019910116810190811067ffffffffffffffff82111761018257604052565b604051906101d282610166565b565b604051906040820182811067ffffffffffffffff82111761018257604052565b604051906060820182811067ffffffffffffffff82111761018257604052565b604051906020820182811067ffffffffffffffff82111761018257604052565b60209067ffffffffffffffff8111610252575b601f01601f19160190565b61025a61014f565b610247565b604051906080820182811067ffffffffffffffff8211176102f6575b604052605382527f746e6573732861646472657373207573657229000000000000000000000000006060837f5769746e657373207769746e65737329546f6b656e5065726d697373696f6e7360208201527f286164647265737320746f6b656e2c75696e7432353620616d6f756e7429576960408201520152565b6102fe61014f565b61027b565b919082519283825260005b84811061032f575050826000602080949584010152601f8019910116010190565b60208183018101518483018201520161030e565b50346100f75760003660031901126100f75761037461036061025f565b604051918291602083526020830190610303565b0390f35b50346100f75760003660031901126100f75760206040517ffeed45b61d43f452c933000e813412318e408c352e137cba26cfbe202b355c3a8152f35b50346100f75760003660031901126100f75760206001600160a01b0360045416604051908152f35b50346100f75760003660031901126100f75760206001600160a01b0360035416604051908152f35b6001600160a01b038116036100f757565b60a09060031901126100f75760405161042d81610166565b60043561043981610404565b815260243561044781610404565b602082015260443561045881610404565b604082015260643561046981610404565b606082015260843561047a81610404565b608082015290565b50346100f75761049136610415565b6000549060ff8260081c1615809281936105bc575b811561059c575b5015610531576104d390826104ca600160ff196000541617600055565b61051857611e11565b6104d957005b6104e961ff001960005416600055565b604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb384740249890602090a1005b61052c61010061ff00196000541617600055565b611e11565b60405162461bcd60e51b815260206004820152602e60248201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160448201527f647920696e697469616c697a65640000000000000000000000000000000000006064820152608490fd5b303b159150816105ae575b50386104ad565b6001915060ff1614386105a7565b600160ff82161091506104a6565b50346100f75760003660031901126100f75760206001600160a01b0360025416604051908152f35b50346100f75761060136610415565b6000549060ff8260081c16156106eb576080816100199362010000600160b01b0360606106cf95015160101b169062010000600160b01b031916176000556001600160a01b038151166001600160a01b0319600154161760015561068e61067260208301516001600160a01b031690565b6001600160a01b03166001600160a01b03196002541617600255565b6106c16106a560408301516001600160a01b031690565b6001600160a01b03166001600160a01b03196003541617600355565b01516001600160a01b031690565b6001600160a01b03166001600160a01b03196004541617600455565b60405162461bcd60e51b815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201526a6e697469616c697a696e6760a81b6064820152608490fd5b9181601f840112156100f75782359167ffffffffffffffff83116100f7576020808501948460051b0101116100f757565b5060403660031901126100f75767ffffffffffffffff6004358181116100f7576107a3903690600401610744565b916024359081116100f7576107bc903690600401610744565b906107ca600f851115611598565b6107d58285146115e4565b60005b8481106107e157005b6107f46107ef828787611688565b6116c6565b6107fd816116a6565b15611474575b6108116107ef828787611688565b61081a816116a6565b600180911461131c575b506108336107ef828787611688565b61083c816116a6565b60028091146111e8575b60036108566107ef848989611688565b61085f816116a6565b1461109b575b5060096108766107ef838888611688565b61087f816116a6565b14610fdb575b600b6108956107ef838888611688565b61089e816116a6565b14610eec575b600a6108b46107ef838888611688565b6108bd816116a6565b14610cf7575b60046108d36107ef838888611688565b6108dc816116a6565b14610b93575b60056108f26107ef838888611688565b6108fb816116a6565b14610b13575b60066109116107ef838888611688565b61091a816116a6565b14610a72575b8060086109346107ef610967948989611688565b61093d816116a6565b14610a24575b60076109536107ef838989611688565b61095c816116a6565b1461096c575b611655565b6107d8565b61098261097a8286866116d3565b810190611c88565b916001600160a01b0380911691169161099c8315156117c0565b156109ad5750610962904790612018565b6040516370a0823160e01b81523060048201526109629260209290918381602481855afa938415610a17575b6000946109e8575b5050611f4b565b610a08929450803d10610a10575b610a0081836101a3565b81019061182a565b9138806109e1565b503d6109f6565b610a1f61181d565b6109d9565b610a3a610a328286866116d3565b810190611c4e565b90916001600160a01b0380911691610a538315156117c0565b15610a685750610a639250612018565b610943565b610a639316611f4b565b610a88610a808285856116d3565b810190611bf3565b90610aaa610a9e6004546001600160a01b031690565b6001600160a01b031690565b91823b156100f757604051632e1a7d4d60e01b81526004810191909152610967926000908290602490829084905af18015610b06575b610aed575b509050610920565b80610afa610b009261018f565b806100ec565b38610ae5565b610b0e61181d565b610ae0565b610b21610a808285856116d3565b610b2d81471015611c02565b610b42610a9e6004546001600160a01b031690565b803b156100f757600090600460405180948193630d0e30db60e41b83525af18015610b86575b610b73575b50610901565b80610afa610b809261018f565b38610b6d565b610b8e61181d565b610b68565b610c78610c86610baf610ba78487876116d3565b810190611aff565b9792909596919450610c32610bd3610a9e6000546001600160a01b039060101c1690565b91610bdc6101d4565b6001600160a01b03918216815297816020948b868c01521697610bfd6101f4565b998a52848a01526040890152610c116101d4565b30815298838a0152610c21610214565b951685906001600160a01b03169052565b6040519283918201948591909160206001600160a01b0360408301947ffeed45b61d43f452c933000e813412318e408c352e137cba26cfbe202b355c3a84525116910152565b03601f1981018352826101a3565b51902091610c9261025f565b94823b156100f757600094610cc18692604051988997889687956309be14ff60e11b8752339160048801611b64565b03925af18015610cea575b610cd7575b506108e2565b80610afa610ce49261018f565b38610cd1565b610cf261181d565b610ccc565b610d028184846116d3565b8101610d0d91611a97565b60405162415c3360e91b815260ff861660048201529295939493869390916001600160a01b038916826024815a602094600091f1938415986001600160a01b0398610db460208b99600099610e3698839f610edf575b8b91610eb2575b50610d80610a9e6003546001600160a01b031690565b8b8d60405180978196829563095ea7b360e01b845260048401602090939291936001600160a01b0360408201951681520152565b0393165af18015610ea5575b610e78575b50610ddb610a9e6003546001600160a01b031690565b986040519c8d9b8c9a8b99637fcb499160e11b8b52169116600489019360ff60c0969399989794819360e088019b6001600160a01b038092168952166020880152166040860152166060840152608083015260a08201520152565b03925af18015610e6b575b610e4c575b506108c3565b610e649060203d602011610a1057610a0081836101a3565b5038610e46565b610e7361181d565b610e41565b610e97908c3d8e11610e9e575b610e8f81836101a3565b810190611805565b5038610dc5565b503d610e85565b610ead61181d565b610dc0565b610ed29150833d8511610ed8575b610eca81836101a3565b810190611aea565b38610d6a565b503d610ec0565b610ee761181d565b610d63565b6000610f04610efc8386866116d3565b810190611a97565b610f996001600160a01b03989294959397969880991691610f26898685611cbb565b610f3b610a9e6003546001600160a01b031690565b95604051998a98899788966338c7897360e01b885260209e8f9d16600489019360ff60c0969399989794819360e088019b6001600160a01b038092168952166020880152166040860152166060840152608083015260a08201520152565b03925af18015610fce575b610fb0575b50506108a4565b81610fc692903d10610a1057610a0081836101a3565b503880610fa9565b610fd661181d565b610fa4565b60006110596001600160a01b03610ffe610ff68588886116d3565b810190611a52565b94979193959092971692611013818786611cbb565b604051968795869485936348b4aac360e11b855260209b8c9a60048701919260ff60809497969592978160a0860199168552166020840152604083015260608201520152565b03925af1801561108e575b611070575b5050610885565b8161108692903d10610a1057610a0081836101a3565b503880611069565b61109661181d565b611064565b60006001600160a01b0361117d610a9e8361115f6110c56110bd898c8c6116d3565b8101906118a6565b9793949296919816996110d98b15156117c0565b866110f9610a9e610a9e6110ec8d611949565b516001600160a01b031690565b61110d610a9e84546001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b039190911660048201526024810192909252602091908290829060449082908c905af180156111db575b6111bd575b5050546001600160a01b031690565b9460405198899788968795634401edf760e11b8752600487016119d9565b03925af180156111b0575b15610865576111a9903d806000833e6111a181836101a3565b81019061195f565b5038610865565b6111b861181d565b611188565b816111d392903d10610e9e57610e8f81836101a3565b503880611150565b6111e361181d565b61114b565b6000806001600160a01b036112016110bd8689896116d3565b9396919416956112128715156117c0565b80611225610a9e610a9e6110ec89611949565b611239610a9e8b546001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b0391909116600482015260248101929092526020919082908290604490829088905af1801561130f575b6112f1575b50506112b3611295610a9e8a546001600160a01b031690565b94604051988997889687956338ed173960e01b8752600487016119d9565b03925af180156112e4575b6112c9575b50610846565b6112dd903d806000833e6111a181836101a3565b50386112c3565b6112ec61181d565b6112be565b8161130792903d10610e9e57610e8f81836101a3565b50388061127c565b61131761181d565b611277565b6113278285856116d3565b810161133291611775565b91949390926001600160a01b03169061134c8215156117c0565b61135581611eed565b855460405163095ea7b360e01b81526001600160a01b03918216600482015260248101869052602098899791969391929091889188916044918391165a90600091f18015610a9e60009a611409996113de946113c394611467575b61144a575b50546001600160a01b031690565b956113cc6101c5565b9586526001600160a01b031688860152565b604084015260608301526080820152604051948580948193631e51809360e31b835260048301611839565b03925af1801561143d575b61141f575b50610824565b8161143592903d10610a1057610a0081836101a3565b503880611419565b61144561181d565b611414565b611460908c8d3d10610e9e57610e8f81836101a3565b50386113b5565b61146f61181d565b6113b0565b61147f8184846116d3565b810161148a91611775565b9092936001600160a01b03809516908115156114a5906117c0565b6114ae81611e82565b509260019586546114c5906001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b039190911660048201526024810182905260209889979196889188916044918391165a90600091f18015610a9e60009a6115569961152b946113c3946114675761144a5750546001600160a01b031690565b60408401526060830152608082015260405194858094819363c04b8d5960e01b835260048301611839565b03925af1801561158b575b61156d575b5050610803565b8161158392903d10610a1057610a0081836101a3565b503880611566565b61159361181d565b611561565b1561159f57565b60405162461bcd60e51b815260206004820152601f60248201527f546f6f206d616e7920636f6d6d616e647320666f72206578656375746f722e006044820152606490fd5b156115eb57565b60405162461bcd60e51b815260206004820152602560248201527f416d6f756e74206f6620636f6d6d616e6473206d757374206d6174636820696e604482015264383aba399760d91b6064820152608490fd5b50634e487b7160e01b600052601160045260246000fd5b6001906000198114611665570190565b61166d61163e565b0190565b50634e487b7160e01b600052603260045260246000fd5b9190811015611699575b60051b0190565b6116a1611671565b611692565b600c11156116b057565b634e487b7160e01b600052602160045260246000fd5b35600c8110156100f75790565b9190811015611716575b60051b81013590601e19813603018212156100f757019081359167ffffffffffffffff83116100f75760200182360381136100f7579190565b61171e611671565b6116dd565b81601f820112156100f75780359061173a82610234565b9261174860405194856101a3565b828452602083830101116100f757816000926020809301838601378301015290565b35906101d282610404565b9060a0828203126100f75781359067ffffffffffffffff82116100f75761179d918301611723565b9160208201356117ac81610404565b916040810135916080606083013592013590565b156117c757565b60405162461bcd60e51b815260206004820152600c60248201526b5a65726f204164647265737360a01b6044820152606490fd5b801515036100f757565b908160209103126100f7575161181a816117fb565b90565b506040513d6000823e3d90fd5b908160209103126100f7575190565b6020815260a06080611856845183602086015260c0850190610303565b936001600160a01b03602082015116604085015260408101516060850152606081015182850152015191015290565b60209067ffffffffffffffff811161189e5760051b0190565b6116a161014f565b9160a0838303126100f7578235926020928382013593604083013567ffffffffffffffff81116100f75783019180601f840112156100f75782356118e981611885565b936118f760405195866101a3565b818552838086019260051b8201019283116100f7578301905b828210611930575050505091608061192a6060840161176a565b92013590565b838091833561193e81610404565b815201910190611910565b602090805115611957570190565b61166d611671565b60209081818403126100f75780519067ffffffffffffffff82116100f757019180601f840112156100f757825161199581611885565b936119a360405195866101a3565b818552838086019260051b8201019283116100f7578301905b8282106119ca575050505090565b815181529083019083016119bc565b9291909594939560a084019084526020918285015260a0604085015282518091528160c0850193019160005b828110611a275750505050906001600160a01b03608092951660608201520152565b83516001600160a01b031685529381019392810192600101611a05565b359060ff821682036100f757565b91908260c09103126100f7578135611a6981610404565b91611a7660208201611a44565b91611a8360408301611a44565b9160608101359160a0608083013592013590565b908160e09103126100f7578035611aad81610404565b916020820135611abc81610404565b91611ac960408201611a44565b91611ad660608301611a44565b9160808101359160c060a083013592013590565b908160209103126100f7575161181a81610404565b9060e0828203126100f7578135926020830135611b1b81610404565b926040810135611b2a81610404565b926060820135611b3981610404565b9260808301359260a08101359260c082013567ffffffffffffffff81116100f75761181a9201611723565b9491611be493611bc76001600160a01b0392604061181a9a9895611b9c8b8251602080916001600160a01b0381511684520151910152565b6020818101518c84015291015160608b015281516001600160a01b031660808b0152015160a0890152565b1660c086015260e085015261014080610100860152840190610303565b91610120818403910152610303565b908160209103126100f7573590565b15611c0957565b60405162461bcd60e51b815260206004820152601860248201527f496e73756666696369656e74204554482062616c616e636500000000000000006044820152606490fd5b91908260809103126100f7578135611c6581610404565b916020810135611c7481610404565b916060604083013592013561181a816117fb565b908160609103126100f7578035611c9e81610404565b9160406020830135611caf81610404565b92013561181a816117fb565b60405162415c3360e91b815260ff929092166004830152602092611d84928492906001600160a01b0390848160248160008688165af1908115611e04575b600091611de7575b5060405163095ea7b360e01b8082526001600160a01b03949094166004820152602481018590529116919084816044816000875af18015611dda575b611dbd575b506000611d5a610a9e6003546001600160a01b031690565b6040519283526001600160a01b031660048301526024820193909352938492839182906044820190565b03925af18015611db0575b611d97575050565b81611dad92903d10610e9e57610e8f81836101a3565b50565b611db861181d565b611d8f565b611dd390853d8711610e9e57610e8f81836101a3565b5038611d42565b611de261181d565b611d3d565b611dfe9150853d8711610ed857610eca81836101a3565b38611d01565b611e0c61181d565b611cf9565b6000549060ff8260081c16156106eb576080816101d29362010000600160b01b0360606106cf95015160101b169062010000600160b01b031916176000556001600160a01b038151166001600160a01b0319600154161760015561068e61067260208301516001600160a01b031690565b906014825110611ea857602082015160601c916028815110611ea8576034015160601c90565b60405162461bcd60e51b815260206004820152601560248201527f746f416464726573735f6f75744f66426f756e647300000000000000000000006044820152606490fd5b805180601319810111611f0e575b80825110611ea85701600c015160601c90565b611f1661163e565b611efb565b3d15611f46573d90611f2c82610234565b91611f3a60405193846101a3565b82523d6000602084013e565b606090565b60405163a9059cbb60e01b602082019081526001600160a01b03909316602482015260448101939093526000928392908390611f8a8160648101610c78565b51925af1611f96611f1b565b81611fe9575b5015611fa457565b60405162461bcd60e51b815260206004820152601f60248201527f5472616e7366657248656c7065723a205452414e534645525f4641494c4544006044820152606490fd5b8051801592508215611ffe575b505038611f9c565b6120119250602080918301019101611805565b3880611ff6565b60008080938193826040516020810181811067ffffffffffffffff8211176120a2575b604052525af1612049611f1b565b501561205157565b60405162461bcd60e51b815260206004820152602360248201527f5472616e7366657248656c7065723a204554485f5452414e534645525f46414960448201526213115160ea1b6064820152608490fd5b6120aa61014f565b61203b56fea264697066735822122004734597ce29d7951fd64fee6ce3eb7642123fea86567eaf9370c4ec254fb08f64736f6c63430008110033
Deployed Bytecode
0x6080604052600436101561001b575b361561001957600080fd5b005b60003560e01c80630dc91306146100e357806312261ee7146100da578063156e2152146100d15780632c03ae6a146100c85780633fc8cef3146100bf5780634c3677c8146100b65780638f656d22146100ad5780638f8dc10a146100a4578063d7f478ee1461009b5763ff08da6e0361000e57610096610775565b61000e565b506100966105f2565b506100966105ca565b50610096610482565b506100966103dc565b506100966103b4565b50610096610378565b50610096610343565b50610096610124565b506100966100fc565b60009103126100f757565b600080fd5b50346100f75760003660031901126100f75760206001600160a01b0360015416604051908152f35b50346100f75760003660031901126100f75760206001600160a01b0360005460101c16604051908152f35b50634e487b7160e01b600052604160045260246000fd5b60a0810190811067ffffffffffffffff82111761018257604052565b61018a61014f565b604052565b67ffffffffffffffff811161018257604052565b90601f8019910116810190811067ffffffffffffffff82111761018257604052565b604051906101d282610166565b565b604051906040820182811067ffffffffffffffff82111761018257604052565b604051906060820182811067ffffffffffffffff82111761018257604052565b604051906020820182811067ffffffffffffffff82111761018257604052565b60209067ffffffffffffffff8111610252575b601f01601f19160190565b61025a61014f565b610247565b604051906080820182811067ffffffffffffffff8211176102f6575b604052605382527f746e6573732861646472657373207573657229000000000000000000000000006060837f5769746e657373207769746e65737329546f6b656e5065726d697373696f6e7360208201527f286164647265737320746f6b656e2c75696e7432353620616d6f756e7429576960408201520152565b6102fe61014f565b61027b565b919082519283825260005b84811061032f575050826000602080949584010152601f8019910116010190565b60208183018101518483018201520161030e565b50346100f75760003660031901126100f75761037461036061025f565b604051918291602083526020830190610303565b0390f35b50346100f75760003660031901126100f75760206040517ffeed45b61d43f452c933000e813412318e408c352e137cba26cfbe202b355c3a8152f35b50346100f75760003660031901126100f75760206001600160a01b0360045416604051908152f35b50346100f75760003660031901126100f75760206001600160a01b0360035416604051908152f35b6001600160a01b038116036100f757565b60a09060031901126100f75760405161042d81610166565b60043561043981610404565b815260243561044781610404565b602082015260443561045881610404565b604082015260643561046981610404565b606082015260843561047a81610404565b608082015290565b50346100f75761049136610415565b6000549060ff8260081c1615809281936105bc575b811561059c575b5015610531576104d390826104ca600160ff196000541617600055565b61051857611e11565b6104d957005b6104e961ff001960005416600055565b604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb384740249890602090a1005b61052c61010061ff00196000541617600055565b611e11565b60405162461bcd60e51b815260206004820152602e60248201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160448201527f647920696e697469616c697a65640000000000000000000000000000000000006064820152608490fd5b303b159150816105ae575b50386104ad565b6001915060ff1614386105a7565b600160ff82161091506104a6565b50346100f75760003660031901126100f75760206001600160a01b0360025416604051908152f35b50346100f75761060136610415565b6000549060ff8260081c16156106eb576080816100199362010000600160b01b0360606106cf95015160101b169062010000600160b01b031916176000556001600160a01b038151166001600160a01b0319600154161760015561068e61067260208301516001600160a01b031690565b6001600160a01b03166001600160a01b03196002541617600255565b6106c16106a560408301516001600160a01b031690565b6001600160a01b03166001600160a01b03196003541617600355565b01516001600160a01b031690565b6001600160a01b03166001600160a01b03196004541617600455565b60405162461bcd60e51b815260206004820152602b60248201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960448201526a6e697469616c697a696e6760a81b6064820152608490fd5b9181601f840112156100f75782359167ffffffffffffffff83116100f7576020808501948460051b0101116100f757565b5060403660031901126100f75767ffffffffffffffff6004358181116100f7576107a3903690600401610744565b916024359081116100f7576107bc903690600401610744565b906107ca600f851115611598565b6107d58285146115e4565b60005b8481106107e157005b6107f46107ef828787611688565b6116c6565b6107fd816116a6565b15611474575b6108116107ef828787611688565b61081a816116a6565b600180911461131c575b506108336107ef828787611688565b61083c816116a6565b60028091146111e8575b60036108566107ef848989611688565b61085f816116a6565b1461109b575b5060096108766107ef838888611688565b61087f816116a6565b14610fdb575b600b6108956107ef838888611688565b61089e816116a6565b14610eec575b600a6108b46107ef838888611688565b6108bd816116a6565b14610cf7575b60046108d36107ef838888611688565b6108dc816116a6565b14610b93575b60056108f26107ef838888611688565b6108fb816116a6565b14610b13575b60066109116107ef838888611688565b61091a816116a6565b14610a72575b8060086109346107ef610967948989611688565b61093d816116a6565b14610a24575b60076109536107ef838989611688565b61095c816116a6565b1461096c575b611655565b6107d8565b61098261097a8286866116d3565b810190611c88565b916001600160a01b0380911691169161099c8315156117c0565b156109ad5750610962904790612018565b6040516370a0823160e01b81523060048201526109629260209290918381602481855afa938415610a17575b6000946109e8575b5050611f4b565b610a08929450803d10610a10575b610a0081836101a3565b81019061182a565b9138806109e1565b503d6109f6565b610a1f61181d565b6109d9565b610a3a610a328286866116d3565b810190611c4e565b90916001600160a01b0380911691610a538315156117c0565b15610a685750610a639250612018565b610943565b610a639316611f4b565b610a88610a808285856116d3565b810190611bf3565b90610aaa610a9e6004546001600160a01b031690565b6001600160a01b031690565b91823b156100f757604051632e1a7d4d60e01b81526004810191909152610967926000908290602490829084905af18015610b06575b610aed575b509050610920565b80610afa610b009261018f565b806100ec565b38610ae5565b610b0e61181d565b610ae0565b610b21610a808285856116d3565b610b2d81471015611c02565b610b42610a9e6004546001600160a01b031690565b803b156100f757600090600460405180948193630d0e30db60e41b83525af18015610b86575b610b73575b50610901565b80610afa610b809261018f565b38610b6d565b610b8e61181d565b610b68565b610c78610c86610baf610ba78487876116d3565b810190611aff565b9792909596919450610c32610bd3610a9e6000546001600160a01b039060101c1690565b91610bdc6101d4565b6001600160a01b03918216815297816020948b868c01521697610bfd6101f4565b998a52848a01526040890152610c116101d4565b30815298838a0152610c21610214565b951685906001600160a01b03169052565b6040519283918201948591909160206001600160a01b0360408301947ffeed45b61d43f452c933000e813412318e408c352e137cba26cfbe202b355c3a84525116910152565b03601f1981018352826101a3565b51902091610c9261025f565b94823b156100f757600094610cc18692604051988997889687956309be14ff60e11b8752339160048801611b64565b03925af18015610cea575b610cd7575b506108e2565b80610afa610ce49261018f565b38610cd1565b610cf261181d565b610ccc565b610d028184846116d3565b8101610d0d91611a97565b60405162415c3360e91b815260ff861660048201529295939493869390916001600160a01b038916826024815a602094600091f1938415986001600160a01b0398610db460208b99600099610e3698839f610edf575b8b91610eb2575b50610d80610a9e6003546001600160a01b031690565b8b8d60405180978196829563095ea7b360e01b845260048401602090939291936001600160a01b0360408201951681520152565b0393165af18015610ea5575b610e78575b50610ddb610a9e6003546001600160a01b031690565b986040519c8d9b8c9a8b99637fcb499160e11b8b52169116600489019360ff60c0969399989794819360e088019b6001600160a01b038092168952166020880152166040860152166060840152608083015260a08201520152565b03925af18015610e6b575b610e4c575b506108c3565b610e649060203d602011610a1057610a0081836101a3565b5038610e46565b610e7361181d565b610e41565b610e97908c3d8e11610e9e575b610e8f81836101a3565b810190611805565b5038610dc5565b503d610e85565b610ead61181d565b610dc0565b610ed29150833d8511610ed8575b610eca81836101a3565b810190611aea565b38610d6a565b503d610ec0565b610ee761181d565b610d63565b6000610f04610efc8386866116d3565b810190611a97565b610f996001600160a01b03989294959397969880991691610f26898685611cbb565b610f3b610a9e6003546001600160a01b031690565b95604051998a98899788966338c7897360e01b885260209e8f9d16600489019360ff60c0969399989794819360e088019b6001600160a01b038092168952166020880152166040860152166060840152608083015260a08201520152565b03925af18015610fce575b610fb0575b50506108a4565b81610fc692903d10610a1057610a0081836101a3565b503880610fa9565b610fd661181d565b610fa4565b60006110596001600160a01b03610ffe610ff68588886116d3565b810190611a52565b94979193959092971692611013818786611cbb565b604051968795869485936348b4aac360e11b855260209b8c9a60048701919260ff60809497969592978160a0860199168552166020840152604083015260608201520152565b03925af1801561108e575b611070575b5050610885565b8161108692903d10610a1057610a0081836101a3565b503880611069565b61109661181d565b611064565b60006001600160a01b0361117d610a9e8361115f6110c56110bd898c8c6116d3565b8101906118a6565b9793949296919816996110d98b15156117c0565b866110f9610a9e610a9e6110ec8d611949565b516001600160a01b031690565b61110d610a9e84546001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b039190911660048201526024810192909252602091908290829060449082908c905af180156111db575b6111bd575b5050546001600160a01b031690565b9460405198899788968795634401edf760e11b8752600487016119d9565b03925af180156111b0575b15610865576111a9903d806000833e6111a181836101a3565b81019061195f565b5038610865565b6111b861181d565b611188565b816111d392903d10610e9e57610e8f81836101a3565b503880611150565b6111e361181d565b61114b565b6000806001600160a01b036112016110bd8689896116d3565b9396919416956112128715156117c0565b80611225610a9e610a9e6110ec89611949565b611239610a9e8b546001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b0391909116600482015260248101929092526020919082908290604490829088905af1801561130f575b6112f1575b50506112b3611295610a9e8a546001600160a01b031690565b94604051988997889687956338ed173960e01b8752600487016119d9565b03925af180156112e4575b6112c9575b50610846565b6112dd903d806000833e6111a181836101a3565b50386112c3565b6112ec61181d565b6112be565b8161130792903d10610e9e57610e8f81836101a3565b50388061127c565b61131761181d565b611277565b6113278285856116d3565b810161133291611775565b91949390926001600160a01b03169061134c8215156117c0565b61135581611eed565b855460405163095ea7b360e01b81526001600160a01b03918216600482015260248101869052602098899791969391929091889188916044918391165a90600091f18015610a9e60009a611409996113de946113c394611467575b61144a575b50546001600160a01b031690565b956113cc6101c5565b9586526001600160a01b031688860152565b604084015260608301526080820152604051948580948193631e51809360e31b835260048301611839565b03925af1801561143d575b61141f575b50610824565b8161143592903d10610a1057610a0081836101a3565b503880611419565b61144561181d565b611414565b611460908c8d3d10610e9e57610e8f81836101a3565b50386113b5565b61146f61181d565b6113b0565b61147f8184846116d3565b810161148a91611775565b9092936001600160a01b03809516908115156114a5906117c0565b6114ae81611e82565b509260019586546114c5906001600160a01b031690565b60405163095ea7b360e01b81526001600160a01b039190911660048201526024810182905260209889979196889188916044918391165a90600091f18015610a9e60009a6115569961152b946113c3946114675761144a5750546001600160a01b031690565b60408401526060830152608082015260405194858094819363c04b8d5960e01b835260048301611839565b03925af1801561158b575b61156d575b5050610803565b8161158392903d10610a1057610a0081836101a3565b503880611566565b61159361181d565b611561565b1561159f57565b60405162461bcd60e51b815260206004820152601f60248201527f546f6f206d616e7920636f6d6d616e647320666f72206578656375746f722e006044820152606490fd5b156115eb57565b60405162461bcd60e51b815260206004820152602560248201527f416d6f756e74206f6620636f6d6d616e6473206d757374206d6174636820696e604482015264383aba399760d91b6064820152608490fd5b50634e487b7160e01b600052601160045260246000fd5b6001906000198114611665570190565b61166d61163e565b0190565b50634e487b7160e01b600052603260045260246000fd5b9190811015611699575b60051b0190565b6116a1611671565b611692565b600c11156116b057565b634e487b7160e01b600052602160045260246000fd5b35600c8110156100f75790565b9190811015611716575b60051b81013590601e19813603018212156100f757019081359167ffffffffffffffff83116100f75760200182360381136100f7579190565b61171e611671565b6116dd565b81601f820112156100f75780359061173a82610234565b9261174860405194856101a3565b828452602083830101116100f757816000926020809301838601378301015290565b35906101d282610404565b9060a0828203126100f75781359067ffffffffffffffff82116100f75761179d918301611723565b9160208201356117ac81610404565b916040810135916080606083013592013590565b156117c757565b60405162461bcd60e51b815260206004820152600c60248201526b5a65726f204164647265737360a01b6044820152606490fd5b801515036100f757565b908160209103126100f7575161181a816117fb565b90565b506040513d6000823e3d90fd5b908160209103126100f7575190565b6020815260a06080611856845183602086015260c0850190610303565b936001600160a01b03602082015116604085015260408101516060850152606081015182850152015191015290565b60209067ffffffffffffffff811161189e5760051b0190565b6116a161014f565b9160a0838303126100f7578235926020928382013593604083013567ffffffffffffffff81116100f75783019180601f840112156100f75782356118e981611885565b936118f760405195866101a3565b818552838086019260051b8201019283116100f7578301905b828210611930575050505091608061192a6060840161176a565b92013590565b838091833561193e81610404565b815201910190611910565b602090805115611957570190565b61166d611671565b60209081818403126100f75780519067ffffffffffffffff82116100f757019180601f840112156100f757825161199581611885565b936119a360405195866101a3565b818552838086019260051b8201019283116100f7578301905b8282106119ca575050505090565b815181529083019083016119bc565b9291909594939560a084019084526020918285015260a0604085015282518091528160c0850193019160005b828110611a275750505050906001600160a01b03608092951660608201520152565b83516001600160a01b031685529381019392810192600101611a05565b359060ff821682036100f757565b91908260c09103126100f7578135611a6981610404565b91611a7660208201611a44565b91611a8360408301611a44565b9160608101359160a0608083013592013590565b908160e09103126100f7578035611aad81610404565b916020820135611abc81610404565b91611ac960408201611a44565b91611ad660608301611a44565b9160808101359160c060a083013592013590565b908160209103126100f7575161181a81610404565b9060e0828203126100f7578135926020830135611b1b81610404565b926040810135611b2a81610404565b926060820135611b3981610404565b9260808301359260a08101359260c082013567ffffffffffffffff81116100f75761181a9201611723565b9491611be493611bc76001600160a01b0392604061181a9a9895611b9c8b8251602080916001600160a01b0381511684520151910152565b6020818101518c84015291015160608b015281516001600160a01b031660808b0152015160a0890152565b1660c086015260e085015261014080610100860152840190610303565b91610120818403910152610303565b908160209103126100f7573590565b15611c0957565b60405162461bcd60e51b815260206004820152601860248201527f496e73756666696369656e74204554482062616c616e636500000000000000006044820152606490fd5b91908260809103126100f7578135611c6581610404565b916020810135611c7481610404565b916060604083013592013561181a816117fb565b908160609103126100f7578035611c9e81610404565b9160406020830135611caf81610404565b92013561181a816117fb565b60405162415c3360e91b815260ff929092166004830152602092611d84928492906001600160a01b0390848160248160008688165af1908115611e04575b600091611de7575b5060405163095ea7b360e01b8082526001600160a01b03949094166004820152602481018590529116919084816044816000875af18015611dda575b611dbd575b506000611d5a610a9e6003546001600160a01b031690565b6040519283526001600160a01b031660048301526024820193909352938492839182906044820190565b03925af18015611db0575b611d97575050565b81611dad92903d10610e9e57610e8f81836101a3565b50565b611db861181d565b611d8f565b611dd390853d8711610e9e57610e8f81836101a3565b5038611d42565b611de261181d565b611d3d565b611dfe9150853d8711610ed857610eca81836101a3565b38611d01565b611e0c61181d565b611cf9565b6000549060ff8260081c16156106eb576080816101d29362010000600160b01b0360606106cf95015160101b169062010000600160b01b031916176000556001600160a01b038151166001600160a01b0319600154161760015561068e61067260208301516001600160a01b031690565b906014825110611ea857602082015160601c916028815110611ea8576034015160601c90565b60405162461bcd60e51b815260206004820152601560248201527f746f416464726573735f6f75744f66426f756e647300000000000000000000006044820152606490fd5b805180601319810111611f0e575b80825110611ea85701600c015160601c90565b611f1661163e565b611efb565b3d15611f46573d90611f2c82610234565b91611f3a60405193846101a3565b82523d6000602084013e565b606090565b60405163a9059cbb60e01b602082019081526001600160a01b03909316602482015260448101939093526000928392908390611f8a8160648101610c78565b51925af1611f96611f1b565b81611fe9575b5015611fa457565b60405162461bcd60e51b815260206004820152601f60248201527f5472616e7366657248656c7065723a205452414e534645525f4641494c4544006044820152606490fd5b8051801592508215611ffe575b505038611f9c565b6120119250602080918301019101611805565b3880611ff6565b60008080938193826040516020810181811067ffffffffffffffff8211176120a2575b604052525af1612049611f1b565b501561205157565b60405162461bcd60e51b815260206004820152602360248201527f5472616e7366657248656c7065723a204554485f5452414e534645525f46414960448201526213115160ea1b6064820152608490fd5b6120aa61014f565b61203b56fea264697066735822122004734597ce29d7951fd64fee6ce3eb7642123fea86567eaf9370c4ec254fb08f64736f6c63430008110033
Loading...
Loading
Loading...
Loading
Loading...
Loading
Net Worth in USD
$1.00
Net Worth in GLMR
Token Allocations
AXLUSDC
100.00%
Multichain Portfolio | 35 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|---|---|---|---|---|
| GLMR | 100.00% | $0.999684 | 1 | $0.9996 |
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.