Source Code
Overview
ETH Balance
0 ETH
Eth Value
$0.00More Info
Private Name Tags
ContractCreator
TokenTracker
Latest 25 from a total of 2,440 transactions
| Transaction Hash |
Method
|
Block
|
From
|
To
|
|||||
|---|---|---|---|---|---|---|---|---|---|
| Approve | 23423702 | 153 days ago | IN | 0 ETH | 0.0000164 | ||||
| Redeem | 21940751 | 360 days ago | IN | 0 ETH | 0.0001458 | ||||
| Transfer | 21680871 | 396 days ago | IN | 0 ETH | 0.00131913 | ||||
| Change P Network | 21314344 | 447 days ago | IN | 0 ETH | 0.00046418 | ||||
| Redeem | 20740574 | 527 days ago | IN | 0 ETH | 0.00021392 | ||||
| Approve | 20730711 | 529 days ago | IN | 0 ETH | 0.00004268 | ||||
| Transfer | 20729628 | 529 days ago | IN | 0 ETH | 0.00102012 | ||||
| Redeem | 20483554 | 563 days ago | IN | 0 ETH | 0.0002237 | ||||
| Mint | 20358012 | 581 days ago | IN | 0 ETH | 0.00075513 | ||||
| Approve | 20137978 | 612 days ago | IN | 0 ETH | 0.0001368 | ||||
| Mint | 20137913 | 612 days ago | IN | 0 ETH | 0.00075513 | ||||
| Transfer | 19860080 | 650 days ago | IN | 0 ETH | 0.00025955 | ||||
| Redeem | 19847967 | 652 days ago | IN | 0 ETH | 0.00022012 | ||||
| Transfer | 19820793 | 656 days ago | IN | 0 ETH | 0.00035182 | ||||
| Mint | 19812312 | 657 days ago | IN | 0 ETH | 0.00048434 | ||||
| Mint | 19633570 | 682 days ago | IN | 0 ETH | 0.00168503 | ||||
| Approve | 19575791 | 690 days ago | IN | 0 ETH | 0.00279097 | ||||
| Mint | 19575776 | 690 days ago | IN | 0 ETH | 0.00548521 | ||||
| Mint | 19480785 | 704 days ago | IN | 0 ETH | 0.00251485 | ||||
| Redeem | 19466305 | 706 days ago | IN | 0 ETH | 0.00109929 | ||||
| Redeem | 19424945 | 711 days ago | IN | 0 ETH | 0.00235155 | ||||
| Approve | 19424464 | 711 days ago | IN | 0 ETH | 0.00096514 | ||||
| Approve | 19424202 | 712 days ago | IN | 0 ETH | 0.00102768 | ||||
| Approve | 19400590 | 715 days ago | IN | 0 ETH | 0.00324938 | ||||
| Mint | 19400350 | 715 days ago | IN | 0 ETH | 0.00509083 |
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Loading...
Loading
Loading...
Loading
Cross-Chain Transactions
Loading...
Loading
Contract Name:
PToken
Compiler Version
v0.5.17+commit.d19bba13
Contract Source Code (Solidity)
/**
*Submitted for verification at Etherscan.io on 2021-03-05
*/
pragma solidity ^0.5.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.
*/
contract Context {
// Empty internal constructor, to prevent people from mistakenly deploying
// an instance of this contract, which should be used via inheritance.
constructor () internal { }
// solhint-disable-previous-line no-empty-blocks
function _msgSender() internal view returns (address payable) {
return msg.sender;
}
function _msgData() internal view returns (bytes memory) {
this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691
return msg.data;
}
}
// File: @openzeppelin/contracts/token/ERC777/IERC777.sol
pragma solidity ^0.5.0;
/**
* @dev Interface of the ERC777Token standard as defined in the EIP.
*
* This contract uses the
* https://eips.ethereum.org/EIPS/eip-1820[ERC1820 registry standard] to let
* token holders and recipients react to token movements by using setting implementers
* for the associated interfaces in said registry. See {IERC1820Registry} and
* {ERC1820Implementer}.
*/
interface IERC777 {
/**
* @dev Returns the name of the token.
*/
function name() external view returns (string memory);
/**
* @dev Returns the symbol of the token, usually a shorter version of the
* name.
*/
function symbol() external view returns (string memory);
/**
* @dev Returns the smallest part of the token that is not divisible. This
* means all token operations (creation, movement and destruction) must have
* amounts that are a multiple of this number.
*
* For most token contracts, this value will equal 1.
*/
function granularity() external view returns (uint256);
/**
* @dev Returns the amount of tokens in existence.
*/
function totalSupply() external view returns (uint256);
/**
* @dev Returns the amount of tokens owned by an account (`owner`).
*/
function balanceOf(address owner) external view returns (uint256);
/**
* @dev Moves `amount` tokens from the caller's account to `recipient`.
*
* If send or receive hooks are registered for the caller and `recipient`,
* the corresponding functions will be called with `data` and empty
* `operatorData`. See {IERC777Sender} and {IERC777Recipient}.
*
* Emits a {Sent} event.
*
* Requirements
*
* - the caller must have at least `amount` tokens.
* - `recipient` cannot be the zero address.
* - if `recipient` is a contract, it must implement the {IERC777Recipient}
* interface.
*/
function send(address recipient, uint256 amount, bytes calldata data) external;
/**
* @dev Destroys `amount` tokens from the caller's account, reducing the
* total supply.
*
* If a send hook is registered for the caller, the corresponding function
* will be called with `data` and empty `operatorData`. See {IERC777Sender}.
*
* Emits a {Burned} event.
*
* Requirements
*
* - the caller must have at least `amount` tokens.
*/
function burn(uint256 amount, bytes calldata data) external;
/**
* @dev Returns true if an account is an operator of `tokenHolder`.
* Operators can send and burn tokens on behalf of their owners. All
* accounts are their own operator.
*
* See {operatorSend} and {operatorBurn}.
*/
function isOperatorFor(address operator, address tokenHolder) external view returns (bool);
/**
* @dev Make an account an operator of the caller.
*
* See {isOperatorFor}.
*
* Emits an {AuthorizedOperator} event.
*
* Requirements
*
* - `operator` cannot be calling address.
*/
function authorizeOperator(address operator) external;
/**
* @dev Make an account an operator of the caller.
*
* See {isOperatorFor} and {defaultOperators}.
*
* Emits a {RevokedOperator} event.
*
* Requirements
*
* - `operator` cannot be calling address.
*/
function revokeOperator(address operator) external;
/**
* @dev Returns the list of default operators. These accounts are operators
* for all token holders, even if {authorizeOperator} was never called on
* them.
*
* This list is immutable, but individual holders may revoke these via
* {revokeOperator}, in which case {isOperatorFor} will return false.
*/
function defaultOperators() external view returns (address[] memory);
/**
* @dev Moves `amount` tokens from `sender` to `recipient`. The caller must
* be an operator of `sender`.
*
* If send or receive hooks are registered for `sender` and `recipient`,
* the corresponding functions will be called with `data` and
* `operatorData`. See {IERC777Sender} and {IERC777Recipient}.
*
* Emits a {Sent} event.
*
* Requirements
*
* - `sender` cannot be the zero address.
* - `sender` must have at least `amount` tokens.
* - the caller must be an operator for `sender`.
* - `recipient` cannot be the zero address.
* - if `recipient` is a contract, it must implement the {IERC777Recipient}
* interface.
*/
function operatorSend(
address sender,
address recipient,
uint256 amount,
bytes calldata data,
bytes calldata operatorData
) external;
/**
* @dev Destoys `amount` tokens from `account`, reducing the total supply.
* The caller must be an operator of `account`.
*
* If a send hook is registered for `account`, the corresponding function
* will be called with `data` and `operatorData`. See {IERC777Sender}.
*
* Emits a {Burned} event.
*
* Requirements
*
* - `account` cannot be the zero address.
* - `account` must have at least `amount` tokens.
* - the caller must be an operator for `account`.
*/
function operatorBurn(
address account,
uint256 amount,
bytes calldata data,
bytes calldata operatorData
) external;
event Sent(
address indexed operator,
address indexed from,
address indexed to,
uint256 amount,
bytes data,
bytes operatorData
);
event Minted(address indexed operator, address indexed to, uint256 amount, bytes data, bytes operatorData);
event Burned(address indexed operator, address indexed from, uint256 amount, bytes data, bytes operatorData);
event AuthorizedOperator(address indexed operator, address indexed tokenHolder);
event RevokedOperator(address indexed operator, address indexed tokenHolder);
}
// File: @openzeppelin/contracts/token/ERC777/IERC777Recipient.sol
pragma solidity ^0.5.0;
/**
* @dev Interface of the ERC777TokensRecipient standard as defined in the EIP.
*
* Accounts can be notified of {IERC777} tokens being sent to them by having a
* contract implement this interface (contract holders can be their own
* implementer) and registering it on the
* https://eips.ethereum.org/EIPS/eip-1820[ERC1820 global registry].
*
* See {IERC1820Registry} and {ERC1820Implementer}.
*/
interface IERC777Recipient {
/**
* @dev Called by an {IERC777} token contract whenever tokens are being
* moved or created into a registered account (`to`). The type of operation
* is conveyed by `from` being the zero address or not.
*
* This call occurs _after_ the token contract's state is updated, so
* {IERC777-balanceOf}, etc., can be used to query the post-operation state.
*
* This function may revert to prevent the operation from being executed.
*/
function tokensReceived(
address operator,
address from,
address to,
uint256 amount,
bytes calldata userData,
bytes calldata operatorData
) external;
}
// File: @openzeppelin/contracts/token/ERC777/IERC777Sender.sol
pragma solidity ^0.5.0;
/**
* @dev Interface of the ERC777TokensSender standard as defined in the EIP.
*
* {IERC777} Token holders can be notified of operations performed on their
* tokens by having a contract implement this interface (contract holders can be
* their own implementer) and registering it on the
* https://eips.ethereum.org/EIPS/eip-1820[ERC1820 global registry].
*
* See {IERC1820Registry} and {ERC1820Implementer}.
*/
interface IERC777Sender {
/**
* @dev Called by an {IERC777} token contract whenever a registered holder's
* (`from`) tokens are about to be moved or destroyed. The type of operation
* is conveyed by `to` being the zero address or not.
*
* This call occurs _before_ the token contract's state is updated, so
* {IERC777-balanceOf}, etc., can be used to query the pre-operation state.
*
* This function may revert to prevent the operation from being executed.
*/
function tokensToSend(
address operator,
address from,
address to,
uint256 amount,
bytes calldata userData,
bytes calldata operatorData
) external;
}
// File: @openzeppelin/contracts/token/ERC20/IERC20.sol
pragma solidity ^0.5.0;
/**
* @dev Interface of the ERC20 standard as defined in the EIP. Does not include
* the optional functions; to access them see {ERC20Detailed}.
*/
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);
}
// File: @openzeppelin/contracts/math/SafeMath.sol
pragma solidity ^0.5.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.
*
* _Available since v2.4.0._
*/
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.
*
* _Available since v2.4.0._
*/
function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
// Solidity only automatically asserts when dividing by 0
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.
*
* _Available since v2.4.0._
*/
function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
require(b != 0, errorMessage);
return a % b;
}
}
// File: @openzeppelin/contracts/utils/Address.sol
pragma solidity ^0.5.5;
/**
* @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) {
// According to EIP-1052, 0x0 is the value returned for not-yet created accounts
// and 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470 is returned
// for accounts without code, i.e. `keccak256('')`
bytes32 codehash;
bytes32 accountHash = 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470;
// solhint-disable-next-line no-inline-assembly
assembly { codehash := extcodehash(account) }
return (codehash != accountHash && codehash != 0x0);
}
/**
* @dev Converts an `address` into `address payable`. Note that this is
* simply a type cast: the actual underlying value is not changed.
*
* _Available since v2.4.0._
*/
function toPayable(address account) internal pure returns (address payable) {
return address(uint160(account));
}
/**
* @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].
*
* _Available since v2.4.0._
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
// solhint-disable-next-line avoid-call-value
(bool success, ) = recipient.call.value(amount)("");
require(success, "Address: unable to send value, recipient may have reverted");
}
}
// File: @openzeppelin/contracts/introspection/IERC1820Registry.sol
pragma solidity ^0.5.0;
/**
* @dev Interface of the global ERC1820 Registry, as defined in the
* https://eips.ethereum.org/EIPS/eip-1820[EIP]. Accounts may register
* implementers for interfaces in this registry, as well as query support.
*
* Implementers may be shared by multiple accounts, and can also implement more
* than a single interface for each account. Contracts can implement interfaces
* for themselves, but externally-owned accounts (EOA) must delegate this to a
* contract.
*
* {IERC165} interfaces can also be queried via the registry.
*
* For an in-depth explanation and source code analysis, see the EIP text.
*/
interface IERC1820Registry {
/**
* @dev Sets `newManager` as the manager for `account`. A manager of an
* account is able to set interface implementers for it.
*
* By default, each account is its own manager. Passing a value of `0x0` in
* `newManager` will reset the manager to this initial state.
*
* Emits a {ManagerChanged} event.
*
* Requirements:
*
* - the caller must be the current manager for `account`.
*/
function setManager(address account, address newManager) external;
/**
* @dev Returns the manager for `account`.
*
* See {setManager}.
*/
function getManager(address account) external view returns (address);
/**
* @dev Sets the `implementer` contract as `account`'s implementer for
* `interfaceHash`.
*
* `account` being the zero address is an alias for the caller's address.
* The zero address can also be used in `implementer` to remove an old one.
*
* See {interfaceHash} to learn how these are created.
*
* Emits an {InterfaceImplementerSet} event.
*
* Requirements:
*
* - the caller must be the current manager for `account`.
* - `interfaceHash` must not be an {IERC165} interface id (i.e. it must not
* end in 28 zeroes).
* - `implementer` must implement {IERC1820Implementer} and return true when
* queried for support, unless `implementer` is the caller. See
* {IERC1820Implementer-canImplementInterfaceForAddress}.
*/
function setInterfaceImplementer(address account, bytes32 interfaceHash, address implementer) external;
/**
* @dev Returns the implementer of `interfaceHash` for `account`. If no such
* implementer is registered, returns the zero address.
*
* If `interfaceHash` is an {IERC165} interface id (i.e. it ends with 28
* zeroes), `account` will be queried for support of it.
*
* `account` being the zero address is an alias for the caller's address.
*/
function getInterfaceImplementer(address account, bytes32 interfaceHash) external view returns (address);
/**
* @dev Returns the interface hash for an `interfaceName`, as defined in the
* corresponding
* https://eips.ethereum.org/EIPS/eip-1820#interface-name[section of the EIP].
*/
function interfaceHash(string calldata interfaceName) external pure returns (bytes32);
/**
* @notice Updates the cache with whether the contract implements an ERC165 interface or not.
* @param account Address of the contract for which to update the cache.
* @param interfaceId ERC165 interface for which to update the cache.
*/
function updateERC165Cache(address account, bytes4 interfaceId) external;
/**
* @notice Checks whether a contract implements an ERC165 interface or not.
* If the result is not cached a direct lookup on the contract address is performed.
* If the result is not cached or the cached value is out-of-date, the cache MUST be updated manually by calling
* {updateERC165Cache} with the contract address.
* @param account Address of the contract to check.
* @param interfaceId ERC165 interface to check.
* @return True if `account` implements `interfaceId`, false otherwise.
*/
function implementsERC165Interface(address account, bytes4 interfaceId) external view returns (bool);
/**
* @notice Checks whether a contract implements an ERC165 interface or not without using nor updating the cache.
* @param account Address of the contract to check.
* @param interfaceId ERC165 interface to check.
* @return True if `account` implements `interfaceId`, false otherwise.
*/
function implementsERC165InterfaceNoCache(address account, bytes4 interfaceId) external view returns (bool);
event InterfaceImplementerSet(address indexed account, bytes32 indexed interfaceHash, address indexed implementer);
event ManagerChanged(address indexed account, address indexed newManager);
}
// File: @openzeppelin/contracts/token/ERC777/ERC777.sol
pragma solidity ^0.5.0;
/**
* @dev Implementation of the {IERC777} 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}.
*
* Support for ERC20 is included in this contract, as specified by the EIP: both
* the ERC777 and ERC20 interfaces can be safely used when interacting with it.
* Both {IERC777-Sent} and {IERC20-Transfer} events are emitted on token
* movements.
*
* Additionally, the {IERC777-granularity} value is hard-coded to `1`, meaning that there
* are no special restrictions in the amount of tokens that created, moved, or
* destroyed. This makes integration with ERC20 applications seamless.
*/
contract ERC777 is Context, IERC777, IERC20 {
using SafeMath for uint256;
using Address for address;
IERC1820Registry constant internal ERC1820_REGISTRY = IERC1820Registry(0x1820a4B7618BdE71Dce8cdc73aAB6C95905faD24);
mapping(address => uint256) private _balances;
uint256 private _totalSupply;
string private _name;
string private _symbol;
// We inline the result of the following hashes because Solidity doesn't resolve them at compile time.
// See https://github.com/ethereum/solidity/issues/4024.
// keccak256("ERC777TokensSender")
bytes32 constant private TOKENS_SENDER_INTERFACE_HASH =
0x29ddb589b1fb5fc7cf394961c1adf5f8c6454761adf795e67fe149f658abe895;
// keccak256("ERC777TokensRecipient")
bytes32 constant private TOKENS_RECIPIENT_INTERFACE_HASH =
0xb281fc8c12954d22544db45de3159a39272895b169a852b314f9cc762e44c53b;
// This isn't ever read from - it's only used to respond to the defaultOperators query.
address[] private _defaultOperatorsArray;
// Immutable, but accounts may revoke them (tracked in __revokedDefaultOperators).
mapping(address => bool) private _defaultOperators;
// For each account, a mapping of its operators and revoked default operators.
mapping(address => mapping(address => bool)) private _operators;
mapping(address => mapping(address => bool)) private _revokedDefaultOperators;
// ERC20-allowances
mapping (address => mapping (address => uint256)) private _allowances;
/**
* @dev `defaultOperators` may be an empty array.
*/
constructor(
string memory name,
string memory symbol,
address[] memory defaultOperators
) public {
_name = name;
_symbol = symbol;
_defaultOperatorsArray = defaultOperators;
for (uint256 i = 0; i < _defaultOperatorsArray.length; i++) {
_defaultOperators[_defaultOperatorsArray[i]] = true;
}
// register interfaces
ERC1820_REGISTRY.setInterfaceImplementer(address(this), keccak256("ERC777Token"), address(this));
ERC1820_REGISTRY.setInterfaceImplementer(address(this), keccak256("ERC20Token"), address(this));
}
/**
* @dev See {IERC777-name}.
*/
function name() public view returns (string memory) {
return _name;
}
/**
* @dev See {IERC777-symbol}.
*/
function symbol() public view returns (string memory) {
return _symbol;
}
/**
* @dev See {ERC20Detailed-decimals}.
*
* Always returns 18, as per the
* [ERC777 EIP](https://eips.ethereum.org/EIPS/eip-777#backward-compatibility).
*/
function decimals() public pure returns (uint8) {
return 18;
}
/**
* @dev See {IERC777-granularity}.
*
* This implementation always returns `1`.
*/
function granularity() public view returns (uint256) {
return 1;
}
/**
* @dev See {IERC777-totalSupply}.
*/
function totalSupply() public view returns (uint256) {
return _totalSupply;
}
/**
* @dev Returns the amount of tokens owned by an account (`tokenHolder`).
*/
function balanceOf(address tokenHolder) public view returns (uint256) {
return _balances[tokenHolder];
}
/**
* @dev See {IERC777-send}.
*
* Also emits a {IERC20-Transfer} event for ERC20 compatibility.
*/
function send(address recipient, uint256 amount, bytes memory data) public {
_send(_msgSender(), _msgSender(), recipient, amount, data, "", true);
}
/**
* @dev See {IERC20-transfer}.
*
* Unlike `send`, `recipient` is _not_ required to implement the {IERC777Recipient}
* interface if it is a contract.
*
* Also emits a {Sent} event.
*/
function transfer(address recipient, uint256 amount) public returns (bool) {
require(recipient != address(0), "ERC777: transfer to the zero address");
address from = _msgSender();
_callTokensToSend(from, from, recipient, amount, "", "");
_move(from, from, recipient, amount, "", "");
_callTokensReceived(from, from, recipient, amount, "", "", false);
return true;
}
/**
* @dev See {IERC777-burn}.
*
* Also emits a {IERC20-Transfer} event for ERC20 compatibility.
*/
function burn(uint256 amount, bytes memory data) public {
_burn(_msgSender(), _msgSender(), amount, data, "");
}
/**
* @dev See {IERC777-isOperatorFor}.
*/
function isOperatorFor(
address operator,
address tokenHolder
) public view returns (bool) {
return operator == tokenHolder ||
(_defaultOperators[operator] && !_revokedDefaultOperators[tokenHolder][operator]) ||
_operators[tokenHolder][operator];
}
/**
* @dev See {IERC777-authorizeOperator}.
*/
function authorizeOperator(address operator) public {
require(_msgSender() != operator, "ERC777: authorizing self as operator");
if (_defaultOperators[operator]) {
delete _revokedDefaultOperators[_msgSender()][operator];
} else {
_operators[_msgSender()][operator] = true;
}
emit AuthorizedOperator(operator, _msgSender());
}
/**
* @dev See {IERC777-revokeOperator}.
*/
function revokeOperator(address operator) public {
require(operator != _msgSender(), "ERC777: revoking self as operator");
if (_defaultOperators[operator]) {
_revokedDefaultOperators[_msgSender()][operator] = true;
} else {
delete _operators[_msgSender()][operator];
}
emit RevokedOperator(operator, _msgSender());
}
/**
* @dev See {IERC777-defaultOperators}.
*/
function defaultOperators() public view returns (address[] memory) {
return _defaultOperatorsArray;
}
/**
* @dev See {IERC777-operatorSend}.
*
* Emits {Sent} and {IERC20-Transfer} events.
*/
function operatorSend(
address sender,
address recipient,
uint256 amount,
bytes memory data,
bytes memory operatorData
)
public
{
require(isOperatorFor(_msgSender(), sender), "ERC777: caller is not an operator for holder");
_send(_msgSender(), sender, recipient, amount, data, operatorData, true);
}
/**
* @dev See {IERC777-operatorBurn}.
*
* Emits {Burned} and {IERC20-Transfer} events.
*/
function operatorBurn(address account, uint256 amount, bytes memory data, bytes memory operatorData) public {
require(isOperatorFor(_msgSender(), account), "ERC777: caller is not an operator for holder");
_burn(_msgSender(), account, amount, data, operatorData);
}
/**
* @dev See {IERC20-allowance}.
*
* Note that operator and allowance concepts are orthogonal: operators may
* not have allowance, and accounts with allowance may not be operators
* themselves.
*/
function allowance(address holder, address spender) public view returns (uint256) {
return _allowances[holder][spender];
}
/**
* @dev See {IERC20-approve}.
*
* Note that accounts cannot have allowance issued by their operators.
*/
function approve(address spender, uint256 value) public returns (bool) {
address holder = _msgSender();
_approve(holder, spender, value);
return true;
}
/**
* @dev See {IERC20-transferFrom}.
*
* Note that operator and allowance concepts are orthogonal: operators cannot
* call `transferFrom` (unless they have allowance), and accounts with
* allowance cannot call `operatorSend` (unless they are operators).
*
* Emits {Sent}, {IERC20-Transfer} and {IERC20-Approval} events.
*/
function transferFrom(address holder, address recipient, uint256 amount) public returns (bool) {
require(recipient != address(0), "ERC777: transfer to the zero address");
require(holder != address(0), "ERC777: transfer from the zero address");
address spender = _msgSender();
_callTokensToSend(spender, holder, recipient, amount, "", "");
_move(spender, holder, recipient, amount, "", "");
_approve(holder, spender, _allowances[holder][spender].sub(amount, "ERC777: transfer amount exceeds allowance"));
_callTokensReceived(spender, holder, recipient, amount, "", "", false);
return true;
}
/**
* @dev Creates `amount` tokens and assigns them to `account`, increasing
* the total supply.
*
* If a send hook is registered for `account`, the corresponding function
* will be called with `operator`, `data` and `operatorData`.
*
* See {IERC777Sender} and {IERC777Recipient}.
*
* Emits {Minted} and {IERC20-Transfer} events.
*
* Requirements
*
* - `account` cannot be the zero address.
* - if `account` is a contract, it must implement the {IERC777Recipient}
* interface.
*/
function _mint(
address operator,
address account,
uint256 amount,
bytes memory userData,
bytes memory operatorData
)
internal
{
require(account != address(0), "ERC777: mint to the zero address");
// Update state variables
_totalSupply = _totalSupply.add(amount);
_balances[account] = _balances[account].add(amount);
_callTokensReceived(operator, address(0), account, amount, userData, operatorData, true);
emit Minted(operator, account, amount, userData, operatorData);
emit Transfer(address(0), account, amount);
}
/**
* @dev Send tokens
* @param operator address operator requesting the transfer
* @param from address token holder address
* @param to address recipient address
* @param amount uint256 amount of tokens to transfer
* @param userData bytes extra information provided by the token holder (if any)
* @param operatorData bytes extra information provided by the operator (if any)
* @param requireReceptionAck if true, contract recipients are required to implement ERC777TokensRecipient
*/
function _send(
address operator,
address from,
address to,
uint256 amount,
bytes memory userData,
bytes memory operatorData,
bool requireReceptionAck
)
internal
{
require(operator != address(0), "ERC777: operator is the zero address");
require(from != address(0), "ERC777: send from the zero address");
require(to != address(0), "ERC777: send to the zero address");
_callTokensToSend(operator, from, to, amount, userData, operatorData);
_move(operator, from, to, amount, userData, operatorData);
_callTokensReceived(operator, from, to, amount, userData, operatorData, requireReceptionAck);
}
/**
* @dev Burn tokens
* @param operator address operator requesting the operation
* @param from address token holder address
* @param amount uint256 amount of tokens to burn
* @param data bytes extra information provided by the token holder
* @param operatorData bytes extra information provided by the operator (if any)
*/
function _burn(
address operator,
address from,
uint256 amount,
bytes memory data,
bytes memory operatorData
)
internal
{
require(from != address(0), "ERC777: burn from the zero address");
_callTokensToSend(operator, from, address(0), amount, data, operatorData);
// Update state variables
_balances[from] = _balances[from].sub(amount, "ERC777: burn amount exceeds balance");
_totalSupply = _totalSupply.sub(amount);
emit Burned(operator, from, amount, data, operatorData);
emit Transfer(from, address(0), amount);
}
function _move(
address operator,
address from,
address to,
uint256 amount,
bytes memory userData,
bytes memory operatorData
)
private
{
_balances[from] = _balances[from].sub(amount, "ERC777: transfer amount exceeds balance");
_balances[to] = _balances[to].add(amount);
emit Sent(operator, from, to, amount, userData, operatorData);
emit Transfer(from, to, amount);
}
/**
* @dev See {ERC20-_approve}.
*
* Note that accounts cannot have allowance issued by their operators.
*/
function _approve(address holder, address spender, uint256 value) internal {
require(holder != address(0), "ERC777: approve from the zero address");
require(spender != address(0), "ERC777: approve to the zero address");
_allowances[holder][spender] = value;
emit Approval(holder, spender, value);
}
/**
* @dev Call from.tokensToSend() if the interface is registered
* @param operator address operator requesting the transfer
* @param from address token holder address
* @param to address recipient address
* @param amount uint256 amount of tokens to transfer
* @param userData bytes extra information provided by the token holder (if any)
* @param operatorData bytes extra information provided by the operator (if any)
*/
function _callTokensToSend(
address operator,
address from,
address to,
uint256 amount,
bytes memory userData,
bytes memory operatorData
)
internal
{
address implementer = ERC1820_REGISTRY.getInterfaceImplementer(from, TOKENS_SENDER_INTERFACE_HASH);
if (implementer != address(0)) {
IERC777Sender(implementer).tokensToSend(operator, from, to, amount, userData, operatorData);
}
}
/**
* @dev Call to.tokensReceived() if the interface is registered. Reverts if the recipient is a contract but
* tokensReceived() was not registered for the recipient
* @param operator address operator requesting the transfer
* @param from address token holder address
* @param to address recipient address
* @param amount uint256 amount of tokens to transfer
* @param userData bytes extra information provided by the token holder (if any)
* @param operatorData bytes extra information provided by the operator (if any)
* @param requireReceptionAck if true, contract recipients are required to implement ERC777TokensRecipient
*/
function _callTokensReceived(
address operator,
address from,
address to,
uint256 amount,
bytes memory userData,
bytes memory operatorData,
bool requireReceptionAck
)
internal
{
address implementer = ERC1820_REGISTRY.getInterfaceImplementer(to, TOKENS_RECIPIENT_INTERFACE_HASH);
if (implementer != address(0)) {
IERC777Recipient(implementer).tokensReceived(operator, from, to, amount, userData, operatorData);
} else if (requireReceptionAck) {
require(!to.isContract(), "ERC777: token recipient contract has no implementer for ERC777TokensRecipient");
}
}
}
// File: contracts/AbstractOwnable.sol
pragma solidity ^0.5.0;
contract AbstractOwnable {
/**
* @dev Returns the address of the current owner.
*/
function owner() internal view returns (address);
/**
* @dev Throws if called by any account other than the owner.
*/
modifier onlyOwner() {
require(isOwner(), "Caller is not the owner");
_;
}
/**
* @dev Returns true if the caller is the current owner.
*/
function isOwner() internal view returns (bool) {
return msg.sender == owner();
}
}
// File: @openzeppelin/contracts/cryptography/ECDSA.sol
pragma solidity ^0.5.0;
/**
* @dev Elliptic Curve Digital Signature Algorithm (ECDSA) operations.
*
* These functions can be used to verify that a message was signed by the holder
* of the private keys of a given address.
*/
library ECDSA {
/**
* @dev Returns the address that signed a hashed message (`hash`) with
* `signature`. This address can then be used for verification purposes.
*
* The `ecrecover` EVM opcode allows for malleable (non-unique) signatures:
* this function rejects them by requiring the `s` value to be in the lower
* half order, and the `v` value to be either 27 or 28.
*
* NOTE: This call _does not revert_ if the signature is invalid, or
* if the signer is otherwise unable to be retrieved. In those scenarios,
* the zero address is returned.
*
* IMPORTANT: `hash` _must_ be the result of a hash operation for the
* verification to be secure: it is possible to craft signatures that
* recover to arbitrary addresses for non-hashed data. A safe way to ensure
* this is by receiving a hash of the original message (which may otherwise
* be too long), and then calling {toEthSignedMessageHash} on it.
*/
function recover(bytes32 hash, bytes memory signature) internal pure returns (address) {
// Check the signature length
if (signature.length != 65) {
return (address(0));
}
// Divide the signature in r, s and v variables
bytes32 r;
bytes32 s;
uint8 v;
// ecrecover takes the signature parameters, and the only way to get them
// currently is to use assembly.
// solhint-disable-next-line no-inline-assembly
assembly {
r := mload(add(signature, 0x20))
s := mload(add(signature, 0x40))
v := byte(0, mload(add(signature, 0x60)))
}
// EIP-2 still allows signature malleability for ecrecover(). Remove this possibility and make the signature
// unique. Appendix F in the Ethereum Yellow paper (https://ethereum.github.io/yellowpaper/paper.pdf), defines
// the valid range for s in (281): 0 < s < secp256k1n ÷ 2 + 1, and for v in (282): v ∈ {27, 28}. Most
// signatures from current libraries generate a unique signature with an s-value in the lower half order.
//
// If your library generates malleable signatures, such as s-values in the upper range, calculate a new s-value
// with 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - s1 and flip v from 27 to 28 or
// vice versa. If your library also generates signatures with 0/1 for v instead 27/28, add 27 to v to accept
// these malleable signatures as well.
if (uint256(s) > 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0) {
return address(0);
}
if (v != 27 && v != 28) {
return address(0);
}
// If the signature is valid (and not malleable), return the signer address
return ecrecover(hash, v, r, s);
}
/**
* @dev Returns an Ethereum Signed Message, created from a `hash`. This
* replicates the behavior of the
* https://github.com/ethereum/wiki/wiki/JSON-RPC#eth_sign[`eth_sign`]
* JSON-RPC method.
*
* See {recover}.
*/
function toEthSignedMessageHash(bytes32 hash) internal pure returns (bytes32) {
// 32 is the length in bytes of hash,
// enforced by the type signature above
return keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", hash));
}
}
// File: @openzeppelin/contracts/GSN/IRelayRecipient.sol
pragma solidity ^0.5.0;
/**
* @dev Base interface for a contract that will be called via the GSN from {IRelayHub}.
*
* TIP: You don't need to write an implementation yourself! Inherit from {GSNRecipient} instead.
*/
interface IRelayRecipient {
/**
* @dev Returns the address of the {IRelayHub} instance this recipient interacts with.
*/
function getHubAddr() external view returns (address);
/**
* @dev Called by {IRelayHub} to validate if this recipient accepts being charged for a relayed call. Note that the
* recipient will be charged regardless of the execution result of the relayed call (i.e. if it reverts or not).
*
* The relay request was originated by `from` and will be served by `relay`. `encodedFunction` is the relayed call
* calldata, so its first four bytes are the function selector. The relayed call will be forwarded `gasLimit` gas,
* and the transaction executed with a gas price of at least `gasPrice`. `relay`'s fee is `transactionFee`, and the
* recipient will be charged at most `maxPossibleCharge` (in wei). `nonce` is the sender's (`from`) nonce for
* replay attack protection in {IRelayHub}, and `approvalData` is a optional parameter that can be used to hold a signature
* over all or some of the previous values.
*
* Returns a tuple, where the first value is used to indicate approval (0) or rejection (custom non-zero error code,
* values 1 to 10 are reserved) and the second one is data to be passed to the other {IRelayRecipient} functions.
*
* {acceptRelayedCall} is called with 50k gas: if it runs out during execution, the request will be considered
* rejected. A regular revert will also trigger a rejection.
*/
function acceptRelayedCall(
address relay,
address from,
bytes calldata encodedFunction,
uint256 transactionFee,
uint256 gasPrice,
uint256 gasLimit,
uint256 nonce,
bytes calldata approvalData,
uint256 maxPossibleCharge
)
external
view
returns (uint256, bytes memory);
/**
* @dev Called by {IRelayHub} on approved relay call requests, before the relayed call is executed. This allows to e.g.
* pre-charge the sender of the transaction.
*
* `context` is the second value returned in the tuple by {acceptRelayedCall}.
*
* Returns a value to be passed to {postRelayedCall}.
*
* {preRelayedCall} is called with 100k gas: if it runs out during exection or otherwise reverts, the relayed call
* will not be executed, but the recipient will still be charged for the transaction's cost.
*/
function preRelayedCall(bytes calldata context) external returns (bytes32);
/**
* @dev Called by {IRelayHub} on approved relay call requests, after the relayed call is executed. This allows to e.g.
* charge the user for the relayed call costs, return any overcharges from {preRelayedCall}, or perform
* contract-specific bookkeeping.
*
* `context` is the second value returned in the tuple by {acceptRelayedCall}. `success` is the execution status of
* the relayed call. `actualCharge` is an estimate of how much the recipient will be charged for the transaction,
* not including any gas used by {postRelayedCall} itself. `preRetVal` is {preRelayedCall}'s return value.
*
*
* {postRelayedCall} is called with 100k gas: if it runs out during execution or otherwise reverts, the relayed call
* and the call to {preRelayedCall} will be reverted retroactively, but the recipient will still be charged for the
* transaction's cost.
*/
function postRelayedCall(bytes calldata context, bool success, uint256 actualCharge, bytes32 preRetVal) external;
}
// File: @openzeppelin/contracts/GSN/IRelayHub.sol
pragma solidity ^0.5.0;
/**
* @dev Interface for `RelayHub`, the core contract of the GSN. Users should not need to interact with this contract
* directly.
*
* See the https://github.com/OpenZeppelin/openzeppelin-gsn-helpers[OpenZeppelin GSN helpers] for more information on
* how to deploy an instance of `RelayHub` on your local test network.
*/
interface IRelayHub {
// Relay management
/**
* @dev Adds stake to a relay and sets its `unstakeDelay`. If the relay does not exist, it is created, and the caller
* of this function becomes its owner. If the relay already exists, only the owner can call this function. A relay
* cannot be its own owner.
*
* All Ether in this function call will be added to the relay's stake.
* Its unstake delay will be assigned to `unstakeDelay`, but the new value must be greater or equal to the current one.
*
* Emits a {Staked} event.
*/
function stake(address relayaddr, uint256 unstakeDelay) external payable;
/**
* @dev Emitted when a relay's stake or unstakeDelay are increased
*/
event Staked(address indexed relay, uint256 stake, uint256 unstakeDelay);
/**
* @dev Registers the caller as a relay.
* The relay must be staked for, and not be a contract (i.e. this function must be called directly from an EOA).
*
* This function can be called multiple times, emitting new {RelayAdded} events. Note that the received
* `transactionFee` is not enforced by {relayCall}.
*
* Emits a {RelayAdded} event.
*/
function registerRelay(uint256 transactionFee, string calldata url) external;
/**
* @dev Emitted when a relay is registered or re-registerd. Looking at these events (and filtering out
* {RelayRemoved} events) lets a client discover the list of available relays.
*/
event RelayAdded(address indexed relay, address indexed owner, uint256 transactionFee, uint256 stake, uint256 unstakeDelay, string url);
/**
* @dev Removes (deregisters) a relay. Unregistered (but staked for) relays can also be removed.
*
* Can only be called by the owner of the relay. After the relay's `unstakeDelay` has elapsed, {unstake} will be
* callable.
*
* Emits a {RelayRemoved} event.
*/
function removeRelayByOwner(address relay) external;
/**
* @dev Emitted when a relay is removed (deregistered). `unstakeTime` is the time when unstake will be callable.
*/
event RelayRemoved(address indexed relay, uint256 unstakeTime);
/** Deletes the relay from the system, and gives back its stake to the owner.
*
* Can only be called by the relay owner, after `unstakeDelay` has elapsed since {removeRelayByOwner} was called.
*
* Emits an {Unstaked} event.
*/
function unstake(address relay) external;
/**
* @dev Emitted when a relay is unstaked for, including the returned stake.
*/
event Unstaked(address indexed relay, uint256 stake);
// States a relay can be in
enum RelayState {
Unknown, // The relay is unknown to the system: it has never been staked for
Staked, // The relay has been staked for, but it is not yet active
Registered, // The relay has registered itself, and is active (can relay calls)
Removed // The relay has been removed by its owner and can no longer relay calls. It must wait for its unstakeDelay to elapse before it can unstake
}
/**
* @dev Returns a relay's status. Note that relays can be deleted when unstaked or penalized, causing this function
* to return an empty entry.
*/
function getRelay(address relay) external view returns (uint256 totalStake, uint256 unstakeDelay, uint256 unstakeTime, address payable owner, RelayState state);
// Balance management
/**
* @dev Deposits Ether for a contract, so that it can receive (and pay for) relayed transactions.
*
* Unused balance can only be withdrawn by the contract itself, by calling {withdraw}.
*
* Emits a {Deposited} event.
*/
function depositFor(address target) external payable;
/**
* @dev Emitted when {depositFor} is called, including the amount and account that was funded.
*/
event Deposited(address indexed recipient, address indexed from, uint256 amount);
/**
* @dev Returns an account's deposits. These can be either a contracts's funds, or a relay owner's revenue.
*/
function balanceOf(address target) external view returns (uint256);
/**
* Withdraws from an account's balance, sending it back to it. Relay owners call this to retrieve their revenue, and
* contracts can use it to reduce their funding.
*
* Emits a {Withdrawn} event.
*/
function withdraw(uint256 amount, address payable dest) external;
/**
* @dev Emitted when an account withdraws funds from `RelayHub`.
*/
event Withdrawn(address indexed account, address indexed dest, uint256 amount);
// Relaying
/**
* @dev Checks if the `RelayHub` will accept a relayed operation.
* Multiple things must be true for this to happen:
* - all arguments must be signed for by the sender (`from`)
* - the sender's nonce must be the current one
* - the recipient must accept this transaction (via {acceptRelayedCall})
*
* Returns a `PreconditionCheck` value (`OK` when the transaction can be relayed), or a recipient-specific error
* code if it returns one in {acceptRelayedCall}.
*/
function canRelay(
address relay,
address from,
address to,
bytes calldata encodedFunction,
uint256 transactionFee,
uint256 gasPrice,
uint256 gasLimit,
uint256 nonce,
bytes calldata signature,
bytes calldata approvalData
) external view returns (uint256 status, bytes memory recipientContext);
// Preconditions for relaying, checked by canRelay and returned as the corresponding numeric values.
enum PreconditionCheck {
OK, // All checks passed, the call can be relayed
WrongSignature, // The transaction to relay is not signed by requested sender
WrongNonce, // The provided nonce has already been used by the sender
AcceptRelayedCallReverted, // The recipient rejected this call via acceptRelayedCall
InvalidRecipientStatusCode // The recipient returned an invalid (reserved) status code
}
/**
* @dev Relays a transaction.
*
* For this to succeed, multiple conditions must be met:
* - {canRelay} must `return PreconditionCheck.OK`
* - the sender must be a registered relay
* - the transaction's gas price must be larger or equal to the one that was requested by the sender
* - the transaction must have enough gas to not run out of gas if all internal transactions (calls to the
* recipient) use all gas available to them
* - the recipient must have enough balance to pay the relay for the worst-case scenario (i.e. when all gas is
* spent)
*
* If all conditions are met, the call will be relayed and the recipient charged. {preRelayedCall}, the encoded
* function and {postRelayedCall} will be called in that order.
*
* Parameters:
* - `from`: the client originating the request
* - `to`: the target {IRelayRecipient} contract
* - `encodedFunction`: the function call to relay, including data
* - `transactionFee`: fee (%) the relay takes over actual gas cost
* - `gasPrice`: gas price the client is willing to pay
* - `gasLimit`: gas to forward when calling the encoded function
* - `nonce`: client's nonce
* - `signature`: client's signature over all previous params, plus the relay and RelayHub addresses
* - `approvalData`: dapp-specific data forwared to {acceptRelayedCall}. This value is *not* verified by the
* `RelayHub`, but it still can be used for e.g. a signature.
*
* Emits a {TransactionRelayed} event.
*/
function relayCall(
address from,
address to,
bytes calldata encodedFunction,
uint256 transactionFee,
uint256 gasPrice,
uint256 gasLimit,
uint256 nonce,
bytes calldata signature,
bytes calldata approvalData
) external;
/**
* @dev Emitted when an attempt to relay a call failed.
*
* This can happen due to incorrect {relayCall} arguments, or the recipient not accepting the relayed call. The
* actual relayed call was not executed, and the recipient not charged.
*
* The `reason` parameter contains an error code: values 1-10 correspond to `PreconditionCheck` entries, and values
* over 10 are custom recipient error codes returned from {acceptRelayedCall}.
*/
event CanRelayFailed(address indexed relay, address indexed from, address indexed to, bytes4 selector, uint256 reason);
/**
* @dev Emitted when a transaction is relayed.
* Useful when monitoring a relay's operation and relayed calls to a contract
*
* Note that the actual encoded function might be reverted: this is indicated in the `status` parameter.
*
* `charge` is the Ether value deducted from the recipient's balance, paid to the relay's owner.
*/
event TransactionRelayed(address indexed relay, address indexed from, address indexed to, bytes4 selector, RelayCallStatus status, uint256 charge);
// Reason error codes for the TransactionRelayed event
enum RelayCallStatus {
OK, // The transaction was successfully relayed and execution successful - never included in the event
RelayedCallFailed, // The transaction was relayed, but the relayed call failed
PreRelayedFailed, // The transaction was not relayed due to preRelatedCall reverting
PostRelayedFailed, // The transaction was relayed and reverted due to postRelatedCall reverting
RecipientBalanceChanged // The transaction was relayed and reverted due to the recipient's balance changing
}
/**
* @dev Returns how much gas should be forwarded to a call to {relayCall}, in order to relay a transaction that will
* spend up to `relayedCallStipend` gas.
*/
function requiredGas(uint256 relayedCallStipend) external view returns (uint256);
/**
* @dev Returns the maximum recipient charge, given the amount of gas forwarded, gas price and relay fee.
*/
function maxPossibleCharge(uint256 relayedCallStipend, uint256 gasPrice, uint256 transactionFee) external view returns (uint256);
// Relay penalization.
// Any account can penalize relays, removing them from the system immediately, and rewarding the
// reporter with half of the relay's stake. The other half is burned so that, even if the relay penalizes itself, it
// still loses half of its stake.
/**
* @dev Penalize a relay that signed two transactions using the same nonce (making only the first one valid) and
* different data (gas price, gas limit, etc. may be different).
*
* The (unsigned) transaction data and signature for both transactions must be provided.
*/
function penalizeRepeatedNonce(bytes calldata unsignedTx1, bytes calldata signature1, bytes calldata unsignedTx2, bytes calldata signature2) external;
/**
* @dev Penalize a relay that sent a transaction that didn't target `RelayHub`'s {registerRelay} or {relayCall}.
*/
function penalizeIllegalTransaction(bytes calldata unsignedTx, bytes calldata signature) external;
/**
* @dev Emitted when a relay is penalized.
*/
event Penalized(address indexed relay, address sender, uint256 amount);
/**
* @dev Returns an account's nonce in `RelayHub`.
*/
function getNonce(address from) external view returns (uint256);
}
// File: @openzeppelin/contracts/GSN/GSNRecipient.sol
pragma solidity ^0.5.0;
/**
* @dev Base GSN recipient contract: includes the {IRelayRecipient} interface
* and enables GSN support on all contracts in the inheritance tree.
*
* TIP: This contract is abstract. The functions {IRelayRecipient-acceptRelayedCall},
* {_preRelayedCall}, and {_postRelayedCall} are not implemented and must be
* provided by derived contracts. See the
* xref:ROOT:gsn-strategies.adoc#gsn-strategies[GSN strategies] for more
* information on how to use the pre-built {GSNRecipientSignature} and
* {GSNRecipientERC20Fee}, or how to write your own.
*/
contract GSNRecipient is IRelayRecipient, Context {
// Default RelayHub address, deployed on mainnet and all testnets at the same address
address private _relayHub = 0xD216153c06E857cD7f72665E0aF1d7D82172F494;
uint256 constant private RELAYED_CALL_ACCEPTED = 0;
uint256 constant private RELAYED_CALL_REJECTED = 11;
// How much gas is forwarded to postRelayedCall
uint256 constant internal POST_RELAYED_CALL_MAX_GAS = 100000;
/**
* @dev Emitted when a contract changes its {IRelayHub} contract to a new one.
*/
event RelayHubChanged(address indexed oldRelayHub, address indexed newRelayHub);
/**
* @dev Returns the address of the {IRelayHub} contract for this recipient.
*/
function getHubAddr() public view returns (address) {
return _relayHub;
}
/**
* @dev Switches to a new {IRelayHub} instance. This method is added for future-proofing: there's no reason to not
* use the default instance.
*
* IMPORTANT: After upgrading, the {GSNRecipient} will no longer be able to receive relayed calls from the old
* {IRelayHub} instance. Additionally, all funds should be previously withdrawn via {_withdrawDeposits}.
*/
function _upgradeRelayHub(address newRelayHub) internal {
address currentRelayHub = _relayHub;
require(newRelayHub != address(0), "GSNRecipient: new RelayHub is the zero address");
require(newRelayHub != currentRelayHub, "GSNRecipient: new RelayHub is the current one");
emit RelayHubChanged(currentRelayHub, newRelayHub);
_relayHub = newRelayHub;
}
/**
* @dev Returns the version string of the {IRelayHub} for which this recipient implementation was built. If
* {_upgradeRelayHub} is used, the new {IRelayHub} instance should be compatible with this version.
*/
// This function is view for future-proofing, it may require reading from
// storage in the future.
function relayHubVersion() public view returns (string memory) {
this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691
return "1.0.0";
}
/**
* @dev Withdraws the recipient's deposits in `RelayHub`.
*
* Derived contracts should expose this in an external interface with proper access control.
*/
function _withdrawDeposits(uint256 amount, address payable payee) internal {
IRelayHub(_relayHub).withdraw(amount, payee);
}
// Overrides for Context's functions: when called from RelayHub, sender and
// data require some pre-processing: the actual sender is stored at the end
// of the call data, which in turns means it needs to be removed from it
// when handling said data.
/**
* @dev Replacement for msg.sender. Returns the actual sender of a transaction: msg.sender for regular transactions,
* and the end-user for GSN relayed calls (where msg.sender is actually `RelayHub`).
*
* IMPORTANT: Contracts derived from {GSNRecipient} should never use `msg.sender`, and use {_msgSender} instead.
*/
function _msgSender() internal view returns (address payable) {
if (msg.sender != _relayHub) {
return msg.sender;
} else {
return _getRelayedCallSender();
}
}
/**
* @dev Replacement for msg.data. Returns the actual calldata of a transaction: msg.data for regular transactions,
* and a reduced version for GSN relayed calls (where msg.data contains additional information).
*
* IMPORTANT: Contracts derived from {GSNRecipient} should never use `msg.data`, and use {_msgData} instead.
*/
function _msgData() internal view returns (bytes memory) {
if (msg.sender != _relayHub) {
return msg.data;
} else {
return _getRelayedCallData();
}
}
// Base implementations for pre and post relayedCall: only RelayHub can invoke them, and data is forwarded to the
// internal hook.
/**
* @dev See `IRelayRecipient.preRelayedCall`.
*
* This function should not be overriden directly, use `_preRelayedCall` instead.
*
* * Requirements:
*
* - the caller must be the `RelayHub` contract.
*/
function preRelayedCall(bytes calldata context) external returns (bytes32) {
require(msg.sender == getHubAddr(), "GSNRecipient: caller is not RelayHub");
return _preRelayedCall(context);
}
/**
* @dev See `IRelayRecipient.preRelayedCall`.
*
* Called by `GSNRecipient.preRelayedCall`, which asserts the caller is the `RelayHub` contract. Derived contracts
* must implement this function with any relayed-call preprocessing they may wish to do.
*
*/
function _preRelayedCall(bytes memory context) internal returns (bytes32);
/**
* @dev See `IRelayRecipient.postRelayedCall`.
*
* This function should not be overriden directly, use `_postRelayedCall` instead.
*
* * Requirements:
*
* - the caller must be the `RelayHub` contract.
*/
function postRelayedCall(bytes calldata context, bool success, uint256 actualCharge, bytes32 preRetVal) external {
require(msg.sender == getHubAddr(), "GSNRecipient: caller is not RelayHub");
_postRelayedCall(context, success, actualCharge, preRetVal);
}
/**
* @dev See `IRelayRecipient.postRelayedCall`.
*
* Called by `GSNRecipient.postRelayedCall`, which asserts the caller is the `RelayHub` contract. Derived contracts
* must implement this function with any relayed-call postprocessing they may wish to do.
*
*/
function _postRelayedCall(bytes memory context, bool success, uint256 actualCharge, bytes32 preRetVal) internal;
/**
* @dev Return this in acceptRelayedCall to proceed with the execution of a relayed call. Note that this contract
* will be charged a fee by RelayHub
*/
function _approveRelayedCall() internal pure returns (uint256, bytes memory) {
return _approveRelayedCall("");
}
/**
* @dev See `GSNRecipient._approveRelayedCall`.
*
* This overload forwards `context` to _preRelayedCall and _postRelayedCall.
*/
function _approveRelayedCall(bytes memory context) internal pure returns (uint256, bytes memory) {
return (RELAYED_CALL_ACCEPTED, context);
}
/**
* @dev Return this in acceptRelayedCall to impede execution of a relayed call. No fees will be charged.
*/
function _rejectRelayedCall(uint256 errorCode) internal pure returns (uint256, bytes memory) {
return (RELAYED_CALL_REJECTED + errorCode, "");
}
/*
* @dev Calculates how much RelayHub will charge a recipient for using `gas` at a `gasPrice`, given a relayer's
* `serviceFee`.
*/
function _computeCharge(uint256 gas, uint256 gasPrice, uint256 serviceFee) internal pure returns (uint256) {
// The fee is expressed as a percentage. E.g. a value of 40 stands for a 40% fee, so the recipient will be
// charged for 1.4 times the spent amount.
return (gas * gasPrice * (100 + serviceFee)) / 100;
}
function _getRelayedCallSender() private pure returns (address payable result) {
// We need to read 20 bytes (an address) located at array index msg.data.length - 20. In memory, the array
// is prefixed with a 32-byte length value, so we first add 32 to get the memory read index. However, doing
// so would leave the address in the upper 20 bytes of the 32-byte word, which is inconvenient and would
// require bit shifting. We therefore subtract 12 from the read index so the address lands on the lower 20
// bytes. This can always be done due to the 32-byte prefix.
// The final memory read index is msg.data.length - 20 + 32 - 12 = msg.data.length. Using inline assembly is the
// easiest/most-efficient way to perform this operation.
// These fields are not accessible from assembly
bytes memory array = msg.data;
uint256 index = msg.data.length;
// solhint-disable-next-line no-inline-assembly
assembly {
// Load the 32 bytes word from memory with the address on the lower 20 bytes, and mask those.
result := and(mload(add(array, index)), 0xffffffffffffffffffffffffffffffffffffffff)
}
return result;
}
function _getRelayedCallData() private pure returns (bytes memory) {
// RelayHub appends the sender address at the end of the calldata, so in order to retrieve the actual msg.data,
// we must strip the last 20 bytes (length of an address type) from it.
uint256 actualDataLength = msg.data.length - 20;
bytes memory actualData = new bytes(actualDataLength);
for (uint256 i = 0; i < actualDataLength; ++i) {
actualData[i] = msg.data[i];
}
return actualData;
}
}
// File: contracts/ERC777GSN.sol
pragma solidity ^0.5.0;
contract ERC777GSN is AbstractOwnable, GSNRecipient, ERC777 {
using ECDSA for bytes32;
uint256 constant GSN_RATE_UNIT = 10**18;
enum GSNErrorCodes {
INVALID_SIGNER,
INSUFFICIENT_BALANCE
}
address public gsnTrustedSigner;
address public gsnFeeTarget;
uint256 public gsnExtraGas = 40000; // the gas cost of _postRelayedCall()
constructor(
address _gsnTrustedSigner,
address _gsnFeeTarget
)
public
{
require(_gsnTrustedSigner != address(0), "trusted signer is the zero address");
gsnTrustedSigner = _gsnTrustedSigner;
require(_gsnFeeTarget != address(0), "fee target is the zero address");
gsnFeeTarget = _gsnFeeTarget;
}
function _msgSender() internal view returns (address payable) {
return GSNRecipient._msgSender();
}
function _msgData() internal view returns (bytes memory) {
return GSNRecipient._msgData();
}
function setTrustedSigner(address _gsnTrustedSigner) public onlyOwner {
require(_gsnTrustedSigner != address(0), "trusted signer is the zero address");
gsnTrustedSigner = _gsnTrustedSigner;
}
function setFeeTarget(address _gsnFeeTarget) public onlyOwner {
require(_gsnFeeTarget != address(0), "fee target is the zero address");
gsnFeeTarget = _gsnFeeTarget;
}
function setGSNExtraGas(uint _gsnExtraGas) public onlyOwner {
gsnExtraGas = _gsnExtraGas;
}
/**
* @dev Ensures that only transactions with a trusted signature can be relayed through the GSN.
*/
function acceptRelayedCall(
address relay,
address from,
bytes memory encodedFunction,
uint256 transactionFee,
uint256 gasPrice,
uint256 gasLimit,
uint256 nonce,
bytes memory approvalData,
uint256 /* maxPossibleCharge */
)
public
view
returns (uint256, bytes memory)
{
(uint256 feeRate, bytes memory signature) = abi.decode(approvalData, (uint, bytes));
bytes memory blob = abi.encodePacked(
feeRate,
relay,
from,
encodedFunction,
transactionFee,
gasPrice,
gasLimit,
nonce, // Prevents replays on RelayHub
getHubAddr(), // Prevents replays in multiple RelayHubs
address(this) // Prevents replays in multiple recipients
);
if (keccak256(blob).toEthSignedMessageHash().recover(signature) == gsnTrustedSigner) {
return _approveRelayedCall(abi.encode(feeRate, from, transactionFee, gasPrice));
} else {
return _rejectRelayedCall(uint256(GSNErrorCodes.INVALID_SIGNER));
}
}
function _preRelayedCall(bytes memory context) internal returns (bytes32) {}
function _postRelayedCall(bytes memory context, bool, uint256 actualCharge, bytes32) internal {
(uint256 feeRate, address from, uint256 transactionFee, uint256 gasPrice) =
abi.decode(context, (uint256, address, uint256, uint256));
// actualCharge is an _estimated_ charge, which assumes postRelayedCall will use all available gas.
// This implementation's gas cost can be roughly estimated as 10k gas, for the two SSTORE operations in an
// ERC20 transfer.
uint256 overestimation = _computeCharge(POST_RELAYED_CALL_MAX_GAS.sub(gsnExtraGas), gasPrice, transactionFee);
uint fee = actualCharge.sub(overestimation).mul(feeRate).div(GSN_RATE_UNIT);
if (fee > 0) {
_send(_msgSender(), from, gsnFeeTarget, fee, "", "", false);
}
}
}
// File: contracts/ERC777WithAdminOperator.sol
pragma solidity ^0.5.0;
contract ERC777WithAdminOperator is ERC777 {
address public adminOperator;
event AdminOperatorChange(address oldOperator, address newOperator);
event AdminTransferInvoked(address operator);
constructor(address _adminOperator) public {
adminOperator = _adminOperator;
}
/**
* @dev Similar to {IERC777-operatorSend}.
*
* Emits {Sent} and {IERC20-Transfer} events.
*/
function adminTransfer(
address sender,
address recipient,
uint256 amount,
bytes memory data,
bytes memory operatorData
)
public
{
require(_msgSender() == adminOperator, "caller is not the admin operator");
_send(adminOperator, sender, recipient, amount, data, operatorData, false);
emit AdminTransferInvoked(adminOperator);
}
/**
* @dev Only the actual admin operator can change the address
*/
function setAdminOperator(address adminOperator_) public {
require(msg.sender == adminOperator, "Only the actual admin operator can change the address");
emit AdminOperatorChange(adminOperator, adminOperator_);
adminOperator = adminOperator_;
}
}
// File: contracts/ERC777OptionalAckOnMint.sol
pragma solidity ^0.5.0;
contract ERC777OptionalAckOnMint is ERC777 {
bytes32 constant private TOKENS_RECIPIENT_INTERFACE_HASH =
0xb281fc8c12954d22544db45de3159a39272895b169a852b314f9cc762e44c53b;
/**
* @dev Call to.tokensReceived() if the interface is registered. Reverts if the recipient is a contract but
* tokensReceived() was not registered for the recipient
* @param operator address operator requesting the transfer
* @param from address token holder address
* @param to address recipient address
* @param amount uint256 amount of tokens to transfer
* @param userData bytes extra information provided by the token holder (if any)
* @param operatorData bytes extra information provided by the operator (if any)
* @param requireReceptionAck if true, contract recipients are required to implement ERC777TokensRecipient
*/
function _callTokensReceived(
address operator,
address from,
address to,
uint256 amount,
bytes memory userData,
bytes memory operatorData,
bool requireReceptionAck
)
internal
{
address implementer = ERC1820_REGISTRY.getInterfaceImplementer(to, TOKENS_RECIPIENT_INTERFACE_HASH);
if (implementer != address(0)) {
IERC777Recipient(implementer).tokensReceived(operator, from, to, amount, userData, operatorData);
} else if (requireReceptionAck && from != address(0)) {
require(!to.isContract(), "ERC777: token recipient contract has no implementer for ERC777TokensRecipient");
}
}
}
// File: contracts/pToken.sol
pragma solidity ^0.5.0;
contract PToken is
AbstractOwnable,
ERC777,
ERC777OptionalAckOnMint,
ERC777GSN,
ERC777WithAdminOperator
{
address public pNetwork;
event Redeem(
address indexed redeemer,
uint256 value,
string underlyingAssetRecipient
);
constructor(
string memory tokenName,
string memory tokenSymbol,
address[] memory defaultOperators
)
ERC777(tokenName, tokenSymbol, defaultOperators)
ERC777GSN(msg.sender, msg.sender)
ERC777WithAdminOperator(msg.sender)
public
{
pNetwork = _msgSender();
}
function owner() internal view returns (address) {
return pNetwork;
}
function changePNetwork(
address newPNetwork
)
external
{
require(
_msgSender() == pNetwork,
"Only the pNetwork can change the `pNetwork` account!"
);
require(
newPNetwork != address(0),
"pNetwork cannot be the zero address!"
);
pNetwork = newPNetwork;
}
function mint(
address recipient,
uint256 value
)
external
returns (bool)
{
mint(recipient, value, "", "");
return true;
}
function mint(
address recipient,
uint256 value,
bytes memory userData,
bytes memory operatorData
)
public
returns (bool)
{
require(
_msgSender() == pNetwork,
"Only the pNetwork can mint tokens!"
);
require(
recipient != address(0),
"pToken: Cannot mint to the zero address!"
);
_mint(pNetwork, recipient, value, userData, operatorData);
return true;
}
function redeem(
uint256 amount,
string calldata underlyingAssetRecipient
)
external
returns (bool)
{
redeem(amount, "", underlyingAssetRecipient);
return true;
}
function redeem(
uint256 amount,
bytes memory data,
string memory underlyingAssetRecipient
)
public
{
_burn(_msgSender(), _msgSender(), amount, data, "");
emit Redeem(msg.sender, amount, underlyingAssetRecipient);
}
function operatorRedeem(
address account,
uint256 amount,
bytes calldata data,
bytes calldata operatorData,
string calldata underlyingAssetRecipient
)
external
{
require(
isOperatorFor(_msgSender(), account),
"ERC777: caller is not an operator for holder"
);
_burn(_msgSender(), account, amount, data, operatorData);
emit Redeem(account, amount, underlyingAssetRecipient);
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"string","name":"tokenName","type":"string"},{"internalType":"string","name":"tokenSymbol","type":"string"},{"internalType":"address[]","name":"defaultOperators","type":"address[]"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"oldOperator","type":"address"},{"indexed":false,"internalType":"address","name":"newOperator","type":"address"}],"name":"AdminOperatorChange","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"operator","type":"address"}],"name":"AdminTransferInvoked","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"spender","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"tokenHolder","type":"address"}],"name":"AuthorizedOperator","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"data","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"Burned","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"data","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"Minted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"redeemer","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"},{"indexed":false,"internalType":"string","name":"underlyingAssetRecipient","type":"string"}],"name":"Redeem","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"oldRelayHub","type":"address"},{"indexed":true,"internalType":"address","name":"newRelayHub","type":"address"}],"name":"RelayHubChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"tokenHolder","type":"address"}],"name":"RevokedOperator","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"data","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"Sent","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"Transfer","type":"event"},{"constant":true,"inputs":[{"internalType":"address","name":"relay","type":"address"},{"internalType":"address","name":"from","type":"address"},{"internalType":"bytes","name":"encodedFunction","type":"bytes"},{"internalType":"uint256","name":"transactionFee","type":"uint256"},{"internalType":"uint256","name":"gasPrice","type":"uint256"},{"internalType":"uint256","name":"gasLimit","type":"uint256"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"bytes","name":"approvalData","type":"bytes"},{"internalType":"uint256","name":"","type":"uint256"}],"name":"acceptRelayedCall","outputs":[{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"bytes","name":"","type":"bytes"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"adminOperator","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"sender","type":"address"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"adminTransfer","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"holder","type":"address"},{"internalType":"address","name":"spender","type":"address"}],"name":"allowance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"spender","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"}],"name":"approve","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"operator","type":"address"}],"name":"authorizeOperator","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"tokenHolder","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"burn","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"newPNetwork","type":"address"}],"name":"changePNetwork","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"decimals","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[],"name":"defaultOperators","outputs":[{"internalType":"address[]","name":"","type":"address[]"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"getHubAddr","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"granularity","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"gsnExtraGas","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"gsnFeeTarget","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"gsnTrustedSigner","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"address","name":"tokenHolder","type":"address"}],"name":"isOperatorFor","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"}],"name":"mint","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"},{"internalType":"bytes","name":"userData","type":"bytes"},{"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"mint","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"account","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"operatorBurn","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"account","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"bytes","name":"operatorData","type":"bytes"},{"internalType":"string","name":"underlyingAssetRecipient","type":"string"}],"name":"operatorRedeem","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"sender","type":"address"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"bytes","name":"operatorData","type":"bytes"}],"name":"operatorSend","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"pNetwork","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes","name":"context","type":"bytes"},{"internalType":"bool","name":"success","type":"bool"},{"internalType":"uint256","name":"actualCharge","type":"uint256"},{"internalType":"bytes32","name":"preRetVal","type":"bytes32"}],"name":"postRelayedCall","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes","name":"context","type":"bytes"}],"name":"preRelayedCall","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"string","name":"underlyingAssetRecipient","type":"string"}],"name":"redeem","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"},{"internalType":"string","name":"underlyingAssetRecipient","type":"string"}],"name":"redeem","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"relayHubVersion","outputs":[{"internalType":"string","name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"operator","type":"address"}],"name":"revokeOperator","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"send","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"adminOperator_","type":"address"}],"name":"setAdminOperator","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_gsnFeeTarget","type":"address"}],"name":"setFeeTarget","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"uint256","name":"_gsnExtraGas","type":"uint256"}],"name":"setGSNExtraGas","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_gsnTrustedSigner","type":"address"}],"name":"setTrustedSigner","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transfer","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"holder","type":"address"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transferFrom","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"}]Contract Creation Code
608060405273d216153c06e857cd7f72665e0af1d7d82172f4946000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550619c40600c553480156200006b57600080fd5b50604051620064a5380380620064a5833981810160405260608110156200009157600080fd5b8101908080516040519392919084640100000000821115620000b257600080fd5b83820191506020820185811115620000c957600080fd5b8251866001820283011164010000000082111715620000e757600080fd5b8083526020830192505050908051906020019080838360005b838110156200011d57808201518184015260208101905062000100565b50505050905090810190601f1680156200014b5780820380516001836020036101000a031916815260200191505b50604052602001805160405193929190846401000000008211156200016f57600080fd5b838201915060208201858111156200018657600080fd5b8251866001820283011164010000000082111715620001a457600080fd5b8083526020830192505050908051906020019080838360005b83811015620001da578082015181840152602081019050620001bd565b50505050905090810190601f168015620002085780820380516001836020036101000a031916815260200191505b50604052602001805160405193929190846401000000008211156200022c57600080fd5b838201915060208201858111156200024357600080fd5b82518660208202830111640100000000821117156200026157600080fd5b8083526020830192505050908051906020019060200280838360005b838110156200029a5780820151818401526020810190506200027d565b505050509050016040525050503333338585858260039080519060200190620002c59291906200093f565b508160049080519060200190620002de9291906200093f565b508060059080519060200190620002f7929190620009c6565b5060008090505b600580549050811015620003aa57600160066000600584815481106200032057fe5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055508080600101915050620002fe565b50731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff166329965a1d3060405180807f455243373737546f6b656e000000000000000000000000000000000000000000815250600b0190506040518091039020306040518463ffffffff1660e01b8152600401808473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018381526020018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019350505050600060405180830381600087803b158015620004b057600080fd5b505af1158015620004c5573d6000803e3d6000fd5b50505050731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff166329965a1d3060405180807f4552433230546f6b656e00000000000000000000000000000000000000000000815250600a0190506040518091039020306040518463ffffffff1660e01b8152600401808473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018381526020018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019350505050600060405180830381600087803b158015620005ce57600080fd5b505af1158015620005e3573d6000803e3d6000fd5b50505050505050600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141562000672576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401808060200182810382526022815260200180620064836022913960400191505060405180910390fd5b81600a60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16141562000757576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252601e8152602001807f6665652074617267657420697320746865207a65726f2061646472657373000081525060200191505060405180910390fd5b80600b60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550505080600d60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050620007ec6200083560201b60201c565b600e60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050505062000ac3565b60006200084c6200085160201b620052341760201c565b905090565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614620008b157339050620008c4565b620008c1620008c760201b60201c565b90505b90565b600060606000368080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509050600080369050905073ffffffffffffffffffffffffffffffffffffffff81830151169250829250505090565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106200098257805160ff1916838001178555620009b3565b82800160010185558215620009b3579182015b82811115620009b257825182559160200191906001019062000995565b5b509050620009c2919062000a55565b5090565b82805482825590600052602060002090810192821562000a42579160200282015b8281111562000a415782518260006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555091602001919060010190620009e7565b5b50905062000a51919062000a7d565b5090565b62000a7a91905b8082111562000a7657600081600090555060010162000a5c565b5090565b90565b62000ac091905b8082111562000abc57600081816101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690555060010162000a84565b5090565b90565b6159b08062000ad36000396000f3fe608060405234801561001057600080fd5b506004361061023d5760003560e01c80639bd9bbc61161013b578063dc3ca1bf116100b8578063fad8b32a1161007c578063fad8b32a14611672578063fc673c4f146116b6578063fc87675414611832578063fd4add661461187c578063fe9d9303146118c05761023d565b8063dc3ca1bf1461133f578063dcdc7dd014611383578063dd62ed3e14611517578063e06e0e221461158f578063e900a491146116285761023d565b8063ca16814e116100ff578063ca16814e146110b5578063cbe1f06c146110ff578063ce67c0031461111d578063d95b637114611279578063dab02527146112f55761023d565b80639bd9bbc614610d1d5780639bf8d82f14610e02578063a9059cbb14610e30578063ad61ccd514610e96578063bcc33e9d14610f195761023d565b806340c10f19116101c957806374e861d61161018d57806374e861d61461093a57806380274db71461098457806383947ea014610a11578063959b8c3f14610c5657806395d89b4114610c9a5761023d565b806340c10f191461067e578063556f0dc7146106e457806356a1c7011461070257806362ad1b831461074657806370a08231146108e25761023d565b80631e9cee74116102105780631e9cee74146103a857806323b872dd146104f557806324b76fd51461057b578063313ce56714610616578063394f02311461063a5761023d565b806306e485381461024257806306fdde03146102a1578063095ea7b31461032457806318160ddd1461038a575b600080fd5b61024a611985565b6040518080602001828103825283818151815260200191508051906020019060200280838360005b8381101561028d578082015181840152602081019050610272565b505050509050019250505060405180910390f35b6102a9611a13565b6040518080602001828103825283818151815260200191508051906020019080838360005b838110156102e95780820151818401526020810190506102ce565b50505050905090810190601f1680156103165780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b6103706004803603604081101561033a57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050611ab5565b604051808215151515815260200191505060405180910390f35b610392611ad8565b6040518082815260200191505060405180910390f35b6104f3600480360360a08110156103be57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291908035906020019064010000000081111561040557600080fd5b82018360208201111561041757600080fd5b8035906020019184600183028401116401000000008311171561043957600080fd5b90919293919293908035906020019064010000000081111561045a57600080fd5b82018360208201111561046c57600080fd5b8035906020019184600183028401116401000000008311171561048e57600080fd5b9091929391929390803590602001906401000000008111156104af57600080fd5b8201836020820111156104c157600080fd5b803590602001918460018302840111640100000000831117156104e357600080fd5b9091929391929390505050611ae2565b005b6105616004803603606081101561050b57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050611c70565b604051808215151515815260200191505060405180910390f35b6105fc6004803603604081101561059157600080fd5b8101908080359060200190929190803590602001906401000000008111156105b857600080fd5b8201836020820111156105ca57600080fd5b803590602001918460018302840111640100000000831117156105ec57600080fd5b9091929391929390505050611ece565b604051808215151515815260200191505060405180910390f35b61061e611f39565b604051808260ff1660ff16815260200191505060405180910390f35b61067c6004803603602081101561065057600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050611f42565b005b6106ca6004803603604081101561069457600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291905050506120e5565b604051808215151515815260200191505060405180910390f35b6106ec61211c565b6040518082815260200191505060405180910390f35b6107446004803603602081101561071857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050612125565b005b6108e0600480360360a081101561075c57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190803590602001906401000000008111156107c357600080fd5b8201836020820111156107d557600080fd5b803590602001918460018302840111640100000000831117156107f757600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561085a57600080fd5b82018360208201111561086c57600080fd5b8035906020019184600183028401116401000000008311171561088e57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612269565b005b610924600480360360208110156108f857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506122ed565b6040518082815260200191505060405180910390f35b610942612336565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6109fb6004803603602081101561099a57600080fd5b81019080803590602001906401000000008111156109b757600080fd5b8201836020820111156109c957600080fd5b803590602001918460018302840111640100000000831117156109eb57600080fd5b909192939192939050505061235f565b6040518082815260200191505060405180910390f35b610bd46004803603610120811015610a2857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190640100000000811115610a8557600080fd5b820183602082011115610a9757600080fd5b80359060200191846001830284011164010000000083111715610ab957600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019092919080359060200190929190803590602001909291908035906020019092919080359060200190640100000000811115610b4457600080fd5b820183602082011115610b5657600080fd5b80359060200191846001830284011164010000000083111715610b7857600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050919291929080359060200190929190505050612441565b6040518083815260200180602001828103825283818151815260200191508051906020019080838360005b83811015610c1a578082015181840152602081019050610bff565b50505050905090810190601f168015610c475780820380516001836020036101000a031916815260200191505b50935050505060405180910390f35b610c9860048036036020811015610c6c57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506127bb565b005b610ca2612a32565b6040518080602001828103825283818151815260200191508051906020019080838360005b83811015610ce2578082015181840152602081019050610cc7565b50505050905090810190601f168015610d0f5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b610e0060048036036060811015610d3357600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919080359060200190640100000000811115610d7a57600080fd5b820183602082011115610d8c57600080fd5b80359060200191846001830284011164010000000083111715610dae57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612ad4565b005b610e2e60048036036020811015610e1857600080fd5b8101908080359060200190929190505050612b06565b005b610e7c60048036036040811015610e4657600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050612b8a565b604051808215151515815260200191505060405180910390f35b610e9e612cae565b6040518080602001828103825283818151815260200191508051906020019080838360005b83811015610ede578082015181840152602081019050610ec3565b50505050905090810190601f168015610f0b5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b6110b3600480360360a0811015610f2f57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919080359060200190640100000000811115610f9657600080fd5b820183602082011115610fa857600080fd5b80359060200191846001830284011164010000000083111715610fca57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561102d57600080fd5b82018360208201111561103f57600080fd5b8035906020019184600183028401116401000000008311171561106157600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612ceb565b005b6110bd612e73565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b611107612e99565b6040518082815260200191505060405180910390f35b6112776004803603606081101561113357600080fd5b81019080803590602001909291908035906020019064010000000081111561115a57600080fd5b82018360208201111561116c57600080fd5b8035906020019184600183028401116401000000008311171561118e57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290803590602001906401000000008111156111f157600080fd5b82018360208201111561120357600080fd5b8035906020019184600183028401116401000000008311171561122557600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612e9f565b005b6112db6004803603604081101561128f57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050612f89565b604051808215151515815260200191505060405180910390f35b6112fd61313a565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6113816004803603602081101561135557600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050613160565b005b6114fd6004803603608081101561139957600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190803590602001906401000000008111156113e057600080fd5b8201836020820111156113f257600080fd5b8035906020019184600183028401116401000000008311171561141457600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561147757600080fd5b82018360208201111561148957600080fd5b803590602001918460018302840111640100000000831117156114ab57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192905050506132c1565b604051808215151515815260200191505060405180910390f35b6115796004803603604081101561152d57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050613431565b6040518082815260200191505060405180910390f35b611626600480360360808110156115a557600080fd5b81019080803590602001906401000000008111156115c257600080fd5b8201836020820111156115d457600080fd5b803590602001918460018302840111640100000000831117156115f657600080fd5b909192939192939080351515906020019092919080359060200190929190803590602001909291905050506134b8565b005b61163061359a565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6116b46004803603602081101561168857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506135c0565b005b611830600480360360808110156116cc57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291908035906020019064010000000081111561171357600080fd5b82018360208201111561172557600080fd5b8035906020019184600183028401116401000000008311171561174757600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290803590602001906401000000008111156117aa57600080fd5b8201836020820111156117bc57600080fd5b803590602001918460018302840111640100000000831117156117de57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050613837565b005b61183a6138b7565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6118be6004803603602081101561189257600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506138dd565b005b611983600480360360408110156118d657600080fd5b8101908080359060200190929190803590602001906401000000008111156118fd57600080fd5b82018360208201111561190f57600080fd5b8035906020019184600183028401116401000000008311171561193157600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050613a54565b005b60606005805480602002602001604051908101604052809291908181526020018280548015611a0957602002820191906000526020600020905b8160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190600101908083116119bf575b5050505050905090565b606060038054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015611aab5780601f10611a8057610100808354040283529160200191611aab565b820191906000526020600020905b815481529060010190602001808311611a8e57829003601f168201915b5050505050905090565b600080611ac0613a82565b9050611acd818585613a91565b600191505092915050565b6000600254905090565b611af3611aed613a82565b89612f89565b611b48576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b611be4611b53613a82565b898989898080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505088888080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050613c88565b8773ffffffffffffffffffffffffffffffffffffffff167f78e6c3f67f57c26578f2487b930b70d844bcc8dd8f4d629fb4af81252ab5aa6588848460405180848152602001806020018281038252848482818152602001925080828437600081840152601f19601f82011690508083019250505094505050505060405180910390a25050505050505050565b60008073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415611cf7576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158736024913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415611d7d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260268152602001806159106026913960400191505060405180910390fd5b6000611d87613a82565b9050611db5818686866040518060200160405280600081525060405180602001604052806000815250613f93565b611de18186868660405180602001604052806000815250604051806020016040528060008152506142ad565b611e948582611e8f866040518060600160405280602981526020016158e760299139600960008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008873ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b613a91565b611ec28186868660405180602001604052806000815250604051806020016040528060008152506000614674565b60019150509392505050565b6000611f2e846040518060200160405280600081525085858080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050612e9f565b600190509392505050565b60006012905090565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614611fe8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260358152602001806157f16035913960400191505060405180910390fd5b7fe8fdc5340d9288e129a7c6af86dc4002f708091280d69f89583f7e6349c0a8d6600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1682604051808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019250505060405180910390a180600d60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6000612111838360405180602001604052806000815250604051806020016040528060008152506132c1565b506001905092915050565b60006001905090565b61212d614a48565b61219f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415612225576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806156a56022913960400191505060405180910390fd5b80600a60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b61227a612274613a82565b86612f89565b6122cf576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b6122e66122da613a82565b86868686866001614a85565b5050505050565b6000600160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020549050919050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6000612369612336565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146123ec576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158976024913960400191505060405180910390fd5b61243983838080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050614c68565b905092915050565b600060606000606085806020019051604081101561245e57600080fd5b81019080805190602001909291908051604051939291908464010000000082111561248857600080fd5b8382019150602082018581111561249e57600080fd5b82518660018202830111640100000000821117156124bb57600080fd5b8083526020830192505050908051906020019080838360005b838110156124ef5780820151818401526020810190506124d4565b50505050905090810190601f16801561251c5780820380516001836020036101000a031916815260200191505b50604052505050915091506060828e8e8e8e8e8e8e612539612336565b30604051602001808b81526020018a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014018973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b815260140188805190602001908083835b602083106125e057805182526020820191506020810190506020830392506125bd565b6001836020036101000a0380198251168184511680821785525050505050509050018781526020018681526020018581526020018481526020018373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014019a50505050505050505050506040516020818303038152906040529050600a60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff166126fc836126ee8480519060200120614c6f565b614cc790919063ffffffff16565b73ffffffffffffffffffffffffffffffffffffffff16141561279057612784838e8d8d604051602001808581526020018473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001838152602001828152602001945050505050604051602081830303815290604052614dcb565b945094505050506127ad565b6127a5600060018111156127a057fe5b614ddb565b945094505050505b995099975050505050505050565b8073ffffffffffffffffffffffffffffffffffffffff166127da613a82565b73ffffffffffffffffffffffffffffffffffffffff161415612847576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806156e96024913960400191505060405180910390fd5b600660008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff161561293157600860006128a5613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81549060ff02191690556129ce565b60016007600061293f613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055505b6129d6613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167ff4caeb2d6ca8932a215a353d0703c326ec2d81fc68170f320eb2ab49e9df61f960405160405180910390a350565b606060048054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015612aca5780601f10612a9f57610100808354040283529160200191612aca565b820191906000526020600020905b815481529060010190602001808311612aad57829003601f168201915b5050505050905090565b612b01612adf613a82565b612ae7613a82565b858585604051806020016040528060008152506001614a85565b505050565b612b0e614a48565b612b80576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b80600c8190555050565b60008073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612c11576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158736024913960400191505060405180910390fd5b6000612c1b613a82565b9050612c49818286866040518060200160405280600081525060405180602001604052806000815250613f93565b612c758182868660405180602001604052806000815250604051806020016040528060008152506142ad565b612ca38182868660405180602001604052806000815250604051806020016040528060008152506000614674565b600191505092915050565b60606040518060400160405280600581526020017f312e302e30000000000000000000000000000000000000000000000000000000815250905090565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16612d2c613a82565b73ffffffffffffffffffffffffffffffffffffffff1614612db5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f63616c6c6572206973206e6f74207468652061646d696e206f70657261746f7281525060200191505060405180910390fd5b612de7600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1686868686866000614a85565b7fb22a57ba0314fafe219dc14abcf1f22e86e6e82d599c0c31177a2d7c2e1b17e1600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390a15050505050565b600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600c5481565b612ec9612eaa613a82565b612eb2613a82565b858560405180602001604052806000815250613c88565b3373ffffffffffffffffffffffffffffffffffffffff167f78e6c3f67f57c26578f2487b930b70d844bcc8dd8f4d629fb4af81252ab5aa6584836040518083815260200180602001828103825283818151815260200191508051906020019080838360005b83811015612f49578082015181840152602081019050612f2e565b50505050905090810190601f168015612f765780820380516001836020036101000a031916815260200191505b50935050505060405180910390a2505050565b60008173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff1614806130a15750600660008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff1680156130a05750600860008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16155b5b806131325750600760008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff165b905092915050565b600b60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b613168614a48565b6131da576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16141561327d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252601e8152602001807f6665652074617267657420697320746865207a65726f2061646472657373000081525060200191505060405180910390fd5b80600b60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6000600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16613304613a82565b73ffffffffffffffffffffffffffffffffffffffff1614613370576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806157356022913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff1614156133f6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602881526020018061570d6028913960400191505060405180910390fd5b613425600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1686868686614dfc565b60019050949350505050565b6000600960008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054905092915050565b6134c0612336565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614613543576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158976024913960400191505060405180910390fd5b61359385858080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505084848461510c565b5050505050565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b6135c8613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16141561364c576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260218152602001806157576021913960400191505060405180910390fd5b600660008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff161561373f576001600860006136ac613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506137d3565b6007600061374b613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81549060ff02191690555b6137db613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f50546e66e5f44d728365dc3908c63bc5cfeeab470722c1677e3073a6ac294aa160405160405180910390a350565b613848613842613a82565b85612f89565b61389d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b6138b16138a8613a82565b85858585613c88565b50505050565b600a60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1661391e613a82565b73ffffffffffffffffffffffffffffffffffffffff161461398a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252603481526020018061579c6034913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415613a10576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806156136024913960400191505060405180910390fd5b80600e60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b613a7e613a5f613a82565b613a67613a82565b848460405180602001604052806000815250613c88565b5050565b6000613a8c615234565b905090565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415613b17576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260258152602001806156376025913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415613b9d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260238152602001806159596023913960400191505060405180910390fd5b80600960008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925836040518082815260200191505060405180910390a3505050565b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415613d0e576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806156c76022913960400191505060405180910390fd5b613d1d85856000868686613f93565b613d898360405180606001604052806023815260200161593660239139600160008873ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550613de1836002546152a090919063ffffffff16565b6002819055508373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167fa78a9be3a7b862d26933ad85fb11d80ef66b8f972d7cbba06621d583943a4098858585604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b83811015613e83578082015181840152602081019050613e68565b50505050905090810190601f168015613eb05780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b83811015613ee9578082015181840152602081019050613ece565b50505050905090810190601f168015613f165780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a3600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a35050505050565b6000731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff1663aabbb8ca877f29ddb589b1fb5fc7cf394961c1adf5f8c6454761adf795e67fe149f658abe89560001b6040518363ffffffff1660e01b8152600401808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018281526020019250505060206040518083038186803b15801561405157600080fd5b505afa158015614065573d6000803e3d6000fd5b505050506040513d602081101561407b57600080fd5b81019080805190602001909291905050509050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16146142a4578073ffffffffffffffffffffffffffffffffffffffff166375ab97828888888888886040518763ffffffff1660e01b8152600401808773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156141d35780820151818401526020810190506141b8565b50505050905090810190601f1680156142005780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b8381101561423957808201518184015260208101905061421e565b50505050905090810190601f1680156142665780820380516001836020036101000a031916815260200191505b5098505050505050505050600060405180830381600087803b15801561428b57600080fd5b505af115801561429f573d6000803e3d6000fd5b505050505b50505050505050565b6143198360405180606001604052806027815260200161567e60279139600160008973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506143ae83600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546152ea90919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167f06b541ddaa720db2b10a4d0cdac39b8d360425fc073085fac19bc82614677987868686604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156144a4578082015181840152602081019050614489565b50505050905090810190601f1680156144d15780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b8381101561450a5780820151818401526020810190506144ef565b50505050905090810190601f1680156145375780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a48373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a3505050505050565b6000838311158290614661576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561462657808201518184015260208101905061460b565b50505050905090810190601f1680156146535780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b5060008385039050809150509392505050565b6000731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff1663aabbb8ca877fb281fc8c12954d22544db45de3159a39272895b169a852b314f9cc762e44c53b60001b6040518363ffffffff1660e01b8152600401808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018281526020019250505060206040518083038186803b15801561473257600080fd5b505afa158015614746573d6000803e3d6000fd5b505050506040513d602081101561475c57600080fd5b81019080805190602001909291905050509050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614614988578073ffffffffffffffffffffffffffffffffffffffff166223de298989898989896040518763ffffffff1660e01b8152600401808773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156148b3578082015181840152602081019050614898565b50505050905090810190601f1680156148e05780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b838110156149195780820151818401526020810190506148fe565b50505050905090810190601f1680156149465780820380516001836020036101000a031916815260200191505b5098505050505050505050600060405180830381600087803b15801561496b57600080fd5b505af115801561497f573d6000803e3d6000fd5b50505050614a3e565b8180156149c25750600073ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff1614155b15614a3d576149e68673ffffffffffffffffffffffffffffffffffffffff16615372565b15614a3c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252604d815260200180615826604d913960600191505060405180910390fd5b5b5b5050505050505050565b6000614a526153bd565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614905090565b600073ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff161415614b0b576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806157786024913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168673ffffffffffffffffffffffffffffffffffffffff161415614b91576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602281526020018061565c6022913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415614c34576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f4552433737373a2073656e6420746f20746865207a65726f206164647265737381525060200191505060405180910390fd5b614c42878787878787613f93565b614c508787878787876142ad565b614c5f87878787878787614674565b50505050505050565b6000919050565b60008160405160200180807f19457468657265756d205369676e6564204d6573736167653a0a333200000000815250601c01828152602001915050604051602081830303815290604052805190602001209050919050565b60006041825114614cdb5760009050614dc5565b60008060006020850151925060408501519150606085015160001a90507f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a08260001c1115614d2f5760009350505050614dc5565b601b8160ff1614158015614d475750601c8160ff1614155b15614d585760009350505050614dc5565b60018682858560405160008152602001604052604051808581526020018460ff1660ff1681526020018381526020018281526020019450505050506020604051602081039080840390855afa158015614db5573d6000803e3d6000fd5b5050506020604051035193505050505b92915050565b6000606060008391509150915091565b6000606082600b016040518060200160405280600081525091509150915091565b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415614e9f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f4552433737373a206d696e7420746f20746865207a65726f206164647265737381525060200191505060405180910390fd5b614eb4836002546152ea90919063ffffffff16565b600281905550614f0c83600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546152ea90919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550614f60856000868686866001614674565b8373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167f2fe5be0146f74c5bce36c0b80911af6c7d86ff27e89d5cfa61fc681327954e5d858585604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b83811015614ffc578082015181840152602081019050614fe1565b50505050905090810190601f1680156150295780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b83811015615062578082015181840152602081019050615047565b50505050905090810190601f16801561508f5780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a38373ffffffffffffffffffffffffffffffffffffffff16600073ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a35050505050565b60008060008087806020019051608081101561512757600080fd5b81019080805190602001909291908051906020019092919080519060200190929190805190602001909291905050509350935093509350600061518261517b600c54620186a06152a090919063ffffffff16565b83856153e7565b905060006151c5670de0b6b3a76400006151b7886151a9868d6152a090919063ffffffff16565b61540490919063ffffffff16565b61548a90919063ffffffff16565b90506000811115615228576152276151db613a82565b86600b60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff168460405180602001604052806000815250604051806020016040528060008152506000614a85565b5b50505050505050505050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146152925733905061529d565b61529a6154d4565b90505b90565b60006152e283836040518060400160405280601e81526020017f536166654d6174683a207375627472616374696f6e206f766572666c6f7700008152506145b4565b905092915050565b600080828401905083811015615368576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252601b8152602001807f536166654d6174683a206164646974696f6e206f766572666c6f77000000000081525060200191505060405180910390fd5b8091505092915050565b60008060007fc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a47060001b9050833f91508082141580156153b457506000801b8214155b92505050919050565b6000600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b600060648260640184860202816153fa57fe5b0490509392505050565b6000808314156154175760009050615484565b600082840290508284828161542857fe5b041461547f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260218152602001806157d06021913960400191505060405180910390fd5b809150505b92915050565b60006154cc83836040518060400160405280601a81526020017f536166654d6174683a206469766973696f6e206279207a65726f00000000000081525061554c565b905092915050565b600060606000368080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509050600080369050905073ffffffffffffffffffffffffffffffffffffffff81830151169250829250505090565b600080831182906155f8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825283818151815260200191508051906020019080838360005b838110156155bd5780820151818401526020810190506155a2565b50505050905090810190601f1680156155ea5780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b50600083858161560457fe5b04905080915050939250505056fe704e6574776f726b2063616e6e6f7420626520746865207a65726f2061646472657373214552433737373a20617070726f76652066726f6d20746865207a65726f20616464726573734552433737373a2073656e642066726f6d20746865207a65726f20616464726573734552433737373a207472616e7366657220616d6f756e7420657863656564732062616c616e636574727573746564207369676e657220697320746865207a65726f20616464726573734552433737373a206275726e2066726f6d20746865207a65726f20616464726573734552433737373a20617574686f72697a696e672073656c66206173206f70657261746f7270546f6b656e3a2043616e6e6f74206d696e7420746f20746865207a65726f2061646472657373214f6e6c792074686520704e6574776f726b2063616e206d696e7420746f6b656e73214552433737373a207265766f6b696e672073656c66206173206f70657261746f724552433737373a206f70657261746f7220697320746865207a65726f20616464726573734f6e6c792074686520704e6574776f726b2063616e206368616e6765207468652060704e6574776f726b60206163636f756e7421536166654d6174683a206d756c7469706c69636174696f6e206f766572666c6f774f6e6c79207468652061637475616c2061646d696e206f70657261746f722063616e206368616e67652074686520616464726573734552433737373a20746f6b656e20726563697069656e7420636f6e747261637420686173206e6f20696d706c656d656e74657220666f7220455243373737546f6b656e73526563697069656e744552433737373a207472616e7366657220746f20746865207a65726f206164647265737347534e526563697069656e743a2063616c6c6572206973206e6f742052656c61794875624552433737373a2063616c6c6572206973206e6f7420616e206f70657261746f7220666f7220686f6c6465724552433737373a207472616e7366657220616d6f756e74206578636565647320616c6c6f77616e63654552433737373a207472616e736665722066726f6d20746865207a65726f20616464726573734552433737373a206275726e20616d6f756e7420657863656564732062616c616e63654552433737373a20617070726f766520746f20746865207a65726f2061646472657373a265627a7a723158202848c6af7096dc3957e78c764f97a1ae96193f25088cbc719ba4cd2bfd15522764736f6c6343000511003274727573746564207369676e657220697320746865207a65726f2061646472657373000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000000000000000000000000000000000000000000e0000000000000000000000000000000000000000000000000000000000000000a70546f6b656e7320495100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000249510000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
Deployed Bytecode
0x608060405234801561001057600080fd5b506004361061023d5760003560e01c80639bd9bbc61161013b578063dc3ca1bf116100b8578063fad8b32a1161007c578063fad8b32a14611672578063fc673c4f146116b6578063fc87675414611832578063fd4add661461187c578063fe9d9303146118c05761023d565b8063dc3ca1bf1461133f578063dcdc7dd014611383578063dd62ed3e14611517578063e06e0e221461158f578063e900a491146116285761023d565b8063ca16814e116100ff578063ca16814e146110b5578063cbe1f06c146110ff578063ce67c0031461111d578063d95b637114611279578063dab02527146112f55761023d565b80639bd9bbc614610d1d5780639bf8d82f14610e02578063a9059cbb14610e30578063ad61ccd514610e96578063bcc33e9d14610f195761023d565b806340c10f19116101c957806374e861d61161018d57806374e861d61461093a57806380274db71461098457806383947ea014610a11578063959b8c3f14610c5657806395d89b4114610c9a5761023d565b806340c10f191461067e578063556f0dc7146106e457806356a1c7011461070257806362ad1b831461074657806370a08231146108e25761023d565b80631e9cee74116102105780631e9cee74146103a857806323b872dd146104f557806324b76fd51461057b578063313ce56714610616578063394f02311461063a5761023d565b806306e485381461024257806306fdde03146102a1578063095ea7b31461032457806318160ddd1461038a575b600080fd5b61024a611985565b6040518080602001828103825283818151815260200191508051906020019060200280838360005b8381101561028d578082015181840152602081019050610272565b505050509050019250505060405180910390f35b6102a9611a13565b6040518080602001828103825283818151815260200191508051906020019080838360005b838110156102e95780820151818401526020810190506102ce565b50505050905090810190601f1680156103165780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b6103706004803603604081101561033a57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050611ab5565b604051808215151515815260200191505060405180910390f35b610392611ad8565b6040518082815260200191505060405180910390f35b6104f3600480360360a08110156103be57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291908035906020019064010000000081111561040557600080fd5b82018360208201111561041757600080fd5b8035906020019184600183028401116401000000008311171561043957600080fd5b90919293919293908035906020019064010000000081111561045a57600080fd5b82018360208201111561046c57600080fd5b8035906020019184600183028401116401000000008311171561048e57600080fd5b9091929391929390803590602001906401000000008111156104af57600080fd5b8201836020820111156104c157600080fd5b803590602001918460018302840111640100000000831117156104e357600080fd5b9091929391929390505050611ae2565b005b6105616004803603606081101561050b57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050611c70565b604051808215151515815260200191505060405180910390f35b6105fc6004803603604081101561059157600080fd5b8101908080359060200190929190803590602001906401000000008111156105b857600080fd5b8201836020820111156105ca57600080fd5b803590602001918460018302840111640100000000831117156105ec57600080fd5b9091929391929390505050611ece565b604051808215151515815260200191505060405180910390f35b61061e611f39565b604051808260ff1660ff16815260200191505060405180910390f35b61067c6004803603602081101561065057600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050611f42565b005b6106ca6004803603604081101561069457600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291905050506120e5565b604051808215151515815260200191505060405180910390f35b6106ec61211c565b6040518082815260200191505060405180910390f35b6107446004803603602081101561071857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050612125565b005b6108e0600480360360a081101561075c57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190803590602001906401000000008111156107c357600080fd5b8201836020820111156107d557600080fd5b803590602001918460018302840111640100000000831117156107f757600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561085a57600080fd5b82018360208201111561086c57600080fd5b8035906020019184600183028401116401000000008311171561088e57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612269565b005b610924600480360360208110156108f857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506122ed565b6040518082815260200191505060405180910390f35b610942612336565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6109fb6004803603602081101561099a57600080fd5b81019080803590602001906401000000008111156109b757600080fd5b8201836020820111156109c957600080fd5b803590602001918460018302840111640100000000831117156109eb57600080fd5b909192939192939050505061235f565b6040518082815260200191505060405180910390f35b610bd46004803603610120811015610a2857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190640100000000811115610a8557600080fd5b820183602082011115610a9757600080fd5b80359060200191846001830284011164010000000083111715610ab957600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019092919080359060200190929190803590602001909291908035906020019092919080359060200190640100000000811115610b4457600080fd5b820183602082011115610b5657600080fd5b80359060200191846001830284011164010000000083111715610b7857600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050919291929080359060200190929190505050612441565b6040518083815260200180602001828103825283818151815260200191508051906020019080838360005b83811015610c1a578082015181840152602081019050610bff565b50505050905090810190601f168015610c475780820380516001836020036101000a031916815260200191505b50935050505060405180910390f35b610c9860048036036020811015610c6c57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506127bb565b005b610ca2612a32565b6040518080602001828103825283818151815260200191508051906020019080838360005b83811015610ce2578082015181840152602081019050610cc7565b50505050905090810190601f168015610d0f5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b610e0060048036036060811015610d3357600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919080359060200190640100000000811115610d7a57600080fd5b820183602082011115610d8c57600080fd5b80359060200191846001830284011164010000000083111715610dae57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612ad4565b005b610e2e60048036036020811015610e1857600080fd5b8101908080359060200190929190505050612b06565b005b610e7c60048036036040811015610e4657600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050612b8a565b604051808215151515815260200191505060405180910390f35b610e9e612cae565b6040518080602001828103825283818151815260200191508051906020019080838360005b83811015610ede578082015181840152602081019050610ec3565b50505050905090810190601f168015610f0b5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b6110b3600480360360a0811015610f2f57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919080359060200190640100000000811115610f9657600080fd5b820183602082011115610fa857600080fd5b80359060200191846001830284011164010000000083111715610fca57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561102d57600080fd5b82018360208201111561103f57600080fd5b8035906020019184600183028401116401000000008311171561106157600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612ceb565b005b6110bd612e73565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b611107612e99565b6040518082815260200191505060405180910390f35b6112776004803603606081101561113357600080fd5b81019080803590602001909291908035906020019064010000000081111561115a57600080fd5b82018360208201111561116c57600080fd5b8035906020019184600183028401116401000000008311171561118e57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290803590602001906401000000008111156111f157600080fd5b82018360208201111561120357600080fd5b8035906020019184600183028401116401000000008311171561122557600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050612e9f565b005b6112db6004803603604081101561128f57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050612f89565b604051808215151515815260200191505060405180910390f35b6112fd61313a565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6113816004803603602081101561135557600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050613160565b005b6114fd6004803603608081101561139957600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190803590602001906401000000008111156113e057600080fd5b8201836020820111156113f257600080fd5b8035906020019184600183028401116401000000008311171561141457600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192908035906020019064010000000081111561147757600080fd5b82018360208201111561148957600080fd5b803590602001918460018302840111640100000000831117156114ab57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505091929192905050506132c1565b604051808215151515815260200191505060405180910390f35b6115796004803603604081101561152d57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050613431565b6040518082815260200191505060405180910390f35b611626600480360360808110156115a557600080fd5b81019080803590602001906401000000008111156115c257600080fd5b8201836020820111156115d457600080fd5b803590602001918460018302840111640100000000831117156115f657600080fd5b909192939192939080351515906020019092919080359060200190929190803590602001909291905050506134b8565b005b61163061359a565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6116b46004803603602081101561168857600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506135c0565b005b611830600480360360808110156116cc57600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291908035906020019064010000000081111561171357600080fd5b82018360208201111561172557600080fd5b8035906020019184600183028401116401000000008311171561174757600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290803590602001906401000000008111156117aa57600080fd5b8201836020820111156117bc57600080fd5b803590602001918460018302840111640100000000831117156117de57600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050613837565b005b61183a6138b7565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6118be6004803603602081101561189257600080fd5b81019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506138dd565b005b611983600480360360408110156118d657600080fd5b8101908080359060200190929190803590602001906401000000008111156118fd57600080fd5b82018360208201111561190f57600080fd5b8035906020019184600183028401116401000000008311171561193157600080fd5b91908080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509192919290505050613a54565b005b60606005805480602002602001604051908101604052809291908181526020018280548015611a0957602002820191906000526020600020905b8160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190600101908083116119bf575b5050505050905090565b606060038054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015611aab5780601f10611a8057610100808354040283529160200191611aab565b820191906000526020600020905b815481529060010190602001808311611a8e57829003601f168201915b5050505050905090565b600080611ac0613a82565b9050611acd818585613a91565b600191505092915050565b6000600254905090565b611af3611aed613a82565b89612f89565b611b48576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b611be4611b53613a82565b898989898080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505088888080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050613c88565b8773ffffffffffffffffffffffffffffffffffffffff167f78e6c3f67f57c26578f2487b930b70d844bcc8dd8f4d629fb4af81252ab5aa6588848460405180848152602001806020018281038252848482818152602001925080828437600081840152601f19601f82011690508083019250505094505050505060405180910390a25050505050505050565b60008073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415611cf7576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158736024913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415611d7d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260268152602001806159106026913960400191505060405180910390fd5b6000611d87613a82565b9050611db5818686866040518060200160405280600081525060405180602001604052806000815250613f93565b611de18186868660405180602001604052806000815250604051806020016040528060008152506142ad565b611e948582611e8f866040518060600160405280602981526020016158e760299139600960008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008873ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b613a91565b611ec28186868660405180602001604052806000815250604051806020016040528060008152506000614674565b60019150509392505050565b6000611f2e846040518060200160405280600081525085858080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050612e9f565b600190509392505050565b60006012905090565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614611fe8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260358152602001806157f16035913960400191505060405180910390fd5b7fe8fdc5340d9288e129a7c6af86dc4002f708091280d69f89583f7e6349c0a8d6600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1682604051808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019250505060405180910390a180600d60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6000612111838360405180602001604052806000815250604051806020016040528060008152506132c1565b506001905092915050565b60006001905090565b61212d614a48565b61219f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415612225576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806156a56022913960400191505060405180910390fd5b80600a60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b61227a612274613a82565b86612f89565b6122cf576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b6122e66122da613a82565b86868686866001614a85565b5050505050565b6000600160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020549050919050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6000612369612336565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146123ec576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158976024913960400191505060405180910390fd5b61243983838080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f82011690508083019250505050505050614c68565b905092915050565b600060606000606085806020019051604081101561245e57600080fd5b81019080805190602001909291908051604051939291908464010000000082111561248857600080fd5b8382019150602082018581111561249e57600080fd5b82518660018202830111640100000000821117156124bb57600080fd5b8083526020830192505050908051906020019080838360005b838110156124ef5780820151818401526020810190506124d4565b50505050905090810190601f16801561251c5780820380516001836020036101000a031916815260200191505b50604052505050915091506060828e8e8e8e8e8e8e612539612336565b30604051602001808b81526020018a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014018973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b815260140188805190602001908083835b602083106125e057805182526020820191506020810190506020830392506125bd565b6001836020036101000a0380198251168184511680821785525050505050509050018781526020018681526020018581526020018481526020018373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014018273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660601b81526014019a50505050505050505050506040516020818303038152906040529050600a60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff166126fc836126ee8480519060200120614c6f565b614cc790919063ffffffff16565b73ffffffffffffffffffffffffffffffffffffffff16141561279057612784838e8d8d604051602001808581526020018473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001838152602001828152602001945050505050604051602081830303815290604052614dcb565b945094505050506127ad565b6127a5600060018111156127a057fe5b614ddb565b945094505050505b995099975050505050505050565b8073ffffffffffffffffffffffffffffffffffffffff166127da613a82565b73ffffffffffffffffffffffffffffffffffffffff161415612847576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806156e96024913960400191505060405180910390fd5b600660008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff161561293157600860006128a5613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81549060ff02191690556129ce565b60016007600061293f613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055505b6129d6613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167ff4caeb2d6ca8932a215a353d0703c326ec2d81fc68170f320eb2ab49e9df61f960405160405180910390a350565b606060048054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015612aca5780601f10612a9f57610100808354040283529160200191612aca565b820191906000526020600020905b815481529060010190602001808311612aad57829003601f168201915b5050505050905090565b612b01612adf613a82565b612ae7613a82565b858585604051806020016040528060008152506001614a85565b505050565b612b0e614a48565b612b80576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b80600c8190555050565b60008073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612c11576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158736024913960400191505060405180910390fd5b6000612c1b613a82565b9050612c49818286866040518060200160405280600081525060405180602001604052806000815250613f93565b612c758182868660405180602001604052806000815250604051806020016040528060008152506142ad565b612ca38182868660405180602001604052806000815250604051806020016040528060008152506000614674565b600191505092915050565b60606040518060400160405280600581526020017f312e302e30000000000000000000000000000000000000000000000000000000815250905090565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16612d2c613a82565b73ffffffffffffffffffffffffffffffffffffffff1614612db5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f63616c6c6572206973206e6f74207468652061646d696e206f70657261746f7281525060200191505060405180910390fd5b612de7600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1686868686866000614a85565b7fb22a57ba0314fafe219dc14abcf1f22e86e6e82d599c0c31177a2d7c2e1b17e1600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390a15050505050565b600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600c5481565b612ec9612eaa613a82565b612eb2613a82565b858560405180602001604052806000815250613c88565b3373ffffffffffffffffffffffffffffffffffffffff167f78e6c3f67f57c26578f2487b930b70d844bcc8dd8f4d629fb4af81252ab5aa6584836040518083815260200180602001828103825283818151815260200191508051906020019080838360005b83811015612f49578082015181840152602081019050612f2e565b50505050905090810190601f168015612f765780820380516001836020036101000a031916815260200191505b50935050505060405180910390a2505050565b60008173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff1614806130a15750600660008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff1680156130a05750600860008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16155b5b806131325750600760008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff165b905092915050565b600b60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b613168614a48565b6131da576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260178152602001807f43616c6c6572206973206e6f7420746865206f776e657200000000000000000081525060200191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16141561327d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252601e8152602001807f6665652074617267657420697320746865207a65726f2061646472657373000081525060200191505060405180910390fd5b80600b60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6000600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16613304613a82565b73ffffffffffffffffffffffffffffffffffffffff1614613370576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806157356022913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff1614156133f6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602881526020018061570d6028913960400191505060405180910390fd5b613425600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1686868686614dfc565b60019050949350505050565b6000600960008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054905092915050565b6134c0612336565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614613543576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806158976024913960400191505060405180910390fd5b61359385858080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f8201169050808301925050505050505084848461510c565b5050505050565b600d60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b6135c8613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16141561364c576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260218152602001806157576021913960400191505060405180910390fd5b600660008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff161561373f576001600860006136ac613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506137d3565b6007600061374b613a82565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81549060ff02191690555b6137db613a82565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f50546e66e5f44d728365dc3908c63bc5cfeeab470722c1677e3073a6ac294aa160405160405180910390a350565b613848613842613a82565b85612f89565b61389d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602c8152602001806158bb602c913960400191505060405180910390fd5b6138b16138a8613a82565b85858585613c88565b50505050565b600a60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1661391e613a82565b73ffffffffffffffffffffffffffffffffffffffff161461398a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252603481526020018061579c6034913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415613a10576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806156136024913960400191505060405180910390fd5b80600e60006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b613a7e613a5f613a82565b613a67613a82565b848460405180602001604052806000815250613c88565b5050565b6000613a8c615234565b905090565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415613b17576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260258152602001806156376025913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415613b9d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260238152602001806159596023913960400191505060405180910390fd5b80600960008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925836040518082815260200191505060405180910390a3505050565b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415613d0e576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260228152602001806156c76022913960400191505060405180910390fd5b613d1d85856000868686613f93565b613d898360405180606001604052806023815260200161593660239139600160008873ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550613de1836002546152a090919063ffffffff16565b6002819055508373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167fa78a9be3a7b862d26933ad85fb11d80ef66b8f972d7cbba06621d583943a4098858585604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b83811015613e83578082015181840152602081019050613e68565b50505050905090810190601f168015613eb05780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b83811015613ee9578082015181840152602081019050613ece565b50505050905090810190601f168015613f165780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a3600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a35050505050565b6000731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff1663aabbb8ca877f29ddb589b1fb5fc7cf394961c1adf5f8c6454761adf795e67fe149f658abe89560001b6040518363ffffffff1660e01b8152600401808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018281526020019250505060206040518083038186803b15801561405157600080fd5b505afa158015614065573d6000803e3d6000fd5b505050506040513d602081101561407b57600080fd5b81019080805190602001909291905050509050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16146142a4578073ffffffffffffffffffffffffffffffffffffffff166375ab97828888888888886040518763ffffffff1660e01b8152600401808773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156141d35780820151818401526020810190506141b8565b50505050905090810190601f1680156142005780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b8381101561423957808201518184015260208101905061421e565b50505050905090810190601f1680156142665780820380516001836020036101000a031916815260200191505b5098505050505050505050600060405180830381600087803b15801561428b57600080fd5b505af115801561429f573d6000803e3d6000fd5b505050505b50505050505050565b6143198360405180606001604052806027815260200161567e60279139600160008973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546145b49092919063ffffffff16565b600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506143ae83600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546152ea90919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167f06b541ddaa720db2b10a4d0cdac39b8d360425fc073085fac19bc82614677987868686604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156144a4578082015181840152602081019050614489565b50505050905090810190601f1680156144d15780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b8381101561450a5780820151818401526020810190506144ef565b50505050905090810190601f1680156145375780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a48373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a3505050505050565b6000838311158290614661576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561462657808201518184015260208101905061460b565b50505050905090810190601f1680156146535780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b5060008385039050809150509392505050565b6000731820a4b7618bde71dce8cdc73aab6c95905fad2473ffffffffffffffffffffffffffffffffffffffff1663aabbb8ca877fb281fc8c12954d22544db45de3159a39272895b169a852b314f9cc762e44c53b60001b6040518363ffffffff1660e01b8152600401808373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018281526020019250505060206040518083038186803b15801561473257600080fd5b505afa158015614746573d6000803e3d6000fd5b505050506040513d602081101561475c57600080fd5b81019080805190602001909291905050509050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614614988578073ffffffffffffffffffffffffffffffffffffffff166223de298989898989896040518763ffffffff1660e01b8152600401808773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020018481526020018060200180602001838103835285818151815260200191508051906020019080838360005b838110156148b3578082015181840152602081019050614898565b50505050905090810190601f1680156148e05780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b838110156149195780820151818401526020810190506148fe565b50505050905090810190601f1680156149465780820380516001836020036101000a031916815260200191505b5098505050505050505050600060405180830381600087803b15801561496b57600080fd5b505af115801561497f573d6000803e3d6000fd5b50505050614a3e565b8180156149c25750600073ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff1614155b15614a3d576149e68673ffffffffffffffffffffffffffffffffffffffff16615372565b15614a3c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252604d815260200180615826604d913960600191505060405180910390fd5b5b5b5050505050505050565b6000614a526153bd565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff1614905090565b600073ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff161415614b0b576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260248152602001806157786024913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168673ffffffffffffffffffffffffffffffffffffffff161415614b91576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602281526020018061565c6022913960400191505060405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415614c34576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f4552433737373a2073656e6420746f20746865207a65726f206164647265737381525060200191505060405180910390fd5b614c42878787878787613f93565b614c508787878787876142ad565b614c5f87878787878787614674565b50505050505050565b6000919050565b60008160405160200180807f19457468657265756d205369676e6564204d6573736167653a0a333200000000815250601c01828152602001915050604051602081830303815290604052805190602001209050919050565b60006041825114614cdb5760009050614dc5565b60008060006020850151925060408501519150606085015160001a90507f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a08260001c1115614d2f5760009350505050614dc5565b601b8160ff1614158015614d475750601c8160ff1614155b15614d585760009350505050614dc5565b60018682858560405160008152602001604052604051808581526020018460ff1660ff1681526020018381526020018281526020019450505050506020604051602081039080840390855afa158015614db5573d6000803e3d6000fd5b5050506020604051035193505050505b92915050565b6000606060008391509150915091565b6000606082600b016040518060200160405280600081525091509150915091565b600073ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415614e9f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260208152602001807f4552433737373a206d696e7420746f20746865207a65726f206164647265737381525060200191505060405180910390fd5b614eb4836002546152ea90919063ffffffff16565b600281905550614f0c83600160008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546152ea90919063ffffffff16565b600160008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550614f60856000868686866001614674565b8373ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff167f2fe5be0146f74c5bce36c0b80911af6c7d86ff27e89d5cfa61fc681327954e5d858585604051808481526020018060200180602001838103835285818151815260200191508051906020019080838360005b83811015614ffc578082015181840152602081019050614fe1565b50505050905090810190601f1680156150295780820380516001836020036101000a031916815260200191505b50838103825284818151815260200191508051906020019080838360005b83811015615062578082015181840152602081019050615047565b50505050905090810190601f16801561508f5780820380516001836020036101000a031916815260200191505b509550505050505060405180910390a38373ffffffffffffffffffffffffffffffffffffffff16600073ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef856040518082815260200191505060405180910390a35050505050565b60008060008087806020019051608081101561512757600080fd5b81019080805190602001909291908051906020019092919080519060200190929190805190602001909291905050509350935093509350600061518261517b600c54620186a06152a090919063ffffffff16565b83856153e7565b905060006151c5670de0b6b3a76400006151b7886151a9868d6152a090919063ffffffff16565b61540490919063ffffffff16565b61548a90919063ffffffff16565b90506000811115615228576152276151db613a82565b86600b60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff168460405180602001604052806000815250604051806020016040528060008152506000614a85565b5b50505050505050505050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146152925733905061529d565b61529a6154d4565b90505b90565b60006152e283836040518060400160405280601e81526020017f536166654d6174683a207375627472616374696f6e206f766572666c6f7700008152506145b4565b905092915050565b600080828401905083811015615368576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252601b8152602001807f536166654d6174683a206164646974696f6e206f766572666c6f77000000000081525060200191505060405180910390fd5b8091505092915050565b60008060007fc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a47060001b9050833f91508082141580156153b457506000801b8214155b92505050919050565b6000600e60009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b600060648260640184860202816153fa57fe5b0490509392505050565b6000808314156154175760009050615484565b600082840290508284828161542857fe5b041461547f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260218152602001806157d06021913960400191505060405180910390fd5b809150505b92915050565b60006154cc83836040518060400160405280601a81526020017f536166654d6174683a206469766973696f6e206279207a65726f00000000000081525061554c565b905092915050565b600060606000368080601f016020809104026020016040519081016040528093929190818152602001838380828437600081840152601f19601f820116905080830192505050505050509050600080369050905073ffffffffffffffffffffffffffffffffffffffff81830151169250829250505090565b600080831182906155f8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825283818151815260200191508051906020019080838360005b838110156155bd5780820151818401526020810190506155a2565b50505050905090810190601f1680156155ea5780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b50600083858161560457fe5b04905080915050939250505056fe704e6574776f726b2063616e6e6f7420626520746865207a65726f2061646472657373214552433737373a20617070726f76652066726f6d20746865207a65726f20616464726573734552433737373a2073656e642066726f6d20746865207a65726f20616464726573734552433737373a207472616e7366657220616d6f756e7420657863656564732062616c616e636574727573746564207369676e657220697320746865207a65726f20616464726573734552433737373a206275726e2066726f6d20746865207a65726f20616464726573734552433737373a20617574686f72697a696e672073656c66206173206f70657261746f7270546f6b656e3a2043616e6e6f74206d696e7420746f20746865207a65726f2061646472657373214f6e6c792074686520704e6574776f726b2063616e206d696e7420746f6b656e73214552433737373a207265766f6b696e672073656c66206173206f70657261746f724552433737373a206f70657261746f7220697320746865207a65726f20616464726573734f6e6c792074686520704e6574776f726b2063616e206368616e6765207468652060704e6574776f726b60206163636f756e7421536166654d6174683a206d756c7469706c69636174696f6e206f766572666c6f774f6e6c79207468652061637475616c2061646d696e206f70657261746f722063616e206368616e67652074686520616464726573734552433737373a20746f6b656e20726563697069656e7420636f6e747261637420686173206e6f20696d706c656d656e74657220666f7220455243373737546f6b656e73526563697069656e744552433737373a207472616e7366657220746f20746865207a65726f206164647265737347534e526563697069656e743a2063616c6c6572206973206e6f742052656c61794875624552433737373a2063616c6c6572206973206e6f7420616e206f70657261746f7220666f7220686f6c6465724552433737373a207472616e7366657220616d6f756e74206578636565647320616c6c6f77616e63654552433737373a207472616e736665722066726f6d20746865207a65726f20616464726573734552433737373a206275726e20616d6f756e7420657863656564732062616c616e63654552433737373a20617070726f766520746f20746865207a65726f2061646472657373a265627a7a723158202848c6af7096dc3957e78c764f97a1ae96193f25088cbc719ba4cd2bfd15522764736f6c63430005110032
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000000000000000000000000000000000000000000e0000000000000000000000000000000000000000000000000000000000000000a70546f6b656e7320495100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000249510000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
-----Decoded View---------------
Arg [0] : tokenName (string): pTokens IQ
Arg [1] : tokenSymbol (string): IQ
Arg [2] : defaultOperators (address[]):
-----Encoded View---------------
8 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000060
Arg [1] : 00000000000000000000000000000000000000000000000000000000000000a0
Arg [2] : 00000000000000000000000000000000000000000000000000000000000000e0
Arg [3] : 000000000000000000000000000000000000000000000000000000000000000a
Arg [4] : 70546f6b656e7320495100000000000000000000000000000000000000000000
Arg [5] : 0000000000000000000000000000000000000000000000000000000000000002
Arg [6] : 4951000000000000000000000000000000000000000000000000000000000000
Arg [7] : 0000000000000000000000000000000000000000000000000000000000000000
Deployed Bytecode Sourcemap
79965:2906:0:-;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;79965:2906:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;33225:115;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;33225:115:0;;;;;;;;;;;;;;;;;29507:83;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;29507:83:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;34792:184;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;34792:184:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;30282:91;;;:::i;:::-;;;;;;;;;;;;;;;;;;;82363:505;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;82363:505:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;82363:505:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;82363:505:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;82363:505:0;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;82363:505:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;82363:505:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;82363:505:0;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;82363:505:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;82363:505:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;82363:505:0;;;;;;;;;;;;:::i;:::-;;35352:677;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;35352:677:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;81832:231;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;81832:231:0;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;81832:231:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;81832:231:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;81832:231:0;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;29938:76;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;78039:262;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;78039:262:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;81098:191;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;81098:191:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;30136:80;;;:::i;:::-;;;;;;;;;;;;;;;;;;;74547:204;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;74547:204:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;33466:382;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;33466:382:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;33466:382:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;33466:382:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;33466:382:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;33466:382:0;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;33466:382:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;33466:382:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;33466:382:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;33466:382:0;;;;;;;;;;;;;;;:::i;:::-;;30478:118;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;30478:118:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;65049:87;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;68712:211;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;68712:211:0;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;68712:211:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;68712:211:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;68712:211:0;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;75159:1051;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;75159:1051:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;75159:1051:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;75159:1051:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;75159:1051:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;75159:1051:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;32284:405;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;32284:405:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;29651:87;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;29651:87:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30733:162;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;30733:162:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;30733:162:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;30733:162:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;30733:162:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;30733:162:0;;;;;;;;;;;;;;;:::i;:::-;;74943:99;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;74943:99:0;;;;;;;;;;;;;;;;;:::i;:::-;;31136:434;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;31136:434:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;66307:230;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;66307:230:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;77576:378;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;77576:378:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;77576:378:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;77576:378:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;77576:378:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;77576:378:0;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;77576:378:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;77576:378:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;77576:378:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;77576:378:0;;;;;;;;;;;;;;;:::i;:::-;;80104:23;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;73903:34;;;:::i;:::-;;;;;;;;;;;;;;;;;;;82071:284;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;82071:284:0;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;82071:284:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;82071:284:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;82071:284:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;82071:284:0;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;82071:284:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;82071:284:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;82071:284:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;82071:284:0;;;;;;;;;;;;;;;:::i;:::-;;31901:311;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;31901:311:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;73871:27;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;74757:180;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;74757:180:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;81297:527;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;81297:527:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;81297:527:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;81297:527:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;81297:527:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;81297:527:0;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;81297:527:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;81297:527:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;81297:527:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;81297:527:0;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;34511:136;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;34511:136:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;69572:277;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;69572:277:0;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;69572:277:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;69572:277:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;69572:277:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;77219:28;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;32758:396;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;32758:396:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;33976:287;;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;33976:287:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;33976:287:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;33976:287:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;33976:287:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;33976:287:0;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;33976:287:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;33976:287:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;33976:287:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;33976:287:0;;;;;;;;;;;;;;;:::i;:::-;;73835:31;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;80706:384;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;80706:384:0;;;;;;;;;;;;;;;;;;;:::i;:::-;;31707:126;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;31707:126:0;;;;;;;;;;;;;;;;;;;21:11:-1;8;5:28;2:2;;;46:1;43;36:12;2:2;31707:126:0;;35:9:-1;28:4;12:14;8:25;5:40;2:2;;;58:1;55;48:12;2:2;31707:126:0;;;;;;100:9:-1;95:1;81:12;77:20;67:8;63:35;60:50;39:11;25:12;22:29;11:107;8:2;;;131:1;128;121:12;8:2;31707:126:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;31707:126:0;;;;;;;;;;;;;;;:::i;:::-;;33225:115;33274:16;33310:22;33303:29;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;33225:115;:::o;29507:83::-;29544:13;29577:5;29570:12;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;29507:83;:::o;34792:184::-;34857:4;34874:14;34891:12;:10;:12::i;:::-;34874:29;;34914:32;34923:6;34931:7;34940:5;34914:8;:32::i;:::-;34964:4;34957:11;;;34792:184;;;;:::o;30282:91::-;30326:7;30353:12;;30346:19;;30282:91;:::o;82363:505::-;82620:36;82634:12;:10;:12::i;:::-;82648:7;82620:13;:36::i;:::-;82598:130;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;82739:56;82745:12;:10;:12::i;:::-;82759:7;82768:6;82776:4;;82739:56;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;82739:56:0;;;;;;82782:12;;82739:56;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;82739:56:0;;;;;;:5;:56::i;:::-;82818:7;82811:49;;;82827:6;82835:24;;82811:49;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;82811:49:0;;;;;;;;;;;;;;;82363:505;;;;;;;;:::o;35352:677::-;35441:4;35487:1;35466:23;;:9;:23;;;;35458:72;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;35567:1;35549:20;;:6;:20;;;;35541:71;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;35625:15;35643:12;:10;:12::i;:::-;35625:30;;35668:61;35686:7;35695:6;35703:9;35714:6;35668:61;;;;;;;;;;;;;;;;;;;;;;;;:17;:61::i;:::-;35742:49;35748:7;35757:6;35765:9;35776:6;35742:49;;;;;;;;;;;;;;;;;;;;;;;;:5;:49::i;:::-;35802:112;35811:6;35819:7;35828:85;35861:6;35828:85;;;;;;;;;;;;;;;;;:11;:19;35840:6;35828:19;;;;;;;;;;;;;;;:28;35848:7;35828:28;;;;;;;;;;;;;;;;:32;;:85;;;;;:::i;:::-;35802:8;:112::i;:::-;35927:70;35947:7;35956:6;35964:9;35975:6;35927:70;;;;;;;;;;;;;;;;;;;;;;;;35991:5;35927:19;:70::i;:::-;36017:4;36010:11;;;35352:677;;;;;:::o;81832:231::-;81967:4;81989:44;81996:6;81989:44;;;;;;;;;;;;82008:24;;81989:44;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;81989:44:0;;;;;;:6;:44::i;:::-;82051:4;82044:11;;81832:231;;;;;:::o;29938:76::-;29979:5;30004:2;29997:9;;29938:76;:::o;78039:262::-;78125:13;;;;;;;;;;;78111:27;;:10;:27;;;78103:93;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;78208:50;78228:13;;;;;;;;;;;78243:14;78208:50;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;78281:14;78265:13;;:30;;;;;;;;;;;;;;;;;;78039:262;:::o;81098:191::-;81207:4;81229:30;81234:9;81245:5;81229:30;;;;;;;;;;;;;;;;;;;;;;;;:4;:30::i;:::-;;81277:4;81270:11;;81098:191;;;;:::o;30136:80::-;30180:7;30207:1;30200:8;;30136:80;:::o;74547:204::-;43300:9;:7;:9::i;:::-;43292:45;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;74661:1;74632:31;;:17;:31;;;;74624:78;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;74728:17;74709:16;;:36;;;;;;;;;;;;;;;;;;74547:204;:::o;33466:382::-;33673:35;33687:12;:10;:12::i;:::-;33701:6;33673:13;:35::i;:::-;33665:92;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;33768:72;33774:12;:10;:12::i;:::-;33788:6;33796:9;33807:6;33815:4;33821:12;33835:4;33768:5;:72::i;:::-;33466:382;;;;;:::o;30478:118::-;30539:7;30566:9;:22;30576:11;30566:22;;;;;;;;;;;;;;;;30559:29;;30478:118;;;:::o;65049:87::-;65092:7;65119:9;;;;;;;;;;;65112:16;;65049:87;:::o;68712:211::-;68778:7;68820:12;:10;:12::i;:::-;68806:26;;:10;:26;;;68798:75;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;68891:24;68907:7;;68891:24;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;68891:24:0;;;;;;:15;:24::i;:::-;68884:31;;68712:211;;;;:::o;75159:1051::-;75466:7;75475:12;75500:15;75517:22;75554:12;75543:39;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;75543:39:0;;;;;;;;;;;;;;;;;;;;;;19:11:-1;14:3;11:20;8:2;;;44:1;41;34:12;8:2;71:11;66:3;62:21;55:28;;123:4;118:3;114:14;159:9;141:16;138:31;135:2;;;182:1;179;172:12;135:2;219:3;213:10;330:9;325:1;311:12;307:20;289:16;285:43;282:58;261:11;247:12;244:29;233:115;230:2;;;361:1;358;351:12;230:2;384:12;379:3;372:25;420:4;415:3;411:14;404:21;;0:432;;75543:39:0;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;75543:39:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;75499:83;;;;75589:17;75634:7;75650:5;75664:4;75677:15;75701:14;75724:8;75741;75758:5;75804:12;:10;:12::i;:::-;75875:4;75609:321;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;36:153:-1;66:2;61:3;58:11;36:153;;182:3;176:10;171:3;164:23;98:2;93:3;89:12;82:19;;123:2;118:3;114:12;107:19;;148:2;143:3;139:12;132:19;;36:153;;;274:1;267:3;263:2;259:12;254:3;250:22;246:30;315:4;311:9;305:3;299:10;295:26;356:4;350:3;344:10;340:21;389:7;380;377:20;372:3;365:33;3:399;;;75609:321:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;49:4:-1;39:7;30;26:21;22:32;13:7;6:49;75609:321:0;;;75589:341;;76004:16;;;;;;;;;;;75941:79;;:59;75990:9;75941:40;75951:4;75941:15;;;;;;:38;:40::i;:::-;:48;;:59;;;;:::i;:::-;:79;;;75937:268;;;76038:72;76069:7;76078:4;76084:14;76100:8;76058:51;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;49:4:-1;39:7;30;26:21;22:32;13:7;6:49;76058:51:0;;;76038:19;:72::i;:::-;76031:79;;;;;;;;;75937:268;76140:57;76167:28;76159:37;;;;;;;;76140:18;:57::i;:::-;76133:64;;;;;;;75159:1051;;;;;;;;;;;;;:::o;32284:405::-;32371:8;32355:24;;:12;:10;:12::i;:::-;:24;;;;32347:73;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;32437:17;:27;32455:8;32437:27;;;;;;;;;;;;;;;;;;;;;;;;;32433:189;;;32488:24;:38;32513:12;:10;:12::i;:::-;32488:38;;;;;;;;;;;;;;;:48;32527:8;32488:48;;;;;;;;;;;;;;;;32481:55;;;;;;;;;;;32433:189;;;32606:4;32569:10;:24;32580:12;:10;:12::i;:::-;32569:24;;;;;;;;;;;;;;;:34;32594:8;32569:34;;;;;;;;;;;;;;;;:41;;;;;;;;;;;;;;;;;;32433:189;32668:12;:10;:12::i;:::-;32639:42;;32658:8;32639:42;;;;;;;;;;;;32284:405;:::o;29651:87::-;29690:13;29723:7;29716:14;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;29651:87;:::o;30733:162::-;30819:68;30825:12;:10;:12::i;:::-;30839;:10;:12::i;:::-;30853:9;30864:6;30872:4;30819:68;;;;;;;;;;;;30882:4;30819:5;:68::i;:::-;30733:162;;;:::o;74943:99::-;43300:9;:7;:9::i;:::-;43292:45;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;75024:12;75010:11;:26;;;;74943:99;:::o;31136:434::-;31205:4;31251:1;31230:23;;:9;:23;;;;31222:72;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;31307:12;31322;:10;:12::i;:::-;31307:27;;31347:56;31365:4;31371;31377:9;31388:6;31347:56;;;;;;;;;;;;;;;;;;;;;;;;:17;:56::i;:::-;31416:44;31422:4;31428;31434:9;31445:6;31416:44;;;;;;;;;;;;;;;;;;;;;;;;:5;:44::i;:::-;31473:65;31493:4;31499;31505:9;31516:6;31473:65;;;;;;;;;;;;;;;;;;;;;;;;31532:5;31473:19;:65::i;:::-;31558:4;31551:11;;;31136:434;;;;:::o;66307:230::-;66355:13;66515:14;;;;;;;;;;;;;;;;;;;66307:230;:::o;77576:378::-;77770:13;;;;;;;;;;;77754:29;;:12;:10;:12::i;:::-;:29;;;77746:74;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;77827;77833:13;;;;;;;;;;;77848:6;77856:9;77867:6;77875:4;77881:12;77895:5;77827;:74::i;:::-;77913:35;77934:13;;;;;;;;;;;77913:35;;;;;;;;;;;;;;;;;;;;;;77576:378;;;;;:::o;80104:23::-;;;;;;;;;;;;;:::o;73903:34::-;;;;:::o;82071:284::-;82228:51;82234:12;:10;:12::i;:::-;82248;:10;:12::i;:::-;82262:6;82270:4;82228:51;;;;;;;;;;;;:5;:51::i;:::-;82302:10;82295:52;;;82314:6;82322:24;82295:52;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;82295:52:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;82071:284;;;:::o;31901:311::-;32009:4;32045:11;32033:23;;:8;:23;;;:121;;;;32074:17;:27;32092:8;32074:27;;;;;;;;;;;;;;;;;;;;;;;;;:79;;;;;32106:24;:37;32131:11;32106:37;;;;;;;;;;;;;;;:47;32144:8;32106:47;;;;;;;;;;;;;;;;;;;;;;;;;32105:48;32074:79;32033:121;:171;;;;32171:10;:23;32182:11;32171:23;;;;;;;;;;;;;;;:33;32195:8;32171:33;;;;;;;;;;;;;;;;;;;;;;;;;32033:171;32026:178;;31901:311;;;;:::o;73871:27::-;;;;;;;;;;;;;:::o;74757:180::-;43300:9;:7;:9::i;:::-;43292:45;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;74859:1;74834:27;;:13;:27;;;;74826:70;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;74918:13;74903:12;;:28;;;;;;;;;;;;;;;;;;74757:180;:::o;81297:527::-;81472:4;81532:8;;;;;;;;;;;81516:24;;:12;:10;:12::i;:::-;:24;;;81494:108;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;81656:1;81635:23;;:9;:23;;;;81613:113;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;81737:57;81743:8;;;;;;;;;;;81753:9;81764:5;81771:8;81781:12;81737:5;:57::i;:::-;81812:4;81805:11;;81297:527;;;;;;:::o;34511:136::-;34584:7;34611:11;:19;34623:6;34611:19;;;;;;;;;;;;;;;:28;34631:7;34611:28;;;;;;;;;;;;;;;;34604:35;;34511:136;;;;:::o;69572:277::-;69718:12;:10;:12::i;:::-;69704:26;;:10;:26;;;69696:75;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;69782:59;69799:7;;69782:59;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;69782:59:0;;;;;;69808:7;69817:12;69831:9;69782:16;:59::i;:::-;69572:277;;;;;:::o;77219:28::-;;;;;;;;;;;;;:::o;32758:396::-;32838:12;:10;:12::i;:::-;32826:24;;:8;:24;;;;32818:70;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;32905:17;:27;32923:8;32905:27;;;;;;;;;;;;;;;;;;;;;;;;;32901:189;;;33000:4;32949:24;:38;32974:12;:10;:12::i;:::-;32949:38;;;;;;;;;;;;;;;:48;32988:8;32949:48;;;;;;;;;;;;;;;;:55;;;;;;;;;;;;;;;;;;32901:189;;;33044:10;:24;33055:12;:10;:12::i;:::-;33044:24;;;;;;;;;;;;;;;:34;33069:8;33044:34;;;;;;;;;;;;;;;;33037:41;;;;;;;;;;;32901:189;33133:12;:10;:12::i;:::-;33107:39;;33123:8;33107:39;;;;;;;;;;;;32758:396;:::o;33976:287::-;34103:36;34117:12;:10;:12::i;:::-;34131:7;34103:13;:36::i;:::-;34095:93;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;34199:56;34205:12;:10;:12::i;:::-;34219:7;34228:6;34236:4;34242:12;34199:5;:56::i;:::-;33976:287;;;;:::o;73835:31::-;;;;;;;;;;;;;:::o;80706:384::-;80839:8;;;;;;;;;;;80823:24;;:12;:10;:12::i;:::-;:24;;;80801:126;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;80983:1;80960:25;;:11;:25;;;;80938:111;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;81071:11;81060:8;;:22;;;;;;;;;;;;;;;;;;80706:384;:::o;31707:126::-;31774:51;31780:12;:10;:12::i;:::-;31794;:10;:12::i;:::-;31808:6;31816:4;31774:51;;;;;;;;;;;;:5;:51::i;:::-;31707:126;;:::o;74326:107::-;74371:15;74402:25;:23;:25::i;:::-;74395:32;;74326:107;:::o;40229:341::-;40341:1;40323:20;;:6;:20;;;;40315:70;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;40423:1;40404:21;;:7;:21;;;;40396:69;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;40509:5;40478:11;:19;40490:6;40478:19;;;;;;;;;;;;;;;:28;40498:7;40478:28;;;;;;;;;;;;;;;:36;;;;40547:7;40530:32;;40539:6;40530:32;;;40556:5;40530:32;;;;;;;;;;;;;;;;;;40229:341;;;:::o;38939:654::-;39158:1;39142:18;;:4;:18;;;;39134:65;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;39212:73;39230:8;39240:4;39254:1;39258:6;39266:4;39272:12;39212:17;:73::i;:::-;39351:66;39371:6;39351:66;;;;;;;;;;;;;;;;;:9;:15;39361:4;39351:15;;;;;;;;;;;;;;;;:19;;:66;;;;;:::i;:::-;39333:9;:15;39343:4;39333:15;;;;;;;;;;;;;;;:84;;;;39443:24;39460:6;39443:12;;:16;;:24;;;;:::i;:::-;39428:12;:39;;;;39502:4;39485:50;;39492:8;39485:50;;;39508:6;39516:4;39522:12;39485:50;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;39485:50:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;39485:50:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;39574:1;39551:34;;39560:4;39551:34;;;39578:6;39551:34;;;;;;;;;;;;;;;;;;38939:654;;;;;:::o;41054:497::-;41286:19;27367:42;41308:40;;;41349:4;27845:66;41355:28;;41308:76;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;41308:76:0;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;41308:76:0;;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;41308:76:0;;;;;;;;;;;;;;;;41286:98;;41422:1;41399:25;;:11;:25;;;41395:149;;41455:11;41441:39;;;41481:8;41491:4;41497:2;41501:6;41509:8;41519:12;41441:91;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;41441:91:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;41441:91:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;41441:91:0;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;41441:91:0;;;;41395:149;41054:497;;;;;;;:::o;39601:483::-;39838:70;39858:6;39838:70;;;;;;;;;;;;;;;;;:9;:15;39848:4;39838:15;;;;;;;;;;;;;;;;:19;;:70;;;;;:::i;:::-;39820:9;:15;39830:4;39820:15;;;;;;;;;;;;;;;:88;;;;39935:25;39953:6;39935:9;:13;39945:2;39935:13;;;;;;;;;;;;;;;;:17;;:25;;;;:::i;:::-;39919:9;:13;39929:2;39919:13;;;;;;;;;;;;;;;:41;;;;39999:2;39978:56;;39993:4;39978:56;;39983:8;39978:56;;;40003:6;40011:8;40021:12;39978:56;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;39978:56:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;39978:56:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;40065:2;40050:26;;40059:4;40050:26;;;40069:6;40050:26;;;;;;;;;;;;;;;;;;39601:483;;;;;;:::o;14693:192::-;14779:7;14812:1;14807;:6;;14815:12;14799:29;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;14799:29:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;14839:9;14855:1;14851;:5;14839:17;;14876:1;14869:8;;;14693:192;;;;;:::o;79228:660::-;79457:19;27367:42;79479:40;;;79520:2;78503:66;79524:31;;79479:77;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;79479:77:0;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;79479:77:0;;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;79479:77:0;;;;;;;;;;;;;;;;79457:99;;79590:1;79567:25;;:11;:25;;;79563:320;;79620:11;79603:44;;;79648:8;79658:4;79664:2;79668:6;79676:8;79686:12;79603:96;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;79603:96:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;79603:96:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;79603:96:0;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;79603:96:0;;;;79563:320;;;79717:19;:41;;;;;79756:1;79740:18;;:4;:18;;;;79717:41;79713:170;;;79778:15;:2;:13;;;:15::i;:::-;79777:16;79769:106;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;79713:170;79563:320;79228:660;;;;;;;;:::o;43431:89::-;43473:4;43507:7;:5;:7::i;:::-;43493:21;;:10;:21;;;43486:28;;43431:89;:::o;37820:739::-;38103:1;38083:22;;:8;:22;;;;38075:71;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;38181:1;38165:18;;:4;:18;;;;38157:65;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;38255:1;38241:16;;:2;:16;;;;38233:61;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;38307:69;38325:8;38335:4;38341:2;38345:6;38353:8;38363:12;38307:17;:69::i;:::-;38389:57;38395:8;38405:4;38411:2;38415:6;38423:8;38433:12;38389:5;:57::i;:::-;38459:92;38479:8;38489:4;38495:2;38499:6;38507:8;38517:12;38531:19;38459;:92::i;:::-;37820:739;;;;;;;:::o;76216:76::-;76281:7;76216:76;;;:::o;47045:269::-;47114:7;47300:4;47247:58;;;;;;;;;;;;;;;;;;;;;;49:4:-1;39:7;30;26:21;22:32;13:7;6:49;47247:58:0;;;47237:69;;;;;;47230:76;;47045:269;;;:::o;44841:1930::-;44919:7;45002:2;44982:9;:16;:22;44978:74;;45037:1;45021:19;;;;44978:74;45121:9;45141;45161:7;45413:4;45402:9;45398:20;45392:27;45387:32;;45459:4;45448:9;45444:20;45438:27;45433:32;;45513:4;45502:9;45498:20;45492:27;45489:1;45484:36;45479:41;;46443:66;46438:1;46430:10;;:79;46426:129;;;46541:1;46526:17;;;;;;;46426:129;46576:2;46571:1;:7;;;;:18;;;;;46587:2;46582:1;:7;;;;46571:18;46567:68;;;46621:1;46606:17;;;;;;;46567:68;46739:24;46749:4;46755:1;46758;46761;46739:24;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;46739:24:0;;;;;;;;46732:31;;;;;44841:1930;;;;;:::o;70753:155::-;70827:7;70836:12;64570:1;70892:7;70861:39;;;;70753:155;;;:::o;71044:158::-;71114:7;71123:12;71180:9;64627:2;71156:33;71148:46;;;;;;;;;;;;;;;;71044:158;;;:::o;36618:650::-;36843:1;36824:21;;:7;:21;;;;36816:66;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;36945:24;36962:6;36945:12;;:16;;:24;;;;:::i;:::-;36930:12;:39;;;;37001:30;37024:6;37001:9;:18;37011:7;37001:18;;;;;;;;;;;;;;;;:22;;:30;;;;:::i;:::-;36980:9;:18;36990:7;36980:18;;;;;;;;;;;;;;;:51;;;;37044:88;37064:8;37082:1;37086:7;37095:6;37103:8;37113:12;37127:4;37044:19;:88::i;:::-;37167:7;37150:57;;37157:8;37150:57;;;37176:6;37184:8;37194:12;37150:57;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;37150:57:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;37150:57:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;37244:7;37223:37;;37240:1;37223:37;;;37253:6;37223:37;;;;;;;;;;;;;;;;;;36618:650;;;;;:::o;76298:785::-;76400:15;76417:12;76431:22;76455:16;76493:7;76482:57;;;;;13:3:-1;8;5:12;2:2;;;30:1;27;20:12;2:2;76482:57:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;76399:140;;;;;;;;76789:22;76814:84;76829:42;76859:11;;64745:6;76829:29;;:42;;;;:::i;:::-;76873:8;76883:14;76814;:84::i;:::-;76789:109;;76905:8;76916:64;73744:6;76916:45;76953:7;76916:32;76933:14;76916:12;:16;;:32;;;;:::i;:::-;:36;;:45;;;;:::i;:::-;:49;;:64;;;;:::i;:::-;76905:75;;76999:1;76993:3;:7;76989:89;;;77011:59;77017:12;:10;:12::i;:::-;77031:4;77037:12;;;;;;;;;;;77051:3;77011:59;;;;;;;;;;;;;;;;;;;;;;;;77064:5;77011;:59::i;:::-;76989:89;76298:785;;;;;;;;;;:::o;67509:216::-;67554:15;67600:9;;;;;;;;;;;67586:23;;:10;:23;;;67582:136;;67633:10;67626:17;;;;67582:136;67683:23;:21;:23::i;:::-;67676:30;;67509:216;;:::o;14220:136::-;14278:7;14305:43;14309:1;14312;14305:43;;;;;;;;;;;;;;;;;:3;:43::i;:::-;14298:50;;14220:136;;;;:::o;13764:181::-;13822:7;13842:9;13858:1;13854;:5;13842:17;;13883:1;13878;:6;;13870:46;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;13936:1;13929:8;;;13764:181;;;;:::o;19123:619::-;19183:4;19445:16;19472:19;19494:66;19472:88;;;;19663:7;19651:20;19639:32;;19703:11;19691:8;:23;;:42;;;;;19730:3;19718:15;;:8;:15;;19691:42;19683:51;;;;19123:619;;;:::o;80615:83::-;80655:7;80682:8;;;;;;;;;;;80675:15;;80615:83;:::o;71366:344::-;71464:7;71699:3;71684:10;71678:3;:16;71666:8;71660:3;:14;:35;71659:43;;;;;;71652:50;;71366:344;;;;;:::o;15136:471::-;15194:7;15444:1;15439;:6;15435:47;;;15469:1;15462:8;;;;15435:47;15494:9;15510:1;15506;:5;15494:17;;15539:1;15534;15530;:5;;;;;;:10;15522:56;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;15598:1;15591:8;;;15136:471;;;;;:::o;16075:132::-;16133:7;16160:39;16164:1;16167;16160:39;;;;;;;;;;;;;;;;;:3;:39::i;:::-;16153:46;;16075:132;;;;:::o;71718:1270::-;71773:22;72591:18;72612:8;;72591:29;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;30:3:-1;22:6;14;1:33;99:1;93:3;85:6;81:16;74:27;137:4;133:9;126:4;121:3;117:14;113:30;106:37;;169:3;161:6;157:16;147:26;;72591:29:0;;;;;;;;72631:13;72647:8;;:15;;72631:31;;72903:42;72894:5;72887;72883:17;72877:24;72873:73;72863:83;;72974:6;72967:13;;;;71718:1270;:::o;16737:345::-;16823:7;16922:1;16918;:5;16925:12;16910:28;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;23:1:-1;8:100;33:3;30:1;27:10;8:100;;;99:1;94:3;90:11;84:18;80:1;75:3;71:11;64:39;52:2;49:1;45:10;40:15;;8:100;;;12:14;16910:28:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;16949:9;16965:1;16961;:5;;;;;;16949:17;;17073:1;17066:8;;;16737:345;;;;;:::o
Swarm Source
bzzr://2848c6af7096dc3957e78c764f97a1ae96193f25088cbc719ba4cd2bfd155227
Loading...
Loading
Loading...
Loading
Net Worth in USD
$0.00
Net Worth in ETH
0
Multichain Portfolio | 34 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.