Source Code
Latest 1 internal transaction
Advanced mode:
| Parent Transaction Hash | Method | Block |
From
|
|
To
|
||
|---|---|---|---|---|---|---|---|
| 0x415565b0 | 15256671 | 1335 days ago | 0.00997 ETH |
Loading...
Loading
Loading...
Loading
Cross-Chain Transactions
Loading...
Loading
Contract Name:
BalancerV2PortalIn
Compiler Version
v0.8.11+commit.d7f03943
Contract Source Code (Solidity Standard Json-Input format)
/// Copyright (C) 2022 Portals.fi
/// @author Portals.fi
/// @notice This contract adds liquidity to Balancer V2 like pools using any ERC20 token or the network token.
/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
import "../base/PortalBaseV1.sol";
import "../interface/IPortalRegistry.sol";
import "./interface/IBalancerVault.sol";
/// Thrown when insufficient liquidity is received after deposit
/// @param buyAmount The amount of liquidity received
/// @param minBuyAmount The minimum acceptable quantity of liquidity received
error InsufficientBuy(uint256 buyAmount, uint256 minBuyAmount);
contract BalancerV2PortalIn is PortalBaseV1 {
using SafeTransferLib for address;
using SafeTransferLib for ERC20;
IBalancerVault public immutable VAULT;
/// @notice Emitted when a portal is entered
/// @param sellToken The ERC20 token address to spend (address(0) if network token)
/// @param sellAmount The quantity of sellToken to Portal in
/// @param buyToken The ERC20 token address to buy (address(0) if network token)
/// @param buyAmount The quantity of buyToken received
/// @param fee The fee in BPS
/// @param sender The msg.sender
/// @param partner The front end operator address
event PortalIn(
address sellToken,
uint256 sellAmount,
address buyToken,
uint256 buyAmount,
uint256 fee,
address indexed sender,
address indexed partner
);
constructor(
bytes32 protocolId,
PortalType portalType,
IPortalRegistry registry,
address exchange,
address wrappedNetworkToken,
uint256 fee,
IBalancerVault _vault
)
PortalBaseV1(
protocolId,
portalType,
registry,
exchange,
wrappedNetworkToken,
fee
)
{
VAULT = _vault;
}
/// @notice Add liquidity to Balancer V2 like pools with network tokens/ERC20 tokens
/// @param sellToken The ERC20 token address to spend (address(0) if network token)
/// @param sellAmount The quantity of sellToken to Portal in
/// @param intermediateToken The intermediate token to swap to (must be one of the pool tokens)
/// @param buyToken The Balancer V2 pool address (i.e. the LP token address)
/// @param minBuyAmount The minimum quantity of buyTokens to receive. Reverts otherwise
/// @param target The excecution target for the intermediate swap
/// @param data The encoded call for the intermediate swap
/// @param partner The front end operator address
/// @return buyAmount The quantity of buyToken acquired
function portalIn(
address sellToken,
uint256 sellAmount,
address intermediateToken,
address buyToken,
uint256 minBuyAmount,
address target,
bytes calldata data,
address partner,
bytes calldata poolData
) external payable pausable returns (uint256 buyAmount) {
uint256 amount = _transferFromCaller(sellToken, sellAmount);
amount = _getFeeAmount(amount, fee);
amount = _execute(sellToken, amount, intermediateToken, target, data);
buyAmount = _deposit(intermediateToken, amount, buyToken, poolData);
if (buyAmount < minBuyAmount)
revert InsufficientBuy(buyAmount, minBuyAmount);
emit PortalIn(
sellToken,
sellAmount,
buyToken,
buyAmount,
fee,
msg.sender,
partner
);
}
/// @notice Deposits the sellToken into the pool
/// @param sellToken The ERC20 token address to spend (address(0) if network token)
/// @param sellAmount The quantity of sellToken to deposit
/// @param buyToken The Balancer V2 pool token address
/// @param poolData Encoded pool data including the following:
/// poolId The balancer pool ID
/// assets An array of all tokens in the pool
/// The index of the sellToken in the pool
/// @return liquidity The quantity of LP tokens acquired
function _deposit(
address sellToken,
uint256 sellAmount,
address buyToken,
bytes calldata poolData
) internal returns (uint256) {
(bytes32 poolId, address[] memory assets, uint256 index) = abi.decode(
poolData,
(bytes32, address[], uint256)
);
uint256[] memory maxAmountsIn = new uint256[](assets.length);
maxAmountsIn[index] = sellAmount;
bytes memory userData = abi.encode(1, maxAmountsIn, 0);
uint256 balance = _getBalance(msg.sender, buyToken);
uint256 valueToSend;
if (sellToken == address(0)) {
valueToSend = sellAmount;
} else {
_approve(sellToken, address(VAULT), sellAmount);
}
VAULT.joinPool{ value: valueToSend }(
poolId,
address(this),
msg.sender,
IBalancerVault.JoinPoolRequest({
assets: assets,
maxAmountsIn: maxAmountsIn,
userData: userData,
fromInternalBalance: false
})
);
return _getBalance(msg.sender, buyToken) - balance;
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (access/Ownable.sol)
pragma solidity ^0.8.0;
import "../utils/Context.sol";
/**
* @dev Contract module which provides a basic access control mechanism, where
* there is an account (an owner) that can be granted exclusive access to
* specific functions.
*
* By default, the owner account will be the one that deploys the contract. This
* can later be changed with {transferOwnership}.
*
* This module is used through inheritance. It will make available the modifier
* `onlyOwner`, which can be applied to your functions to restrict their use to
* the owner.
*/
abstract contract Ownable is Context {
address private _owner;
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
/**
* @dev Initializes the contract setting the deployer as the initial owner.
*/
constructor() {
_transferOwnership(_msgSender());
}
/**
* @dev Returns the address of the current owner.
*/
function owner() public view virtual returns (address) {
return _owner;
}
/**
* @dev Throws if called by any account other than the owner.
*/
modifier onlyOwner() {
require(owner() == _msgSender(), "Ownable: caller is not the owner");
_;
}
/**
* @dev Leaves the contract without owner. It will not be possible to call
* `onlyOwner` functions anymore. Can only be called by the current owner.
*
* NOTE: Renouncing ownership will leave the contract without an owner,
* thereby removing any functionality that is only available to the owner.
*/
function renounceOwnership() public virtual onlyOwner {
_transferOwnership(address(0));
}
/**
* @dev Transfers ownership of the contract to a new account (`newOwner`).
* Can only be called by the current owner.
*/
function transferOwnership(address newOwner) public virtual onlyOwner {
require(newOwner != address(0), "Ownable: new owner is the zero address");
_transferOwnership(newOwner);
}
/**
* @dev Transfers ownership of the contract to a new account (`newOwner`).
* Internal function without access restriction.
*/
function _transferOwnership(address newOwner) internal virtual {
address oldOwner = _owner;
_owner = newOwner;
emit OwnershipTransferred(oldOwner, newOwner);
}
}// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)
pragma solidity ^0.8.0;
/**
* @dev Provides information about the current execution context, including the
* sender of the transaction and its data. While these are generally available
* via msg.sender and msg.data, they should not be accessed in such a direct
* manner, since when dealing with meta-transactions the account sending and
* paying for execution may not be the actual sender (as far as an application
* is concerned).
*
* This contract is only required for intermediate, library-like contracts.
*/
abstract contract Context {
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
}/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
interface IBalancerVault {
/**
* @dev Called by users to join a Pool, which transfers tokens from `sender` into the Pool's balance. This will
* trigger custom Pool behavior, which will typically grant something in return to `recipient` - often tokenized
* Pool shares.
*
* If the caller is not `sender`, it must be an authorized relayer for them.
*
* The `assets` and `maxAmountsIn` arrays must have the same length, and each entry indicates the maximum amount
* to send for each asset. The amounts to send are decided by the Pool and not the Vault: it just enforces
* these maximums.
*
* If joining a Pool that holds WETH, it is possible to send ETH directly: the Vault will do the wrapping. To enable
* this mechanism, the IAsset sentinel value (the zero address) must be passed in the `assets` array instead of the
* WETH address. Note that it is not possible to combine ETH and WETH in the same join. Any excess ETH will be sent
* back to the caller (not the sender, which is important for relayers).
*
* `assets` must have the same length and order as the array returned by `getPoolTokens`. This prevents issues when
* interacting with Pools that register and deregister tokens frequently. If sending ETH however, the array must be
* sorted *before* replacing the WETH address with the ETH sentinel value (the zero address), which means the final
* `assets` array might not be sorted. Pools with no registered tokens cannot be joined.
*
* If `fromInternalBalance` is true, the caller's Internal Balance will be preferred: ERC20 transfers will only
* be made for the difference between the requested amount and Internal Balance (if any). Note that ETH cannot be
* withdrawn from Internal Balance: attempting to do so will trigger a revert.
*
* This causes the Vault to call the `IBasePool.onJoinPool` hook on the Pool's contract, where Pools implement
* their own custom logic. This typically requires additional information from the user (such as the expected number
* of Pool shares). This can be encoded in the `userData` argument, which is ignored by the Vault and passed
* directly to the Pool's contract, as is `recipient`.
*
* Emits a `PoolBalanceChanged` event.
*/
function joinPool(
bytes32 poolId,
address sender,
address recipient,
JoinPoolRequest memory request
) external payable;
struct JoinPoolRequest {
address[] assets;
uint256[] maxAmountsIn;
bytes userData;
bool fromInternalBalance;
}
function getPoolTokens(bytes32 poolId)
external
view
returns (
address[] memory tokens,
uint256[] memory balances,
uint256 lastChangeBlock
);
}/// Copyright (C) 2022 Portals.fi
/// @author Portals.fi
/// @notice Base contract inherited by Portal Factories
/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
import "@openzeppelin/contracts/access/Ownable.sol";
import "../libraries/solmate/utils/SafeTransferLib.sol";
import "../interface/IWETH.sol";
import "../interface/IPortalFactory.sol";
import "../interface/IPortalRegistry.sol";
abstract contract PortalBaseV1 is Ownable {
using SafeTransferLib for address;
using SafeTransferLib for ERC20;
// Active status of this contract. If false, contract is active (i.e un-paused)
bool public paused;
// Fee in basis points (bps)
uint256 public fee;
// Address of the Portal Registry
IPortalRegistry public registry;
// Address of the exchange used for swaps
address public immutable exchange;
// Address of the wrapped network token (e.g. WETH, wMATIC, wFTM, wAVAX, etc.)
address public immutable wrappedNetworkToken;
// Circuit breaker
modifier pausable() {
require(!paused, "Paused");
_;
}
constructor(
bytes32 protocolId,
PortalType portalType,
IPortalRegistry _registry,
address _exchange,
address _wrappedNetworkToken,
uint256 _fee
) {
wrappedNetworkToken = _wrappedNetworkToken;
setFee(_fee);
exchange = _exchange;
registry = _registry;
registry.addPortal(address(this), portalType, protocolId);
transferOwnership(registry.owner());
}
/// @notice Transfers tokens or the network token from the caller to this contract
/// @param token The address of the token to transfer (address(0) if network token)
/// @param quantity The quantity of tokens to transfer from the caller
/// @dev quantity must == msg.value when token == address(0)
/// @dev msg.value must == 0 when token != address(0)
/// @return The quantity of tokens or network tokens transferred from the caller to this contract
function _transferFromCaller(address token, uint256 quantity)
internal
virtual
returns (uint256)
{
if (token == address(0)) {
require(
msg.value > 0 && msg.value == quantity,
"Invalid quantity or msg.value"
);
return msg.value;
}
require(
quantity > 0 && msg.value == 0,
"Invalid quantity or msg.value"
);
ERC20(token).safeTransferFrom(msg.sender, address(this), quantity);
return quantity;
}
/// @notice Returns the quantity of tokens or network tokens after accounting for the fee
/// @param quantity The quantity of tokens to subtract the fee from
/// @param feeBps The fee in basis points (BPS)
/// @return The quantity of tokens or network tokens to transact with less the fee
function _getFeeAmount(uint256 quantity, uint256 feeBps)
internal
pure
returns (uint256)
{
return quantity - (quantity * feeBps) / 10000;
}
/// @notice Executes swap or portal data at the target address
/// @param sellToken The sell token
/// @param sellAmount The quantity of sellToken (in sellToken base units) to send
/// @param buyToken The buy token
/// @param target The execution target for the data
/// @param data The swap or portal data
/// @return amountBought Quantity of buyToken acquired
function _execute(
address sellToken,
uint256 sellAmount,
address buyToken,
address target,
bytes memory data
) internal virtual returns (uint256 amountBought) {
if (sellToken == buyToken) {
return sellAmount;
}
if (sellToken == address(0) && buyToken == wrappedNetworkToken) {
IWETH(wrappedNetworkToken).deposit{ value: sellAmount }();
return sellAmount;
}
if (sellToken == wrappedNetworkToken && buyToken == address(0)) {
IWETH(wrappedNetworkToken).withdraw(sellAmount);
return sellAmount;
}
uint256 valueToSend;
if (sellToken == address(0)) {
valueToSend = sellAmount;
} else {
_approve(sellToken, target, sellAmount);
}
uint256 initialBalance = _getBalance(address(this), buyToken);
require(
target == exchange || registry.isPortal(target),
"Unauthorized target"
);
(bool success, bytes memory returnData) = target.call{
value: valueToSend
}(data);
require(success, string(returnData));
amountBought = _getBalance(address(this), buyToken) - initialBalance;
require(amountBought > 0, "Invalid execution");
}
/// @notice Get the token or network token balance of an account
/// @param account The owner of the tokens or network tokens whose balance is being queried
/// @param token The address of the token (address(0) if network token)
/// @return The owner's token or network token balance
function _getBalance(address account, address token)
internal
view
returns (uint256)
{
if (token == address(0)) {
return account.balance;
} else {
return ERC20(token).balanceOf(account);
}
}
/// @notice Approve a token for spending with finite allowance
/// @param token The ERC20 token to approve
/// @param spender The spender of the token
/// @param amount The allowance to grant to the spender
function _approve(
address token,
address spender,
uint256 amount
) internal {
ERC20 _token = ERC20(token);
_token.safeApprove(spender, 0);
_token.safeApprove(spender, amount);
}
/// @notice Collects tokens or network tokens from this contract
/// @param tokens An array of the tokens to withdraw (address(0) if network token)
function collect(address[] calldata tokens) external {
address collector = registry.collector();
for (uint256 i = 0; i < tokens.length; i++) {
uint256 qty;
if (tokens[i] == address(0)) {
qty = address(this).balance;
collector.safeTransferETH(qty);
} else {
qty = ERC20(tokens[i]).balanceOf(address(this));
ERC20(tokens[i]).safeTransfer(collector, qty);
}
}
}
/// @dev Pause or unpause the contract
function pause() external onlyOwner {
paused = !paused;
}
/// @notice Sets the fee
/// @param _fee The new fee amount between 0.06-1%
function setFee(uint256 _fee) public onlyOwner {
require(_fee >= 6 && _fee <= 100, "Invalid Fee");
fee = _fee;
}
/// @notice Updates the registry
/// @param _registry The address of the new registry
function updateRegistry(IPortalRegistry _registry) external onlyOwner {
registry = _registry;
}
/// @notice Reverts if networks tokens are sent directly to this contract
receive() external payable {
require(msg.sender != tx.origin);
}
}/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
import "./IPortalRegistry.sol";
interface IPortalFactory {
function fee() external view returns (uint256 fee);
function registry() external view returns (IPortalRegistry registry);
}/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
enum PortalType {
IN,
OUT
}
interface IPortalRegistry {
function addPortal(
address portal,
PortalType portalType,
bytes32 protocolId
) external;
function addPortalFactory(
address portalFactory,
PortalType portalType,
bytes32 protocolId
) external;
function removePortal(bytes32 protocolId, PortalType portalType) external;
function owner() external view returns (address owner);
function registrars(address origin) external view returns (bool isDeployer);
function collector() external view returns (address collector);
function isPortal(address portal) external view returns (bool isPortal);
}/// SPDX-License-Identifier: GPL-3.0
pragma solidity 0.8.11;
interface IWETH {
function deposit() external payable;
function withdraw(uint256 wad) external;
}// SPDX-License-Identifier: AGPL-3.0-only
pragma solidity >=0.8.0;
/// @notice Modern and gas efficient ERC20 + EIP-2612 implementation.
/// @author Solmate (https://github.com/Rari-Capital/solmate/blob/main/src/tokens/ERC20.sol)
/// @author Modified from Uniswap (https://github.com/Uniswap/uniswap-v2-core/blob/master/contracts/UniswapV2ERC20.sol)
/// @dev Do not manually set balances without updating totalSupply, as the sum of all user balances must not exceed it.
abstract contract ERC20 {
/*//////////////////////////////////////////////////////////////
EVENTS
//////////////////////////////////////////////////////////////*/
event Transfer(address indexed from, address indexed to, uint256 amount);
event Approval(
address indexed owner,
address indexed spender,
uint256 amount
);
/*//////////////////////////////////////////////////////////////
METADATA STORAGE
//////////////////////////////////////////////////////////////*/
string public name;
string public symbol;
uint8 public immutable decimals;
/*//////////////////////////////////////////////////////////////
ERC20 STORAGE
//////////////////////////////////////////////////////////////*/
uint256 public totalSupply;
mapping(address => uint256) public balanceOf;
mapping(address => mapping(address => uint256)) public allowance;
/*//////////////////////////////////////////////////////////////
EIP-2612 STORAGE
//////////////////////////////////////////////////////////////*/
uint256 internal immutable INITIAL_CHAIN_ID;
bytes32 internal immutable INITIAL_DOMAIN_SEPARATOR;
mapping(address => uint256) public nonces;
/*//////////////////////////////////////////////////////////////
CONSTRUCTOR
//////////////////////////////////////////////////////////////*/
constructor(
string memory _name,
string memory _symbol,
uint8 _decimals
) {
name = _name;
symbol = _symbol;
decimals = _decimals;
INITIAL_CHAIN_ID = block.chainid;
INITIAL_DOMAIN_SEPARATOR = computeDomainSeparator();
}
/*//////////////////////////////////////////////////////////////
ERC20 LOGIC
//////////////////////////////////////////////////////////////*/
function approve(address spender, uint256 amount)
public
virtual
returns (bool)
{
allowance[msg.sender][spender] = amount;
emit Approval(msg.sender, spender, amount);
return true;
}
function transfer(address to, uint256 amount)
public
virtual
returns (bool)
{
balanceOf[msg.sender] -= amount;
// Cannot overflow because the sum of all user
// balances can't exceed the max uint256 value.
unchecked {
balanceOf[to] += amount;
}
emit Transfer(msg.sender, to, amount);
return true;
}
function transferFrom(
address from,
address to,
uint256 amount
) public virtual returns (bool) {
uint256 allowed = allowance[from][msg.sender]; // Saves gas for limited approvals.
if (allowed != type(uint256).max)
allowance[from][msg.sender] = allowed - amount;
balanceOf[from] -= amount;
// Cannot overflow because the sum of all user
// balances can't exceed the max uint256 value.
unchecked {
balanceOf[to] += amount;
}
emit Transfer(from, to, amount);
return true;
}
/*//////////////////////////////////////////////////////////////
EIP-2612 LOGIC
//////////////////////////////////////////////////////////////*/
function permit(
address owner,
address spender,
uint256 value,
uint256 deadline,
uint8 v,
bytes32 r,
bytes32 s
) public virtual {
require(deadline >= block.timestamp, "PERMIT_DEADLINE_EXPIRED");
// Unchecked because the only math done is incrementing
// the owner's nonce which cannot realistically overflow.
unchecked {
address recoveredAddress = ecrecover(
keccak256(
abi.encodePacked(
"\x19\x01",
DOMAIN_SEPARATOR(),
keccak256(
abi.encode(
keccak256(
"Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"
),
owner,
spender,
value,
nonces[owner]++,
deadline
)
)
)
),
v,
r,
s
);
require(
recoveredAddress != address(0) && recoveredAddress == owner,
"INVALID_SIGNER"
);
allowance[recoveredAddress][spender] = value;
}
emit Approval(owner, spender, value);
}
function DOMAIN_SEPARATOR() public view virtual returns (bytes32) {
return
block.chainid == INITIAL_CHAIN_ID
? INITIAL_DOMAIN_SEPARATOR
: computeDomainSeparator();
}
function computeDomainSeparator() internal view virtual returns (bytes32) {
return
keccak256(
abi.encode(
keccak256(
"EIP712Domain(string name,string version,uint256 chainId,address verifyingContract)"
),
keccak256(bytes(name)),
keccak256("1"),
block.chainid,
address(this)
)
);
}
/*//////////////////////////////////////////////////////////////
INTERNAL MINT/BURN LOGIC
//////////////////////////////////////////////////////////////*/
function _mint(address to, uint256 amount) internal virtual {
totalSupply += amount;
// Cannot overflow because the sum of all user
// balances can't exceed the max uint256 value.
unchecked {
balanceOf[to] += amount;
}
emit Transfer(address(0), to, amount);
}
function _burn(address from, uint256 amount) internal virtual {
balanceOf[from] -= amount;
// Cannot underflow because a user's balance
// will never be larger than the total supply.
unchecked {
totalSupply -= amount;
}
emit Transfer(from, address(0), amount);
}
}// SPDX-License-Identifier: AGPL-3.0-only
pragma solidity >=0.8.0;
import { ERC20 } from "../tokens/ERC20.sol";
/// @notice Safe ETH and ERC20 transfer library that gracefully handles missing return values.
/// @author Solmate (https://github.com/Rari-Capital/solmate/blob/main/src/utils/SafeTransferLib.sol)
/// @dev Use with caution! Some functions in this library knowingly create dirty bits at the destination of the free memory pointer.
/// @dev Note that none of the functions in this library check that a token has code at all! That responsibility is delegated to the caller.
library SafeTransferLib {
event Debug(bool one, bool two, uint256 retsize);
/*//////////////////////////////////////////////////////////////
ETH OPERATIONS
//////////////////////////////////////////////////////////////*/
function safeTransferETH(address to, uint256 amount) internal {
bool success;
assembly {
// Transfer the ETH and store if it succeeded or not.
success := call(gas(), to, amount, 0, 0, 0, 0)
}
require(success, "ETH_TRANSFER_FAILED");
}
/*//////////////////////////////////////////////////////////////
ERC20 OPERATIONS
//////////////////////////////////////////////////////////////*/
function safeTransferFrom(
ERC20 token,
address from,
address to,
uint256 amount
) internal {
bool success;
assembly {
// Get a pointer to some free memory.
let freeMemoryPointer := mload(0x40)
// Write the abi-encoded calldata into memory, beginning with the function selector.
mstore(
freeMemoryPointer,
0x23b872dd00000000000000000000000000000000000000000000000000000000
)
mstore(add(freeMemoryPointer, 4), from) // Append the "from" argument.
mstore(add(freeMemoryPointer, 36), to) // Append the "to" argument.
mstore(add(freeMemoryPointer, 68), amount) // Append the "amount" argument.
success := and(
// Set success to whether the call reverted, if not we check it either
// returned exactly 1 (can't just be non-zero data), or had no return data.
or(
and(eq(mload(0), 1), gt(returndatasize(), 31)),
iszero(returndatasize())
),
// We use 100 because the length of our calldata totals up like so: 4 + 32 * 3.
// We use 0 and 32 to copy up to 32 bytes of return data into the scratch space.
// Counterintuitively, this call must be positioned second to the or() call in the
// surrounding and() call or else returndatasize() will be zero during the computation.
call(gas(), token, 0, freeMemoryPointer, 100, 0, 32)
)
}
require(success, "TRANSFER_FROM_FAILED");
}
function safeTransfer(
ERC20 token,
address to,
uint256 amount
) internal {
bool success;
assembly {
// Get a pointer to some free memory.
let freeMemoryPointer := mload(0x40)
// Write the abi-encoded calldata into memory, beginning with the function selector.
mstore(
freeMemoryPointer,
0xa9059cbb00000000000000000000000000000000000000000000000000000000
)
mstore(add(freeMemoryPointer, 4), to) // Append the "to" argument.
mstore(add(freeMemoryPointer, 36), amount) // Append the "amount" argument.
success := and(
// Set success to whether the call reverted, if not we check it either
// returned exactly 1 (can't just be non-zero data), or had no return data.
or(
and(eq(mload(0), 1), gt(returndatasize(), 31)),
iszero(returndatasize())
),
// We use 68 because the length of our calldata totals up like so: 4 + 32 * 2.
// We use 0 and 32 to copy up to 32 bytes of return data into the scratch space.
// Counterintuitively, this call must be positioned second to the or() call in the
// surrounding and() call or else returndatasize() will be zero during the computation.
call(gas(), token, 0, freeMemoryPointer, 68, 0, 32)
)
}
require(success, "TRANSFER_FAILED");
}
function safeApprove(
ERC20 token,
address to,
uint256 amount
) internal {
bool success;
assembly {
// Get a pointer to some free memory.
let freeMemoryPointer := mload(0x40)
// Write the abi-encoded calldata into memory, beginning with the function selector.
mstore(
freeMemoryPointer,
0x095ea7b300000000000000000000000000000000000000000000000000000000
)
mstore(add(freeMemoryPointer, 4), to) // Append the "to" argument.
mstore(add(freeMemoryPointer, 36), amount) // Append the "amount" argument.
success := and(
// Set success to whether the call reverted, if not we check it either
// returned exactly 1 (can't just be non-zero data), or had no return data.
or(
and(eq(mload(0), 1), gt(returndatasize(), 31)),
iszero(returndatasize())
),
// We use 68 because the length of our calldata totals up like so: 4 + 32 * 2.
// We use 0 and 32 to copy up to 32 bytes of return data into the scratch space.
// Counterintuitively, this call must be positioned second to the or() call in the
// surrounding and() call or else returndatasize() will be zero during the computation.
call(gas(), token, 0, freeMemoryPointer, 68, 0, 32)
)
}
require(success, "APPROVE_FAILED");
}
}{
"evmVersion": "london",
"libraries": {},
"metadata": {
"bytecodeHash": "ipfs",
"useLiteralContent": true
},
"optimizer": {
"enabled": true,
"runs": 1000
},
"remappings": [],
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"bytes32","name":"protocolId","type":"bytes32"},{"internalType":"enum PortalType","name":"portalType","type":"uint8"},{"internalType":"contract IPortalRegistry","name":"registry","type":"address"},{"internalType":"address","name":"exchange","type":"address"},{"internalType":"address","name":"wrappedNetworkToken","type":"address"},{"internalType":"uint256","name":"fee","type":"uint256"},{"internalType":"contract IBalancerVault","name":"_vault","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[{"internalType":"uint256","name":"buyAmount","type":"uint256"},{"internalType":"uint256","name":"minBuyAmount","type":"uint256"}],"name":"InsufficientBuy","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"sellToken","type":"address"},{"indexed":false,"internalType":"uint256","name":"sellAmount","type":"uint256"},{"indexed":false,"internalType":"address","name":"buyToken","type":"address"},{"indexed":false,"internalType":"uint256","name":"buyAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"fee","type":"uint256"},{"indexed":true,"internalType":"address","name":"sender","type":"address"},{"indexed":true,"internalType":"address","name":"partner","type":"address"}],"name":"PortalIn","type":"event"},{"inputs":[],"name":"VAULT","outputs":[{"internalType":"contract IBalancerVault","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"tokens","type":"address[]"}],"name":"collect","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"exchange","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"fee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"pause","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"paused","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"sellToken","type":"address"},{"internalType":"uint256","name":"sellAmount","type":"uint256"},{"internalType":"address","name":"intermediateToken","type":"address"},{"internalType":"address","name":"buyToken","type":"address"},{"internalType":"uint256","name":"minBuyAmount","type":"uint256"},{"internalType":"address","name":"target","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"address","name":"partner","type":"address"},{"internalType":"bytes","name":"poolData","type":"bytes"}],"name":"portalIn","outputs":[{"internalType":"uint256","name":"buyAmount","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"registry","outputs":[{"internalType":"contract IPortalRegistry","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_fee","type":"uint256"}],"name":"setFee","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"contract IPortalRegistry","name":"_registry","type":"address"}],"name":"updateRegistry","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"wrappedNetworkToken","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"stateMutability":"payable","type":"receive"}]Contract Creation Code
60e06040523480156200001157600080fd5b5060405162001e9c38038062001e9c83398101604081905262000034916200034a565b868686868686620000453362000181565b6001600160a01b03821660a0526200005d81620001d1565b6001600160a01b03838116608052600280546001600160a01b031916918616918217905560405163dc54e91360e01b815263dc54e91390620000a890309089908b90600401620003e0565b600060405180830381600087803b158015620000c357600080fd5b505af1158015620000d8573d6000803e3d6000fd5b5050505062000160600260009054906101000a90046001600160a01b03166001600160a01b0316638da5cb5b6040518163ffffffff1660e01b8152600401602060405180830381865afa15801562000134573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200015a919062000420565b62000274565b5050506001600160a01b0390931660c0525062000447975050505050505050565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6000546001600160a01b03163314620002205760405162461bcd60e51b8152602060048201819052602482015260008051602062001e7c83398151915260448201526064015b60405180910390fd5b6006811015801562000233575060648111155b6200026f5760405162461bcd60e51b815260206004820152600b60248201526a496e76616c69642046656560a81b604482015260640162000217565b600155565b6000546001600160a01b03163314620002bf5760405162461bcd60e51b8152602060048201819052602482015260008051602062001e7c833981519152604482015260640162000217565b6001600160a01b038116620003265760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b606482015260840162000217565b620003318162000181565b50565b6001600160a01b03811681146200033157600080fd5b600080600080600080600060e0888a0312156200036657600080fd5b875196506020880151600281106200037d57600080fd5b6040890151909650620003908162000334565b6060890151909550620003a38162000334565b6080890151909450620003b68162000334565b60a089015160c08a01519194509250620003d08162000334565b8091505092959891949750929550565b6001600160a01b038416815260608101600284106200040f57634e487b7160e01b600052602160045260246000fd5b602082019390935260400152919050565b6000602082840312156200043357600080fd5b8151620004408162000334565b9392505050565b60805160a05160c0516119d4620004a86000396000818161017d015281816110ec015261116101526000818161010c01528181610c4501528181610c8001528181610cfc0152610d7601526000818161028a0152610e1401526119d46000f3fe6080604052600436106100e15760003560e01c80638456cb591161007f578063d2f7265a11610059578063d2f7265a14610278578063ddca3f43146102ac578063e6baeb7a146102d0578063f2fde38b146102e357600080fd5b80638456cb59146102255780638da5cb5b1461023a578063a4520aee1461025857600080fd5b80635c975abb116100bb5780635c975abb1461019f57806369fe0e2d146101d0578063715018a6146101f05780637b1039991461020557600080fd5b8063041bf7bc146100fa5780631a5da6c81461014b578063411557d11461016b57600080fd5b366100f557333214156100f357600080fd5b005b600080fd5b34801561010657600080fd5b5061012e7f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b34801561015757600080fd5b506100f3610166366004611411565b610303565b34801561017757600080fd5b5061012e7f000000000000000000000000000000000000000000000000000000000000000081565b3480156101ab57600080fd5b506000546101c090600160a01b900460ff1681565b6040519015158152602001610142565b3480156101dc57600080fd5b506100f36101eb36600461142e565b610391565b3480156101fc57600080fd5b506100f361044e565b34801561021157600080fd5b5060025461012e906001600160a01b031681565b34801561023157600080fd5b506100f36104b4565b34801561024657600080fd5b506000546001600160a01b031661012e565b34801561026457600080fd5b506100f3610273366004611447565b61054a565b34801561028457600080fd5b5061012e7f000000000000000000000000000000000000000000000000000000000000000081565b3480156102b857600080fd5b506102c260015481565b604051908152602001610142565b6102c26102de366004611515565b610719565b3480156102ef57600080fd5b506100f36102fe366004611411565b6108bc565b6000546001600160a01b031633146103625760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064015b60405180910390fd5b6002805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0392909216919091179055565b6000546001600160a01b031633146103eb5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b600681101580156103fd575060648111155b6104495760405162461bcd60e51b815260206004820152600b60248201527f496e76616c6964204665650000000000000000000000000000000000000000006044820152606401610359565b600155565b6000546001600160a01b031633146104a85760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b6104b2600061099e565b565b6000546001600160a01b0316331461050e5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b600080547fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff8116600160a01b9182900460ff1615909102179055565b600254604080517f913e77ad00000000000000000000000000000000000000000000000000000000815290516000926001600160a01b03169163913e77ad9160048083019260209291908290030181865afa1580156105ad573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105d191906115fc565b905060005b82811015610713576000808585848181106105f3576105f3611619565b90506020020160208101906106089190611411565b6001600160a01b0316141561063157504761062c6001600160a01b038416826109fb565b610700565b84848381811061064357610643611619565b90506020020160208101906106589190611411565b6040516370a0823160e01b81523060048201526001600160a01b0391909116906370a0823190602401602060405180830381865afa15801561069e573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106c2919061162f565b905061070083828787868181106106db576106db611619565b90506020020160208101906106f09190611411565b6001600160a01b03169190610a5b565b508061070b8161165e565b9150506105d6565b50505050565b60008054600160a01b900460ff16156107745760405162461bcd60e51b815260206004820152600660248201527f50617573656400000000000000000000000000000000000000000000000000006044820152606401610359565b60006107808d8d610afa565b905061078e81600154610be4565b90506107d38d828d8b8b8b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610c0e92505050565b90506107e28b828c8787611019565b915088821015610828576040517fc634b00600000000000000000000000000000000000000000000000000000000815260048101839052602481018a9052604401610359565b846001600160a01b0316336001600160a01b03167fc4d7bc58a132fd4a1b9d658b0a30809bcfb6b4959c1d3d4eb2e300d3a15099be8f8f8e876001546040516108a49594939291906001600160a01b03958616815260208101949094529190931660408301526060820192909252608081019190915260a00190565b60405180910390a3509b9a5050505050505050505050565b6000546001600160a01b031633146109165760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b6001600160a01b0381166109925760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201527f64647265737300000000000000000000000000000000000000000000000000006064820152608401610359565b61099b8161099e565b50565b600080546001600160a01b0383811673ffffffffffffffffffffffffffffffffffffffff19831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b600080600080600085875af1905080610a565760405162461bcd60e51b815260206004820152601360248201527f4554485f5452414e534645525f4641494c4544000000000000000000000000006044820152606401610359565b505050565b60006040517fa9059cbb000000000000000000000000000000000000000000000000000000008152836004820152826024820152602060006044836000895af13d15601f3d11600160005114161716915050806107135760405162461bcd60e51b815260206004820152600f60248201527f5452414e534645525f4641494c454400000000000000000000000000000000006044820152606401610359565b60006001600160a01b038316610b6c57600034118015610b1957508134145b610b655760405162461bcd60e51b815260206004820152601d60248201527f496e76616c6964207175616e74697479206f72206d73672e76616c75650000006044820152606401610359565b5034610bde565b600082118015610b7a575034155b610bc65760405162461bcd60e51b815260206004820152601d60248201527f496e76616c6964207175616e74697479206f72206d73672e76616c75650000006044820152606401610359565b610bdb6001600160a01b0384163330856111f5565b50805b92915050565b6000612710610bf38385611679565b610bfd9190611698565b610c0790846116ba565b9392505050565b6000836001600160a01b0316866001600160a01b03161415610c31575083611010565b6001600160a01b038616158015610c7957507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316846001600160a01b0316145b15610cfa577f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d0e30db0866040518263ffffffff1660e01b81526004016000604051808303818588803b158015610cd957600080fd5b505af1158015610ced573d6000803e3d6000fd5b5050505050849050611010565b7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316866001600160a01b0316148015610d4257506001600160a01b038416155b15610de2576040517f2e1a7d4d000000000000000000000000000000000000000000000000000000008152600481018690527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031690632e1a7d4d90602401600060405180830381600087803b158015610dc257600080fd5b505af1158015610dd6573d6000803e3d6000fd5b50505050849050611010565b60006001600160a01b038716610df9575084610e04565b610e048785886112a1565b6000610e1030876112cb565b90507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316856001600160a01b03161480610ed457506002546040517f13eb46710000000000000000000000000000000000000000000000000000000081526001600160a01b038781166004830152909116906313eb467190602401602060405180830381865afa158015610eb0573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ed491906116d1565b610f205760405162461bcd60e51b815260206004820152601360248201527f556e617574686f72697a656420746172676574000000000000000000000000006044820152606401610359565b600080866001600160a01b03168487604051610f3c919061171f565b60006040518083038185875af1925050503d8060008114610f79576040519150601f19603f3d011682016040523d82523d6000602084013e610f7e565b606091505b5091509150818190610fa35760405162461bcd60e51b81526004016103599190611767565b5082610faf308a6112cb565b610fb991906116ba565b94506000851161100b5760405162461bcd60e51b815260206004820152601160248201527f496e76616c696420657865637574696f6e0000000000000000000000000000006044820152606401610359565b505050505b95945050505050565b600080808061102a85870187611790565b9250925092506000825167ffffffffffffffff81111561104c5761104c61177a565b604051908082528060200260200182016040528015611075578160200160208202803683370190505b5090508881838151811061108b5761108b611619565b602002602001018181525050600060018260006040516020016110b0939291906118a4565b604051602081830303815290604052905060006110cd338b6112cb565b905060006001600160a01b038d166110e657508a611111565b6111118d7f00000000000000000000000000000000000000000000000000000000000000008e6112a1565b60408051608081018252878152602081018690528082018590526000606082015290517fb95cac280000000000000000000000000000000000000000000000000000000081526001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169163b95cac2891849161119d918c9130913391906004016118d3565b6000604051808303818588803b1580156111b657600080fd5b505af11580156111ca573d6000803e3d6000fd5b5050505050816111da338d6112cb565b6111e491906116ba565b9d9c50505050505050505050505050565b60006040517f23b872dd0000000000000000000000000000000000000000000000000000000081528460048201528360248201528260448201526020600060648360008a5af13d15601f3d116001600051141617169150508061129a5760405162461bcd60e51b815260206004820152601460248201527f5452414e534645525f46524f4d5f4641494c45440000000000000000000000006044820152606401610359565b5050505050565b826112b76001600160a01b03821684600061135d565b6107136001600160a01b038216848461135d565b60006001600160a01b0382166112ec57506001600160a01b03821631610bde565b6040516370a0823160e01b81526001600160a01b0384811660048301528316906370a0823190602401602060405180830381865afa158015611332573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611356919061162f565b9050610bde565b60006040517f095ea7b3000000000000000000000000000000000000000000000000000000008152836004820152826024820152602060006044836000895af13d15601f3d11600160005114161716915050806107135760405162461bcd60e51b815260206004820152600e60248201527f415050524f56455f4641494c45440000000000000000000000000000000000006044820152606401610359565b6001600160a01b038116811461099b57600080fd5b60006020828403121561142357600080fd5b8135610c07816113fc565b60006020828403121561144057600080fd5b5035919050565b6000806020838503121561145a57600080fd5b823567ffffffffffffffff8082111561147257600080fd5b818501915085601f83011261148657600080fd5b81358181111561149557600080fd5b8660208260051b85010111156114aa57600080fd5b60209290920196919550909350505050565b80356114c7816113fc565b919050565b60008083601f8401126114de57600080fd5b50813567ffffffffffffffff8111156114f657600080fd5b60208301915083602082850101111561150e57600080fd5b9250929050565b60008060008060008060008060008060006101208c8e03121561153757600080fd5b6115418c356113fc565b8b359a5060208c0135995061155960408d01356113fc565b60408c0135985061156c60608d016114bc565b975060808c0135965061158160a08d016114bc565b955067ffffffffffffffff8060c08e0135111561159d57600080fd5b6115ad8e60c08f01358f016114cc565b90965094506115be60e08e016114bc565b9350806101008e013511156115d257600080fd5b506115e48d6101008e01358e016114cc565b81935080925050509295989b509295989b9093969950565b60006020828403121561160e57600080fd5b8151610c07816113fc565b634e487b7160e01b600052603260045260246000fd5b60006020828403121561164157600080fd5b5051919050565b634e487b7160e01b600052601160045260246000fd5b600060001982141561167257611672611648565b5060010190565b600081600019048311821515161561169357611693611648565b500290565b6000826116b557634e487b7160e01b600052601260045260246000fd5b500490565b6000828210156116cc576116cc611648565b500390565b6000602082840312156116e357600080fd5b81518015158114610c0757600080fd5b60005b8381101561170e5781810151838201526020016116f6565b838111156107135750506000910152565b600082516117318184602087016116f3565b9190910192915050565b600081518084526117538160208601602086016116f3565b601f01601f19169290920160200192915050565b602081526000610c07602083018461173b565b634e487b7160e01b600052604160045260246000fd5b6000806000606084860312156117a557600080fd5b8335925060208085013567ffffffffffffffff808211156117c557600080fd5b818701915087601f8301126117d957600080fd5b8135818111156117eb576117eb61177a565b8060051b604051601f19603f830116810181811085821117156118105761181061177a565b60405291825284820192508381018501918a83111561182e57600080fd5b938501935b8285101561185357611844856114bc565b84529385019392850192611833565b979a979950505050604095909501359450505050565b600081518084526020808501945080840160005b838110156118995781518752958201959082019060010161187d565b509495945050505050565b60ff841681526060602082015260006118c06060830185611869565b905060ff83166040830152949350505050565b848152600060206001600160a01b038087168285015280861660408501526080606085015261010084018551608080870152818151808452610120880191508583019350600092505b8083101561193e5783518516825292850192600192909201919085019061191c565b50848801519450607f199350838782030160a088015261195e8186611869565b94505050506040850151818584030160c086015261197c838261173b565b92505050606084015161199360e085018215159052565b50969550505050505056fea2646970667358221220ae183b17a93735ef26822900c558bf5c54f35e017927d857a5453e23bdcc4c1864736f6c634300080b00334f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657262616c616e6365727632000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ea49d02c248b357b99670d9e9741f54f72df9cb3000000000000000000000000def1c0ded9bec7f1a1670819833240f027b25eff000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000000000000000000000000000000000000000001e000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c8
Deployed Bytecode
0x6080604052600436106100e15760003560e01c80638456cb591161007f578063d2f7265a11610059578063d2f7265a14610278578063ddca3f43146102ac578063e6baeb7a146102d0578063f2fde38b146102e357600080fd5b80638456cb59146102255780638da5cb5b1461023a578063a4520aee1461025857600080fd5b80635c975abb116100bb5780635c975abb1461019f57806369fe0e2d146101d0578063715018a6146101f05780637b1039991461020557600080fd5b8063041bf7bc146100fa5780631a5da6c81461014b578063411557d11461016b57600080fd5b366100f557333214156100f357600080fd5b005b600080fd5b34801561010657600080fd5b5061012e7f000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc281565b6040516001600160a01b0390911681526020015b60405180910390f35b34801561015757600080fd5b506100f3610166366004611411565b610303565b34801561017757600080fd5b5061012e7f000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c881565b3480156101ab57600080fd5b506000546101c090600160a01b900460ff1681565b6040519015158152602001610142565b3480156101dc57600080fd5b506100f36101eb36600461142e565b610391565b3480156101fc57600080fd5b506100f361044e565b34801561021157600080fd5b5060025461012e906001600160a01b031681565b34801561023157600080fd5b506100f36104b4565b34801561024657600080fd5b506000546001600160a01b031661012e565b34801561026457600080fd5b506100f3610273366004611447565b61054a565b34801561028457600080fd5b5061012e7f000000000000000000000000def1c0ded9bec7f1a1670819833240f027b25eff81565b3480156102b857600080fd5b506102c260015481565b604051908152602001610142565b6102c26102de366004611515565b610719565b3480156102ef57600080fd5b506100f36102fe366004611411565b6108bc565b6000546001600160a01b031633146103625760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e657260448201526064015b60405180910390fd5b6002805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0392909216919091179055565b6000546001600160a01b031633146103eb5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b600681101580156103fd575060648111155b6104495760405162461bcd60e51b815260206004820152600b60248201527f496e76616c6964204665650000000000000000000000000000000000000000006044820152606401610359565b600155565b6000546001600160a01b031633146104a85760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b6104b2600061099e565b565b6000546001600160a01b0316331461050e5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b600080547fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff8116600160a01b9182900460ff1615909102179055565b600254604080517f913e77ad00000000000000000000000000000000000000000000000000000000815290516000926001600160a01b03169163913e77ad9160048083019260209291908290030181865afa1580156105ad573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105d191906115fc565b905060005b82811015610713576000808585848181106105f3576105f3611619565b90506020020160208101906106089190611411565b6001600160a01b0316141561063157504761062c6001600160a01b038416826109fb565b610700565b84848381811061064357610643611619565b90506020020160208101906106589190611411565b6040516370a0823160e01b81523060048201526001600160a01b0391909116906370a0823190602401602060405180830381865afa15801561069e573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106c2919061162f565b905061070083828787868181106106db576106db611619565b90506020020160208101906106f09190611411565b6001600160a01b03169190610a5b565b508061070b8161165e565b9150506105d6565b50505050565b60008054600160a01b900460ff16156107745760405162461bcd60e51b815260206004820152600660248201527f50617573656400000000000000000000000000000000000000000000000000006044820152606401610359565b60006107808d8d610afa565b905061078e81600154610be4565b90506107d38d828d8b8b8b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610c0e92505050565b90506107e28b828c8787611019565b915088821015610828576040517fc634b00600000000000000000000000000000000000000000000000000000000815260048101839052602481018a9052604401610359565b846001600160a01b0316336001600160a01b03167fc4d7bc58a132fd4a1b9d658b0a30809bcfb6b4959c1d3d4eb2e300d3a15099be8f8f8e876001546040516108a49594939291906001600160a01b03958616815260208101949094529190931660408301526060820192909252608081019190915260a00190565b60405180910390a3509b9a5050505050505050505050565b6000546001600160a01b031633146109165760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610359565b6001600160a01b0381166109925760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201527f64647265737300000000000000000000000000000000000000000000000000006064820152608401610359565b61099b8161099e565b50565b600080546001600160a01b0383811673ffffffffffffffffffffffffffffffffffffffff19831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b600080600080600085875af1905080610a565760405162461bcd60e51b815260206004820152601360248201527f4554485f5452414e534645525f4641494c4544000000000000000000000000006044820152606401610359565b505050565b60006040517fa9059cbb000000000000000000000000000000000000000000000000000000008152836004820152826024820152602060006044836000895af13d15601f3d11600160005114161716915050806107135760405162461bcd60e51b815260206004820152600f60248201527f5452414e534645525f4641494c454400000000000000000000000000000000006044820152606401610359565b60006001600160a01b038316610b6c57600034118015610b1957508134145b610b655760405162461bcd60e51b815260206004820152601d60248201527f496e76616c6964207175616e74697479206f72206d73672e76616c75650000006044820152606401610359565b5034610bde565b600082118015610b7a575034155b610bc65760405162461bcd60e51b815260206004820152601d60248201527f496e76616c6964207175616e74697479206f72206d73672e76616c75650000006044820152606401610359565b610bdb6001600160a01b0384163330856111f5565b50805b92915050565b6000612710610bf38385611679565b610bfd9190611698565b610c0790846116ba565b9392505050565b6000836001600160a01b0316866001600160a01b03161415610c31575083611010565b6001600160a01b038616158015610c7957507f000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc26001600160a01b0316846001600160a01b0316145b15610cfa577f000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc26001600160a01b031663d0e30db0866040518263ffffffff1660e01b81526004016000604051808303818588803b158015610cd957600080fd5b505af1158015610ced573d6000803e3d6000fd5b5050505050849050611010565b7f000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc26001600160a01b0316866001600160a01b0316148015610d4257506001600160a01b038416155b15610de2576040517f2e1a7d4d000000000000000000000000000000000000000000000000000000008152600481018690527f000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc26001600160a01b031690632e1a7d4d90602401600060405180830381600087803b158015610dc257600080fd5b505af1158015610dd6573d6000803e3d6000fd5b50505050849050611010565b60006001600160a01b038716610df9575084610e04565b610e048785886112a1565b6000610e1030876112cb565b90507f000000000000000000000000def1c0ded9bec7f1a1670819833240f027b25eff6001600160a01b0316856001600160a01b03161480610ed457506002546040517f13eb46710000000000000000000000000000000000000000000000000000000081526001600160a01b038781166004830152909116906313eb467190602401602060405180830381865afa158015610eb0573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ed491906116d1565b610f205760405162461bcd60e51b815260206004820152601360248201527f556e617574686f72697a656420746172676574000000000000000000000000006044820152606401610359565b600080866001600160a01b03168487604051610f3c919061171f565b60006040518083038185875af1925050503d8060008114610f79576040519150601f19603f3d011682016040523d82523d6000602084013e610f7e565b606091505b5091509150818190610fa35760405162461bcd60e51b81526004016103599190611767565b5082610faf308a6112cb565b610fb991906116ba565b94506000851161100b5760405162461bcd60e51b815260206004820152601160248201527f496e76616c696420657865637574696f6e0000000000000000000000000000006044820152606401610359565b505050505b95945050505050565b600080808061102a85870187611790565b9250925092506000825167ffffffffffffffff81111561104c5761104c61177a565b604051908082528060200260200182016040528015611075578160200160208202803683370190505b5090508881838151811061108b5761108b611619565b602002602001018181525050600060018260006040516020016110b0939291906118a4565b604051602081830303815290604052905060006110cd338b6112cb565b905060006001600160a01b038d166110e657508a611111565b6111118d7f000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c88e6112a1565b60408051608081018252878152602081018690528082018590526000606082015290517fb95cac280000000000000000000000000000000000000000000000000000000081526001600160a01b037f000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c8169163b95cac2891849161119d918c9130913391906004016118d3565b6000604051808303818588803b1580156111b657600080fd5b505af11580156111ca573d6000803e3d6000fd5b5050505050816111da338d6112cb565b6111e491906116ba565b9d9c50505050505050505050505050565b60006040517f23b872dd0000000000000000000000000000000000000000000000000000000081528460048201528360248201528260448201526020600060648360008a5af13d15601f3d116001600051141617169150508061129a5760405162461bcd60e51b815260206004820152601460248201527f5452414e534645525f46524f4d5f4641494c45440000000000000000000000006044820152606401610359565b5050505050565b826112b76001600160a01b03821684600061135d565b6107136001600160a01b038216848461135d565b60006001600160a01b0382166112ec57506001600160a01b03821631610bde565b6040516370a0823160e01b81526001600160a01b0384811660048301528316906370a0823190602401602060405180830381865afa158015611332573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611356919061162f565b9050610bde565b60006040517f095ea7b3000000000000000000000000000000000000000000000000000000008152836004820152826024820152602060006044836000895af13d15601f3d11600160005114161716915050806107135760405162461bcd60e51b815260206004820152600e60248201527f415050524f56455f4641494c45440000000000000000000000000000000000006044820152606401610359565b6001600160a01b038116811461099b57600080fd5b60006020828403121561142357600080fd5b8135610c07816113fc565b60006020828403121561144057600080fd5b5035919050565b6000806020838503121561145a57600080fd5b823567ffffffffffffffff8082111561147257600080fd5b818501915085601f83011261148657600080fd5b81358181111561149557600080fd5b8660208260051b85010111156114aa57600080fd5b60209290920196919550909350505050565b80356114c7816113fc565b919050565b60008083601f8401126114de57600080fd5b50813567ffffffffffffffff8111156114f657600080fd5b60208301915083602082850101111561150e57600080fd5b9250929050565b60008060008060008060008060008060006101208c8e03121561153757600080fd5b6115418c356113fc565b8b359a5060208c0135995061155960408d01356113fc565b60408c0135985061156c60608d016114bc565b975060808c0135965061158160a08d016114bc565b955067ffffffffffffffff8060c08e0135111561159d57600080fd5b6115ad8e60c08f01358f016114cc565b90965094506115be60e08e016114bc565b9350806101008e013511156115d257600080fd5b506115e48d6101008e01358e016114cc565b81935080925050509295989b509295989b9093969950565b60006020828403121561160e57600080fd5b8151610c07816113fc565b634e487b7160e01b600052603260045260246000fd5b60006020828403121561164157600080fd5b5051919050565b634e487b7160e01b600052601160045260246000fd5b600060001982141561167257611672611648565b5060010190565b600081600019048311821515161561169357611693611648565b500290565b6000826116b557634e487b7160e01b600052601260045260246000fd5b500490565b6000828210156116cc576116cc611648565b500390565b6000602082840312156116e357600080fd5b81518015158114610c0757600080fd5b60005b8381101561170e5781810151838201526020016116f6565b838111156107135750506000910152565b600082516117318184602087016116f3565b9190910192915050565b600081518084526117538160208601602086016116f3565b601f01601f19169290920160200192915050565b602081526000610c07602083018461173b565b634e487b7160e01b600052604160045260246000fd5b6000806000606084860312156117a557600080fd5b8335925060208085013567ffffffffffffffff808211156117c557600080fd5b818701915087601f8301126117d957600080fd5b8135818111156117eb576117eb61177a565b8060051b604051601f19603f830116810181811085821117156118105761181061177a565b60405291825284820192508381018501918a83111561182e57600080fd5b938501935b8285101561185357611844856114bc565b84529385019392850192611833565b979a979950505050604095909501359450505050565b600081518084526020808501945080840160005b838110156118995781518752958201959082019060010161187d565b509495945050505050565b60ff841681526060602082015260006118c06060830185611869565b905060ff83166040830152949350505050565b848152600060206001600160a01b038087168285015280861660408501526080606085015261010084018551608080870152818151808452610120880191508583019350600092505b8083101561193e5783518516825292850192600192909201919085019061191c565b50848801519450607f199350838782030160a088015261195e8186611869565b94505050506040850151818584030160c086015261197c838261173b565b92505050606084015161199360e085018215159052565b50969550505050505056fea2646970667358221220ae183b17a93735ef26822900c558bf5c54f35e017927d857a5453e23bdcc4c1864736f6c634300080b0033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
62616c616e6365727632000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ea49d02c248b357b99670d9e9741f54f72df9cb3000000000000000000000000def1c0ded9bec7f1a1670819833240f027b25eff000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000000000000000000000000000000000000000001e000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c8
-----Decoded View---------------
Arg [0] : protocolId (bytes32): 0x62616c616e636572763200000000000000000000000000000000000000000000
Arg [1] : portalType (uint8): 0
Arg [2] : registry (address): 0xEa49D02c248b357B99670d9E9741F54f72dF9Cb3
Arg [3] : exchange (address): 0xDef1C0ded9bec7F1a1670819833240f027b25EfF
Arg [4] : wrappedNetworkToken (address): 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2
Arg [5] : fee (uint256): 30
Arg [6] : _vault (address): 0xBA12222222228d8Ba445958a75a0704d566BF2C8
-----Encoded View---------------
7 Constructor Arguments found :
Arg [0] : 62616c616e636572763200000000000000000000000000000000000000000000
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000000
Arg [2] : 000000000000000000000000ea49d02c248b357b99670d9e9741f54f72df9cb3
Arg [3] : 000000000000000000000000def1c0ded9bec7f1a1670819833240f027b25eff
Arg [4] : 000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2
Arg [5] : 000000000000000000000000000000000000000000000000000000000000001e
Arg [6] : 000000000000000000000000ba12222222228d8ba445958a75a0704d566bf2c8
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
[ 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.