Address Details
contract
0xF35ed7156BABF2541E032B3bB8625210316e2832
- Contract Name
- SwappaRouterV1
- Creator
- 0x9fd2f6–5b26dc at 0x6ef38f–740e23
- Balance
- 0 CELO ( )
- Locked CELO Balance
- 0.00 CELO
- Voting CELO Balance
- 0.00 CELO
- Pending Unlocked Gold
- 0.00 CELO
- Tokens
-
Fetching tokens...
- Transactions
- 1,667,656 Transactions
- Transfers
- 2,326,970 Transfers
- Gas Used
- 769,689,115,772
- Last Balance Update
- 25295525
Transactions
Token Transfers
Tokens
Internal Transactions
Coin Balance History
Logs
Code
Read Contract
Write Contract
This contract has been partially verified via Sourcify.
View contract in Sourcify repository
- Contract name:
- SwappaRouterV1
- Optimization enabled
- true
- Compiler version
- v0.6.8+commit.0bbfe453
- Optimization runs
- 10000
- EVM Version
- istanbul
- Verified at
- 2021-12-16T16:47:21.577079Z
project:/contracts/swappa/SwappaRouterV1.sol
// SPDX-License-Identifier: MIT pragma solidity 0.6.8; pragma experimental ABIEncoderV2; import "@openzeppelin/contracts/token/ERC20/ERC20.sol"; import "./ISwappaPairV1.sol"; contract SwappaRouterV1 { event Swap( address indexed sender, address to, address indexed input, address indexed output, uint256 inputAmount, uint256 outputAmount ); modifier ensure(uint deadline) { require(deadline >= block.timestamp, 'SwappaRouter: Expired!'); _; } function getOutputAmount( address[] calldata path, address[] calldata pairs, bytes[] calldata extras, uint256 inputAmount ) external view returns (uint256 outputAmount) { outputAmount = inputAmount; for (uint i; i < pairs.length; i++) { outputAmount = ISwappaPairV1(pairs[i]).getOutputAmount(path[i], path[i+1], outputAmount, extras[i]); } } function swapExactInputForOutput( address[] calldata path, address[] calldata pairs, bytes[] calldata extras, uint256 inputAmount, uint256 minOutputAmount, address to, uint deadline ) external ensure(deadline) returns (uint256 outputAmount) { require(path.length == pairs.length + 1 , "SwappaRouter: Path and Pairs mismatch!"); require(pairs.length == extras.length, "SwappaRouter: Pairs and Extras mismatch!"); require(pairs.length > 0, "SwappaRouter: Must have at least one pair!"); require( ERC20(path[0]).transferFrom(msg.sender, pairs[0], inputAmount), "SwappaRouter: Initial transferFrom failed!"); for (uint i; i < pairs.length; i++) { (address pairInput, address pairOutput) = (path[i], path[i + 1]); address next = i < pairs.length - 1 ? pairs[i+1] : address(this); bytes memory data = extras[i]; ISwappaPairV1(pairs[i]).swap(pairInput, pairOutput, next, data); } // Perform final output check in the router as a final safeguard to make sure // minOutputAmount restriction is honored no matter what. address output = path[path.length - 1]; outputAmount = ERC20(output).balanceOf(address(this)); require( outputAmount >= minOutputAmount, "SwappaRouter: Insufficient output amount!"); require( ERC20(output).transfer(to, outputAmount), "SwappaRouter: Final transfer failed!"); emit Swap(msg.sender, to, path[0], output, inputAmount, outputAmount); } function swapExactInputForOutputWithPrecheck( address[] calldata path, address[] calldata pairs, bytes[] calldata extras, uint256 inputAmount, uint256 minOutputAmount, address to, uint deadline ) external ensure(deadline) returns (uint256 outputAmount) { require(path.length == pairs.length + 1 , "SwappaRouter: Path and Pairs mismatch!"); require(pairs.length == extras.length, "SwappaRouter: Pairs and Extras mismatch!"); require(pairs.length > 0, "SwappaRouter: Must have at least one pair!"); // Note(zviadm): Full code copying is necessary because `bytes[]` arrays can not easily be // passed around between `calldata` and `memory` locations. Manual copying would be necessary // with quite a bit of annoying code to work around stack issues. { outputAmount = inputAmount; // reuse outputAmount variable to avoid "stack too deep" errors. for (uint i; i < pairs.length; i++) { (address input, address output) = (path[i], path[i+1]); bytes memory data = extras[i]; outputAmount = ISwappaPairV1(pairs[i]).getOutputAmount(input, output, outputAmount, data); } require( outputAmount >= minOutputAmount, "SwappaRouter: Insufficient expected output amount!"); } require( ERC20(path[0]).transferFrom(msg.sender, pairs[0], inputAmount), "SwappaRouter: Initial transferFrom failed!"); for (uint i; i < pairs.length; i++) { (address pairInput, address pairOutput) = (path[i], path[i + 1]); address next = i < pairs.length - 1 ? pairs[i+1] : address(this); bytes memory data = extras[i]; ISwappaPairV1(pairs[i]).swap(pairInput, pairOutput, next, data); } // Perform final output check in the router as a final safeguard to make sure // minOutputAmount restriction is honored no matter what. address output = path[path.length - 1]; outputAmount = ERC20(output).balanceOf(address(this)); require( outputAmount >= minOutputAmount, "SwappaRouter: Insufficient output amount!"); require( ERC20(output).transfer(to, outputAmount), "SwappaRouter: Final transfer failed!"); emit Swap(msg.sender, to, path[0], output, inputAmount, outputAmount); } receive() external payable {} }
/_openzeppelin/contracts/GSN/Context.sol
// SPDX-License-Identifier: MIT pragma solidity ^0.6.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 GSN 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 payable) { return msg.sender; } function _msgData() internal view virtual returns (bytes memory) { this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691 return msg.data; } }
/_openzeppelin/contracts/math/SafeMath.sol
// SPDX-License-Identifier: MIT pragma solidity ^0.6.0; /** * @dev Wrappers over Solidity's arithmetic operations with added overflow * checks. * * Arithmetic operations in Solidity wrap on overflow. This can easily result * in bugs, because programmers usually assume that an overflow raises an * error, which is the standard behavior in high level programming languages. * `SafeMath` restores this intuition by reverting the transaction when an * operation overflows. * * Using this library instead of the unchecked operations eliminates an entire * class of bugs, so it's recommended to use it always. */ library SafeMath { /** * @dev Returns the addition of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `+` operator. * * Requirements: * * - Addition cannot overflow. */ function add(uint256 a, uint256 b) internal pure returns (uint256) { uint256 c = a + b; require(c >= a, "SafeMath: addition overflow"); return c; } /** * @dev Returns the subtraction of two unsigned integers, reverting on * overflow (when the result is negative). * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b) internal pure returns (uint256) { return sub(a, b, "SafeMath: subtraction overflow"); } /** * @dev Returns the subtraction of two unsigned integers, reverting with custom message on * overflow (when the result is negative). * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b <= a, errorMessage); uint256 c = a - b; return c; } /** * @dev Returns the multiplication of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `*` operator. * * Requirements: * * - Multiplication cannot overflow. */ function mul(uint256 a, uint256 b) internal pure returns (uint256) { // Gas optimization: this is cheaper than requiring 'a' not being zero, but the // benefit is lost if 'b' is also tested. // See: https://github.com/OpenZeppelin/openzeppelin-contracts/pull/522 if (a == 0) { return 0; } uint256 c = a * b; require(c / a == b, "SafeMath: multiplication overflow"); return c; } /** * @dev Returns the integer division of two unsigned integers. Reverts on * division by zero. The result is rounded towards zero. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b) internal pure returns (uint256) { return div(a, b, "SafeMath: division by zero"); } /** * @dev Returns the integer division of two unsigned integers. Reverts with custom message on * division by zero. The result is rounded towards zero. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b > 0, errorMessage); uint256 c = a / b; // assert(a == b * c + a % b); // There is no case in which this doesn't hold return c; } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * Reverts when dividing by zero. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b) internal pure returns (uint256) { return mod(a, b, "SafeMath: modulo by zero"); } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * Reverts with custom message when dividing by zero. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b != 0, errorMessage); return a % b; } }
/_openzeppelin/contracts/token/ERC20/ERC20.sol
// SPDX-License-Identifier: MIT pragma solidity ^0.6.0; import "../../GSN/Context.sol"; import "./IERC20.sol"; import "../../math/SafeMath.sol"; import "../../utils/Address.sol"; /** * @dev Implementation of the {IERC20} interface. * * This implementation is agnostic to the way tokens are created. This means * that a supply mechanism has to be added in a derived contract using {_mint}. * For a generic mechanism see {ERC20PresetMinterPauser}. * * TIP: For a detailed writeup see our guide * https://forum.zeppelin.solutions/t/how-to-implement-erc20-supply-mechanisms/226[How * to implement supply mechanisms]. * * We have followed general OpenZeppelin guidelines: functions revert instead * of returning `false` on failure. This behavior is nonetheless conventional * and does not conflict with the expectations of ERC20 applications. * * Additionally, an {Approval} event is emitted on calls to {transferFrom}. * This allows applications to reconstruct the allowance for all accounts just * by listening to said events. Other implementations of the EIP may not emit * these events, as it isn't required by the specification. * * Finally, the non-standard {decreaseAllowance} and {increaseAllowance} * functions have been added to mitigate the well-known issues around setting * allowances. See {IERC20-approve}. */ contract ERC20 is Context, IERC20 { using SafeMath for uint256; using Address for address; mapping (address => uint256) private _balances; mapping (address => mapping (address => uint256)) private _allowances; uint256 private _totalSupply; string private _name; string private _symbol; uint8 private _decimals; /** * @dev Sets the values for {name} and {symbol}, initializes {decimals} with * a default value of 18. * * To select a different value for {decimals}, use {_setupDecimals}. * * All three of these values are immutable: they can only be set once during * construction. */ constructor (string memory name, string memory symbol) public { _name = name; _symbol = symbol; _decimals = 18; } /** * @dev Returns the name of the token. */ function name() public view returns (string memory) { return _name; } /** * @dev Returns the symbol of the token, usually a shorter version of the * name. */ function symbol() public view returns (string memory) { return _symbol; } /** * @dev Returns the number of decimals used to get its user representation. * For example, if `decimals` equals `2`, a balance of `505` tokens should * be displayed to a user as `5,05` (`505 / 10 ** 2`). * * Tokens usually opt for a value of 18, imitating the relationship between * Ether and Wei. This is the value {ERC20} uses, unless {_setupDecimals} is * called. * * NOTE: This information is only used for _display_ purposes: it in * no way affects any of the arithmetic of the contract, including * {IERC20-balanceOf} and {IERC20-transfer}. */ function decimals() public view returns (uint8) { return _decimals; } /** * @dev See {IERC20-totalSupply}. */ function totalSupply() public view override returns (uint256) { return _totalSupply; } /** * @dev See {IERC20-balanceOf}. */ function balanceOf(address account) public view override returns (uint256) { return _balances[account]; } /** * @dev See {IERC20-transfer}. * * Requirements: * * - `recipient` cannot be the zero address. * - the caller must have a balance of at least `amount`. */ function transfer(address recipient, uint256 amount) public virtual override returns (bool) { _transfer(_msgSender(), recipient, amount); return true; } /** * @dev See {IERC20-allowance}. */ function allowance(address owner, address spender) public view virtual override returns (uint256) { return _allowances[owner][spender]; } /** * @dev See {IERC20-approve}. * * Requirements: * * - `spender` cannot be the zero address. */ function approve(address spender, uint256 amount) public virtual override returns (bool) { _approve(_msgSender(), spender, amount); return true; } /** * @dev See {IERC20-transferFrom}. * * Emits an {Approval} event indicating the updated allowance. This is not * required by the EIP. See the note at the beginning of {ERC20}; * * Requirements: * - `sender` and `recipient` cannot be the zero address. * - `sender` must have a balance of at least `amount`. * - the caller must have allowance for ``sender``'s tokens of at least * `amount`. */ function transferFrom(address sender, address recipient, uint256 amount) public virtual override returns (bool) { _transfer(sender, recipient, amount); _approve(sender, _msgSender(), _allowances[sender][_msgSender()].sub(amount, "ERC20: transfer amount exceeds allowance")); return true; } /** * @dev Atomically increases the allowance granted to `spender` by the caller. * * This is an alternative to {approve} that can be used as a mitigation for * problems described in {IERC20-approve}. * * Emits an {Approval} event indicating the updated allowance. * * Requirements: * * - `spender` cannot be the zero address. */ function increaseAllowance(address spender, uint256 addedValue) public virtual returns (bool) { _approve(_msgSender(), spender, _allowances[_msgSender()][spender].add(addedValue)); return true; } /** * @dev Atomically decreases the allowance granted to `spender` by the caller. * * This is an alternative to {approve} that can be used as a mitigation for * problems described in {IERC20-approve}. * * Emits an {Approval} event indicating the updated allowance. * * Requirements: * * - `spender` cannot be the zero address. * - `spender` must have allowance for the caller of at least * `subtractedValue`. */ function decreaseAllowance(address spender, uint256 subtractedValue) public virtual returns (bool) { _approve(_msgSender(), spender, _allowances[_msgSender()][spender].sub(subtractedValue, "ERC20: decreased allowance below zero")); return true; } /** * @dev Moves tokens `amount` from `sender` to `recipient`. * * This is internal function is equivalent to {transfer}, and can be used to * e.g. implement automatic token fees, slashing mechanisms, etc. * * Emits a {Transfer} event. * * Requirements: * * - `sender` cannot be the zero address. * - `recipient` cannot be the zero address. * - `sender` must have a balance of at least `amount`. */ function _transfer(address sender, address recipient, uint256 amount) internal virtual { require(sender != address(0), "ERC20: transfer from the zero address"); require(recipient != address(0), "ERC20: transfer to the zero address"); _beforeTokenTransfer(sender, recipient, amount); _balances[sender] = _balances[sender].sub(amount, "ERC20: transfer amount exceeds balance"); _balances[recipient] = _balances[recipient].add(amount); emit Transfer(sender, recipient, amount); } /** @dev Creates `amount` tokens and assigns them to `account`, increasing * the total supply. * * Emits a {Transfer} event with `from` set to the zero address. * * Requirements * * - `to` cannot be the zero address. */ function _mint(address account, uint256 amount) internal virtual { require(account != address(0), "ERC20: mint to the zero address"); _beforeTokenTransfer(address(0), account, amount); _totalSupply = _totalSupply.add(amount); _balances[account] = _balances[account].add(amount); emit Transfer(address(0), account, amount); } /** * @dev Destroys `amount` tokens from `account`, reducing the * total supply. * * Emits a {Transfer} event with `to` set to the zero address. * * Requirements * * - `account` cannot be the zero address. * - `account` must have at least `amount` tokens. */ function _burn(address account, uint256 amount) internal virtual { require(account != address(0), "ERC20: burn from the zero address"); _beforeTokenTransfer(account, address(0), amount); _balances[account] = _balances[account].sub(amount, "ERC20: burn amount exceeds balance"); _totalSupply = _totalSupply.sub(amount); emit Transfer(account, address(0), amount); } /** * @dev Sets `amount` as the allowance of `spender` over the `owner` s tokens. * * This internal function is equivalent to `approve`, and can be used to * e.g. set automatic allowances for certain subsystems, etc. * * Emits an {Approval} event. * * Requirements: * * - `owner` cannot be the zero address. * - `spender` cannot be the zero address. */ function _approve(address owner, address spender, uint256 amount) internal virtual { require(owner != address(0), "ERC20: approve from the zero address"); require(spender != address(0), "ERC20: approve to the zero address"); _allowances[owner][spender] = amount; emit Approval(owner, spender, amount); } /** * @dev Sets {decimals} to a value other than the default one of 18. * * WARNING: This function should only be called from the constructor. Most * applications that interact with token contracts will not expect * {decimals} to ever change, and may work incorrectly if it does. */ function _setupDecimals(uint8 decimals_) internal { _decimals = decimals_; } /** * @dev Hook that is called before any transfer of tokens. This includes * minting and burning. * * Calling conditions: * * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens * will be to transferred to `to`. * - when `from` is zero, `amount` tokens will be minted for `to`. * - when `to` is zero, `amount` of ``from``'s tokens will be burned. * - `from` and `to` are never both zero. * * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks]. */ function _beforeTokenTransfer(address from, address to, uint256 amount) internal virtual { } }
/_openzeppelin/contracts/token/ERC20/IERC20.sol
// SPDX-License-Identifier: MIT pragma solidity ^0.6.0; /** * @dev Interface of the ERC20 standard as defined in the EIP. */ interface IERC20 { /** * @dev Returns the amount of tokens in existence. */ function totalSupply() external view returns (uint256); /** * @dev Returns the amount of tokens owned by `account`. */ function balanceOf(address account) external view returns (uint256); /** * @dev Moves `amount` tokens from the caller's account to `recipient`. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transfer(address recipient, uint256 amount) external returns (bool); /** * @dev Returns the remaining number of tokens that `spender` will be * allowed to spend on behalf of `owner` through {transferFrom}. This is * zero by default. * * This value changes when {approve} or {transferFrom} are called. */ function allowance(address owner, address spender) external view returns (uint256); /** * @dev Sets `amount` as the allowance of `spender` over the caller's tokens. * * Returns a boolean value indicating whether the operation succeeded. * * IMPORTANT: Beware that changing an allowance with this method brings the risk * that someone may use both the old and the new allowance by unfortunate * transaction ordering. One possible solution to mitigate this race * condition is to first reduce the spender's allowance to 0 and set the * desired value afterwards: * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729 * * Emits an {Approval} event. */ function approve(address spender, uint256 amount) external returns (bool); /** * @dev Moves `amount` tokens from `sender` to `recipient` using the * allowance mechanism. `amount` is then deducted from the caller's * allowance. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transferFrom(address sender, address recipient, uint256 amount) external returns (bool); /** * @dev Emitted when `value` tokens are moved from one account (`from`) to * another (`to`). * * Note that `value` may be zero. */ event Transfer(address indexed from, address indexed to, uint256 value); /** * @dev Emitted when the allowance of a `spender` for an `owner` is set by * a call to {approve}. `value` is the new allowance. */ event Approval(address indexed owner, address indexed spender, uint256 value); }
/_openzeppelin/contracts/utils/Address.sol
// SPDX-License-Identifier: MIT pragma solidity ^0.6.2; /** * @dev Collection of functions related to the address type */ library Address { /** * @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 * ==== */ function isContract(address account) internal view returns (bool) { // This method relies in extcodesize, which returns 0 for contracts in // construction, since the code is only stored at the end of the // constructor execution. uint256 size; // solhint-disable-next-line no-inline-assembly assembly { size := extcodesize(account) } return size > 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"); // solhint-disable-next-line avoid-low-level-calls, avoid-call-value (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 functionCall(target, data, "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"); return _functionCallWithValue(target, data, value, errorMessage); } function _functionCallWithValue(address target, bytes memory data, uint256 weiValue, string memory errorMessage) private returns (bytes memory) { require(isContract(target), "Address: call to non-contract"); // solhint-disable-next-line avoid-low-level-calls (bool success, bytes memory returndata) = target.call{ value: weiValue }(data); if (success) { return returndata; } else { // 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 // solhint-disable-next-line no-inline-assembly assembly { let returndata_size := mload(returndata) revert(add(32, returndata), returndata_size) } } else { revert(errorMessage); } } } }
/project_/contracts/swappa/ISwappaPairV1.sol
// SPDX-License-Identifier: MIT pragma solidity 0.6.8; interface ISwappaPairV1 { function swap( address input, address output, address to, bytes calldata data ) external; // Get the output amount in output token for a given amountIn of the input token, with the encoded extra data. // Output amount is undefined if input token is invalid for the swap pair. function getOutputAmount( address input, address output, uint amountIn, bytes calldata data ) external view returns (uint amountOut); }
Contract ABI
[{"type":"event","name":"Swap","inputs":[{"type":"address","name":"sender","internalType":"address","indexed":true},{"type":"address","name":"to","internalType":"address","indexed":false},{"type":"address","name":"input","internalType":"address","indexed":true},{"type":"address","name":"output","internalType":"address","indexed":true},{"type":"uint256","name":"inputAmount","internalType":"uint256","indexed":false},{"type":"uint256","name":"outputAmount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"outputAmount","internalType":"uint256"}],"name":"getOutputAmount","inputs":[{"type":"address[]","name":"path","internalType":"address[]"},{"type":"address[]","name":"pairs","internalType":"address[]"},{"type":"bytes[]","name":"extras","internalType":"bytes[]"},{"type":"uint256","name":"inputAmount","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"uint256","name":"outputAmount","internalType":"uint256"}],"name":"swapExactInputForOutput","inputs":[{"type":"address[]","name":"path","internalType":"address[]"},{"type":"address[]","name":"pairs","internalType":"address[]"},{"type":"bytes[]","name":"extras","internalType":"bytes[]"},{"type":"uint256","name":"inputAmount","internalType":"uint256"},{"type":"uint256","name":"minOutputAmount","internalType":"uint256"},{"type":"address","name":"to","internalType":"address"},{"type":"uint256","name":"deadline","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"uint256","name":"outputAmount","internalType":"uint256"}],"name":"swapExactInputForOutputWithPrecheck","inputs":[{"type":"address[]","name":"path","internalType":"address[]"},{"type":"address[]","name":"pairs","internalType":"address[]"},{"type":"bytes[]","name":"extras","internalType":"bytes[]"},{"type":"uint256","name":"inputAmount","internalType":"uint256"},{"type":"uint256","name":"minOutputAmount","internalType":"uint256"},{"type":"address","name":"to","internalType":"address"},{"type":"uint256","name":"deadline","internalType":"uint256"}]},{"type":"receive","stateMutability":"payable"}]
Contract Creation Code
0x608060405234801561001057600080fd5b50611405806100206000396000f3fe6080604052600436106100385760003560e01c80630862d12f14610044578063adf6fa021461007a578063e2f46a001461009a5761003f565b3661003f57005b600080fd5b34801561005057600080fd5b5061006461005f366004610d8f565b6100ba565b6040516100719190611361565b60405180910390f35b34801561008657600080fd5b50610064610095366004610d8f565b610666565b3480156100a657600080fd5b506100646100b5366004610cf0565b610b29565b600081428110156100e65760405162461bcd60e51b81526004016100dd90611213565b60405180910390fd5b600189018b146101085760405162461bcd60e51b81526004016100dd906112a7565b8887146101275760405162461bcd60e51b81526004016100dd9061124a565b886101445760405162461bcd60e51b81526004016100dd9061109f565b8b8b600081811061015157fe5b90506020020160208101906101669190610cce565b73ffffffffffffffffffffffffffffffffffffffff166323b872dd338c8c600081811061018f57fe5b90506020020160208101906101a49190610cce565b896040518463ffffffff1660e01b81526004016101c393929190610f14565b602060405180830381600087803b1580156101dd57600080fd5b505af11580156101f1573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906102159190610e52565b6102315760405162461bcd60e51b81526004016100dd906110fc565b60005b898110156103e6576000808e8e8481811061024b57fe5b90506020020160208101906102609190610cce565b8f8f8560010181811061026f57fe5b90506020020160208101906102849190610cce565b909250905060007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8d0184106102ba57306102de565b8d8d856001018181106102c957fe5b90506020020160208101906102de9190610cce565b905060608c8c868181106102ee57fe5b9050602002810190610300919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508e8e8681811061035157fe5b90506020020160208101906103669190610cce565b73ffffffffffffffffffffffffffffffffffffffff166332ef8314858585856040518563ffffffff1660e01b81526004016103a49493929190610f45565b600060405180830381600087803b1580156103be57600080fd5b505af11580156103d2573d6000803e3d6000fd5b505060019096019550610234945050505050565b5060008c8c7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff810181811061041757fe5b905060200201602081019061042c9190610cce565b6040517f70a0823100000000000000000000000000000000000000000000000000000000815290915073ffffffffffffffffffffffffffffffffffffffff8216906370a0823190610481903090600401610ef3565b60206040518083038186803b15801561049957600080fd5b505afa1580156104ad573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104d19190610e72565b9250858310156104f35760405162461bcd60e51b81526004016100dd90611304565b6040517fa9059cbb00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82169063a9059cbb90610547908890879060040161104b565b602060405180830381600087803b15801561056157600080fd5b505af1158015610575573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105999190610e52565b6105b55760405162461bcd60e51b81526004016100dd906111b6565b8073ffffffffffffffffffffffffffffffffffffffff168d8d60008181106105d957fe5b90506020020160208101906105ee9190610cce565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff167f20efd6d5195b7b50273f01cd79a27989255356f9f13293edc53ee142accfdb75888b8860405161064e93929190611071565b60405180910390a450509a9950505050505050505050565b600081428110156106895760405162461bcd60e51b81526004016100dd90611213565b600189018b146106ab5760405162461bcd60e51b81526004016100dd906112a7565b8887146106ca5760405162461bcd60e51b81526004016100dd9061124a565b886106e75760405162461bcd60e51b81526004016100dd9061109f565b85915060005b89811015610866576000808e8e8481811061070457fe5b90506020020160208101906107199190610cce565b8f8f8560010181811061072857fe5b905060200201602081019061073d9190610cce565b9150915060608b8b8581811061074f57fe5b9050602002810190610761919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508d8d858181106107b257fe5b90506020020160208101906107c79190610cce565b73ffffffffffffffffffffffffffffffffffffffff16637eace892848489856040518563ffffffff1660e01b8152600401610805949392919061100c565b60206040518083038186803b15801561081d57600080fd5b505afa158015610831573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108559190610e72565b955050600190920191506106ed9050565b50848210156108875760405162461bcd60e51b81526004016100dd90611159565b8b8b600081811061089457fe5b90506020020160208101906108a99190610cce565b73ffffffffffffffffffffffffffffffffffffffff166323b872dd338c8c60008181106108d257fe5b90506020020160208101906108e79190610cce565b896040518463ffffffff1660e01b815260040161090693929190610f14565b602060405180830381600087803b15801561092057600080fd5b505af1158015610934573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906109589190610e52565b6109745760405162461bcd60e51b81526004016100dd906110fc565b60005b898110156103e6576000808e8e8481811061098e57fe5b90506020020160208101906109a39190610cce565b8f8f856001018181106109b257fe5b90506020020160208101906109c79190610cce565b909250905060007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8d0184106109fd5730610a21565b8d8d85600101818110610a0c57fe5b9050602002016020810190610a219190610cce565b905060608c8c86818110610a3157fe5b9050602002810190610a43919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508e8e86818110610a9457fe5b9050602002016020810190610aa99190610cce565b73ffffffffffffffffffffffffffffffffffffffff166332ef8314858585856040518563ffffffff1660e01b8152600401610ae79493929190610f45565b600060405180830381600087803b158015610b0157600080fd5b505af1158015610b15573d6000803e3d6000fd5b505060019096019550610977945050505050565b8060005b85811015610c4f57868682818110610b4157fe5b9050602002016020810190610b569190610cce565b73ffffffffffffffffffffffffffffffffffffffff16637eace8928a8a84818110610b7d57fe5b9050602002016020810190610b929190610cce565b8b8b85600101818110610ba157fe5b9050602002016020810190610bb69190610cce565b85898987818110610bc357fe5b9050602002810190610bd5919061136a565b6040518663ffffffff1660e01b8152600401610bf5959493929190610f90565b60206040518083038186803b158015610c0d57600080fd5b505afa158015610c21573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c459190610e72565b9150600101610b2d565b50979650505050505050565b803573ffffffffffffffffffffffffffffffffffffffff81168114610c7f57600080fd5b92915050565b60008083601f840112610c96578182fd5b50813567ffffffffffffffff811115610cad578182fd5b6020830191508360208083028501011115610cc757600080fd5b9250929050565b600060208284031215610cdf578081fd5b610ce98383610c5b565b9392505050565b60008060008060008060006080888a031215610d0a578283fd5b873567ffffffffffffffff80821115610d21578485fd5b610d2d8b838c01610c85565b909950975060208a0135915080821115610d45578485fd5b610d518b838c01610c85565b909750955060408a0135915080821115610d69578485fd5b50610d768a828b01610c85565b989b979a50959894979596606090950135949350505050565b60008060008060008060008060008060e08b8d031215610dad578283fd5b8a3567ffffffffffffffff80821115610dc4578485fd5b610dd08e838f01610c85565b909c509a5060208d0135915080821115610de8578485fd5b610df48e838f01610c85565b909a50985060408d0135915080821115610e0c578485fd5b50610e198d828e01610c85565b90975095505060608b0135935060808b01359250610e3a8c60a08d01610c5b565b915060c08b013590509295989b9194979a5092959850565b600060208284031215610e63578081fd5b81518015158114610ce9578182fd5b600060208284031215610e83578081fd5b5051919050565b60008151808452815b81811015610eaf57602081850181015186830182015201610e93565b81811115610ec05782602083870101525b50601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b73ffffffffffffffffffffffffffffffffffffffff91909116815260200190565b73ffffffffffffffffffffffffffffffffffffffff9384168152919092166020820152604081019190915260600190565b600073ffffffffffffffffffffffffffffffffffffffff8087168352808616602084015280851660408401525060806060830152610f866080830184610e8a565b9695505050505050565b600073ffffffffffffffffffffffffffffffffffffffff808816835280871660208401525084604083015260806060830152826080830152828460a084013781830160a090810191909152601f9092017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0160101949350505050565b600073ffffffffffffffffffffffffffffffffffffffff808716835280861660208401525083604083015260806060830152610f866080830184610e8a565b73ffffffffffffffffffffffffffffffffffffffff929092168252602082015260400190565b73ffffffffffffffffffffffffffffffffffffffff9390931683526020830191909152604082015260600190565b6020808252602a908201527f537761707061526f757465723a204d7573742068617665206174206c6561737460408201527f206f6e6520706169722100000000000000000000000000000000000000000000606082015260800190565b6020808252602a908201527f537761707061526f757465723a20496e697469616c207472616e73666572467260408201527f6f6d206661696c65642100000000000000000000000000000000000000000000606082015260800190565b60208082526032908201527f537761707061526f757465723a20496e73756666696369656e7420657870656360408201527f746564206f757470757420616d6f756e74210000000000000000000000000000606082015260800190565b60208082526024908201527f537761707061526f757465723a2046696e616c207472616e736665722066616960408201527f6c65642100000000000000000000000000000000000000000000000000000000606082015260800190565b60208082526016908201527f537761707061526f757465723a20457870697265642100000000000000000000604082015260600190565b60208082526028908201527f537761707061526f757465723a20506169727320616e6420457874726173206d60408201527f69736d6174636821000000000000000000000000000000000000000000000000606082015260800190565b60208082526026908201527f537761707061526f757465723a205061746820616e64205061697273206d697360408201527f6d61746368210000000000000000000000000000000000000000000000000000606082015260800190565b60208082526029908201527f537761707061526f757465723a20496e73756666696369656e74206f7574707560408201527f7420616d6f756e74210000000000000000000000000000000000000000000000606082015260800190565b90815260200190565b60008083357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe184360301811261139e578283fd5b8084018035925067ffffffffffffffff8311156113b9578384fd5b60200192505036819003821315610cc757600080fdfea26469706673582212208b7f630fe01c882018a3b216891c30c2ce54a38b74b0e568b8fbc0eae284c6a264736f6c63430006080033
Deployed ByteCode
0x6080604052600436106100385760003560e01c80630862d12f14610044578063adf6fa021461007a578063e2f46a001461009a5761003f565b3661003f57005b600080fd5b34801561005057600080fd5b5061006461005f366004610d8f565b6100ba565b6040516100719190611361565b60405180910390f35b34801561008657600080fd5b50610064610095366004610d8f565b610666565b3480156100a657600080fd5b506100646100b5366004610cf0565b610b29565b600081428110156100e65760405162461bcd60e51b81526004016100dd90611213565b60405180910390fd5b600189018b146101085760405162461bcd60e51b81526004016100dd906112a7565b8887146101275760405162461bcd60e51b81526004016100dd9061124a565b886101445760405162461bcd60e51b81526004016100dd9061109f565b8b8b600081811061015157fe5b90506020020160208101906101669190610cce565b73ffffffffffffffffffffffffffffffffffffffff166323b872dd338c8c600081811061018f57fe5b90506020020160208101906101a49190610cce565b896040518463ffffffff1660e01b81526004016101c393929190610f14565b602060405180830381600087803b1580156101dd57600080fd5b505af11580156101f1573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906102159190610e52565b6102315760405162461bcd60e51b81526004016100dd906110fc565b60005b898110156103e6576000808e8e8481811061024b57fe5b90506020020160208101906102609190610cce565b8f8f8560010181811061026f57fe5b90506020020160208101906102849190610cce565b909250905060007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8d0184106102ba57306102de565b8d8d856001018181106102c957fe5b90506020020160208101906102de9190610cce565b905060608c8c868181106102ee57fe5b9050602002810190610300919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508e8e8681811061035157fe5b90506020020160208101906103669190610cce565b73ffffffffffffffffffffffffffffffffffffffff166332ef8314858585856040518563ffffffff1660e01b81526004016103a49493929190610f45565b600060405180830381600087803b1580156103be57600080fd5b505af11580156103d2573d6000803e3d6000fd5b505060019096019550610234945050505050565b5060008c8c7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff810181811061041757fe5b905060200201602081019061042c9190610cce565b6040517f70a0823100000000000000000000000000000000000000000000000000000000815290915073ffffffffffffffffffffffffffffffffffffffff8216906370a0823190610481903090600401610ef3565b60206040518083038186803b15801561049957600080fd5b505afa1580156104ad573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104d19190610e72565b9250858310156104f35760405162461bcd60e51b81526004016100dd90611304565b6040517fa9059cbb00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff82169063a9059cbb90610547908890879060040161104b565b602060405180830381600087803b15801561056157600080fd5b505af1158015610575573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105999190610e52565b6105b55760405162461bcd60e51b81526004016100dd906111b6565b8073ffffffffffffffffffffffffffffffffffffffff168d8d60008181106105d957fe5b90506020020160208101906105ee9190610cce565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff167f20efd6d5195b7b50273f01cd79a27989255356f9f13293edc53ee142accfdb75888b8860405161064e93929190611071565b60405180910390a450509a9950505050505050505050565b600081428110156106895760405162461bcd60e51b81526004016100dd90611213565b600189018b146106ab5760405162461bcd60e51b81526004016100dd906112a7565b8887146106ca5760405162461bcd60e51b81526004016100dd9061124a565b886106e75760405162461bcd60e51b81526004016100dd9061109f565b85915060005b89811015610866576000808e8e8481811061070457fe5b90506020020160208101906107199190610cce565b8f8f8560010181811061072857fe5b905060200201602081019061073d9190610cce565b9150915060608b8b8581811061074f57fe5b9050602002810190610761919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508d8d858181106107b257fe5b90506020020160208101906107c79190610cce565b73ffffffffffffffffffffffffffffffffffffffff16637eace892848489856040518563ffffffff1660e01b8152600401610805949392919061100c565b60206040518083038186803b15801561081d57600080fd5b505afa158015610831573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108559190610e72565b955050600190920191506106ed9050565b50848210156108875760405162461bcd60e51b81526004016100dd90611159565b8b8b600081811061089457fe5b90506020020160208101906108a99190610cce565b73ffffffffffffffffffffffffffffffffffffffff166323b872dd338c8c60008181106108d257fe5b90506020020160208101906108e79190610cce565b896040518463ffffffff1660e01b815260040161090693929190610f14565b602060405180830381600087803b15801561092057600080fd5b505af1158015610934573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906109589190610e52565b6109745760405162461bcd60e51b81526004016100dd906110fc565b60005b898110156103e6576000808e8e8481811061098e57fe5b90506020020160208101906109a39190610cce565b8f8f856001018181106109b257fe5b90506020020160208101906109c79190610cce565b909250905060007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8d0184106109fd5730610a21565b8d8d85600101818110610a0c57fe5b9050602002016020810190610a219190610cce565b905060608c8c86818110610a3157fe5b9050602002810190610a43919061136a565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505090508e8e86818110610a9457fe5b9050602002016020810190610aa99190610cce565b73ffffffffffffffffffffffffffffffffffffffff166332ef8314858585856040518563ffffffff1660e01b8152600401610ae79493929190610f45565b600060405180830381600087803b158015610b0157600080fd5b505af1158015610b15573d6000803e3d6000fd5b505060019096019550610977945050505050565b8060005b85811015610c4f57868682818110610b4157fe5b9050602002016020810190610b569190610cce565b73ffffffffffffffffffffffffffffffffffffffff16637eace8928a8a84818110610b7d57fe5b9050602002016020810190610b929190610cce565b8b8b85600101818110610ba157fe5b9050602002016020810190610bb69190610cce565b85898987818110610bc357fe5b9050602002810190610bd5919061136a565b6040518663ffffffff1660e01b8152600401610bf5959493929190610f90565b60206040518083038186803b158015610c0d57600080fd5b505afa158015610c21573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c459190610e72565b9150600101610b2d565b50979650505050505050565b803573ffffffffffffffffffffffffffffffffffffffff81168114610c7f57600080fd5b92915050565b60008083601f840112610c96578182fd5b50813567ffffffffffffffff811115610cad578182fd5b6020830191508360208083028501011115610cc757600080fd5b9250929050565b600060208284031215610cdf578081fd5b610ce98383610c5b565b9392505050565b60008060008060008060006080888a031215610d0a578283fd5b873567ffffffffffffffff80821115610d21578485fd5b610d2d8b838c01610c85565b909950975060208a0135915080821115610d45578485fd5b610d518b838c01610c85565b909750955060408a0135915080821115610d69578485fd5b50610d768a828b01610c85565b989b979a50959894979596606090950135949350505050565b60008060008060008060008060008060e08b8d031215610dad578283fd5b8a3567ffffffffffffffff80821115610dc4578485fd5b610dd08e838f01610c85565b909c509a5060208d0135915080821115610de8578485fd5b610df48e838f01610c85565b909a50985060408d0135915080821115610e0c578485fd5b50610e198d828e01610c85565b90975095505060608b0135935060808b01359250610e3a8c60a08d01610c5b565b915060c08b013590509295989b9194979a5092959850565b600060208284031215610e63578081fd5b81518015158114610ce9578182fd5b600060208284031215610e83578081fd5b5051919050565b60008151808452815b81811015610eaf57602081850181015186830182015201610e93565b81811115610ec05782602083870101525b50601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b73ffffffffffffffffffffffffffffffffffffffff91909116815260200190565b73ffffffffffffffffffffffffffffffffffffffff9384168152919092166020820152604081019190915260600190565b600073ffffffffffffffffffffffffffffffffffffffff8087168352808616602084015280851660408401525060806060830152610f866080830184610e8a565b9695505050505050565b600073ffffffffffffffffffffffffffffffffffffffff808816835280871660208401525084604083015260806060830152826080830152828460a084013781830160a090810191909152601f9092017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0160101949350505050565b600073ffffffffffffffffffffffffffffffffffffffff808716835280861660208401525083604083015260806060830152610f866080830184610e8a565b73ffffffffffffffffffffffffffffffffffffffff929092168252602082015260400190565b73ffffffffffffffffffffffffffffffffffffffff9390931683526020830191909152604082015260600190565b6020808252602a908201527f537761707061526f757465723a204d7573742068617665206174206c6561737460408201527f206f6e6520706169722100000000000000000000000000000000000000000000606082015260800190565b6020808252602a908201527f537761707061526f757465723a20496e697469616c207472616e73666572467260408201527f6f6d206661696c65642100000000000000000000000000000000000000000000606082015260800190565b60208082526032908201527f537761707061526f757465723a20496e73756666696369656e7420657870656360408201527f746564206f757470757420616d6f756e74210000000000000000000000000000606082015260800190565b60208082526024908201527f537761707061526f757465723a2046696e616c207472616e736665722066616960408201527f6c65642100000000000000000000000000000000000000000000000000000000606082015260800190565b60208082526016908201527f537761707061526f757465723a20457870697265642100000000000000000000604082015260600190565b60208082526028908201527f537761707061526f757465723a20506169727320616e6420457874726173206d60408201527f69736d6174636821000000000000000000000000000000000000000000000000606082015260800190565b60208082526026908201527f537761707061526f757465723a205061746820616e64205061697273206d697360408201527f6d61746368210000000000000000000000000000000000000000000000000000606082015260800190565b60208082526029908201527f537761707061526f757465723a20496e73756666696369656e74206f7574707560408201527f7420616d6f756e74210000000000000000000000000000000000000000000000606082015260800190565b90815260200190565b60008083357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe184360301811261139e578283fd5b8084018035925067ffffffffffffffff8311156113b9578384fd5b60200192505036819003821315610cc757600080fdfea26469706673582212208b7f630fe01c882018a3b216891c30c2ce54a38b74b0e568b8fbc0eae284c6a264736f6c63430006080033