Source Code
Overview
ETH Balance
0 ETH
ETH Value
$0.00| Transaction Hash |
|
Block
|
From
|
To
|
|||||
|---|---|---|---|---|---|---|---|---|---|
Latest 25 internal transactions (View All)
Advanced mode:
| Parent Transaction Hash | Block | From | To | |||
|---|---|---|---|---|---|---|
| 107553710 | 921 days ago | 0 ETH | ||||
| 107548287 | 921 days ago | 0 ETH | ||||
| 107539976 | 921 days ago | 0 ETH | ||||
| 107531434 | 922 days ago | 0 ETH | ||||
| 107525950 | 922 days ago | 0 ETH | ||||
| 107515607 | 922 days ago | 0 ETH | ||||
| 107423569 | 924 days ago | 0 ETH | ||||
| 107396799 | 925 days ago | 0 ETH | ||||
| 107395573 | 925 days ago | 0 ETH | ||||
| 107395521 | 925 days ago | 0 ETH | ||||
| 107395431 | 925 days ago | 0 ETH | ||||
| 107395396 | 925 days ago | 0 ETH | ||||
| 107395306 | 925 days ago | 0 ETH | ||||
| 107395269 | 925 days ago | 0 ETH | ||||
| 107378064 | 925 days ago | 0 ETH | ||||
| 107365145 | 926 days ago | 0 ETH | ||||
| 107349281 | 926 days ago | 0 ETH | ||||
| 107339452 | 926 days ago | 0 ETH | ||||
| 107310780 | 927 days ago | 0 ETH | ||||
| 107188723 | 930 days ago | 0 ETH | ||||
| 107153891 | 930 days ago | 0 ETH | ||||
| 107051718 | 933 days ago | 0 ETH | ||||
| 107051539 | 933 days ago | 0 ETH | ||||
| 106960658 | 935 days ago | 0 ETH | ||||
| 106701824 | 941 days ago | 0 ETH |
Cross-Chain Transactions
Loading...
Loading
This contract may be a proxy contract. Click on More Options and select Is this a proxy? to confirm and enable the "Read as Proxy" & "Write as Proxy" tabs.
Contract Name:
SBII721A
Compiler Version
v0.8.14+commit.80d49f37
Contract Source Code (Solidity)
/**
*Submitted for verification at optimistic.etherscan.io on 2022-06-05
*/
// SPDX-License-Identifier: MIT
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
// File: @openzeppelin/contracts/token/ERC721/IERC721Receiver.sol
// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC721/IERC721Receiver.sol)
pragma solidity ^0.8.0;
/**
* @title ERC721 token receiver interface
* @dev Interface for any contract that wants to support safeTransfers
* from ERC721 asset contracts.
*/
interface IERC721Receiver {
/**
* @dev Whenever an {IERC721} `tokenId` token is transferred to this contract via {IERC721-safeTransferFrom}
* by `operator` from `from`, this function is called.
*
* It must return its Solidity selector to confirm the token transfer.
* If any other value is returned or the interface is not implemented by the recipient, the transfer will be reverted.
*
* The selector can be obtained in Solidity with `IERC721Receiver.onERC721Received.selector`.
*/
function onERC721Received(
address operator,
address from,
uint256 tokenId,
bytes calldata data
) external returns (bytes4);
}
// File: ISBShipable.sol
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
pragma solidity 0.8.14;
interface ISBShipable {
function initialize(
bytes calldata initArg,
uint128 bip,
address feeReceiver
) external;
}
// File: ISBMintable.sol
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
pragma solidity 0.8.14;
interface ISBMintable {
function mintNext(address reciever, uint256 amount) external;
function mintTarget(address reciever, uint256 target) external;
}
// File: @openzeppelin/contracts/token/ERC20/IERC20.sol
// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)
pragma solidity ^0.8.0;
/**
* @dev Interface of the ERC20 standard as defined in the EIP.
*/
interface IERC20 {
/**
* @dev Emitted when `value` tokens are moved from one account (`from`) to
* another (`to`).
*
* Note that `value` may be zero.
*/
event Transfer(address indexed from, address indexed to, uint256 value);
/**
* @dev Emitted when the allowance of a `spender` for an `owner` is set by
* a call to {approve}. `value` is the new allowance.
*/
event Approval(address indexed owner, address indexed spender, uint256 value);
/**
* @dev Returns the 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 `to`.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* Emits a {Transfer} event.
*/
function transfer(address to, 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 `from` to `to` 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 from,
address to,
uint256 amount
) external returns (bool);
}
// File: @openzeppelin/contracts/utils/cryptography/MerkleProof.sol
// OpenZeppelin Contracts (last updated v4.6.0) (utils/cryptography/MerkleProof.sol)
pragma solidity ^0.8.0;
/**
* @dev These functions deal with verification of Merkle Trees proofs.
*
* The proofs can be generated using the JavaScript library
* https://github.com/miguelmota/merkletreejs[merkletreejs].
* Note: the hashing algorithm should be keccak256 and pair sorting should be enabled.
*
* See `test/utils/cryptography/MerkleProof.test.js` for some examples.
*
* WARNING: You should avoid using leaf values that are 64 bytes long prior to
* hashing, or use a hash function other than keccak256 for hashing leaves.
* This is because the concatenation of a sorted pair of internal nodes in
* the merkle tree could be reinterpreted as a leaf value.
*/
library MerkleProof {
/**
* @dev Returns true if a `leaf` can be proved to be a part of a Merkle tree
* defined by `root`. For this, a `proof` must be provided, containing
* sibling hashes on the branch from the leaf to the root of the tree. Each
* pair of leaves and each pair of pre-images are assumed to be sorted.
*/
function verify(
bytes32[] memory proof,
bytes32 root,
bytes32 leaf
) internal pure returns (bool) {
return processProof(proof, leaf) == root;
}
/**
* @dev Returns the rebuilt hash obtained by traversing a Merkle tree up
* from `leaf` using `proof`. A `proof` is valid if and only if the rebuilt
* hash matches the root of the tree. When processing the proof, the pairs
* of leafs & pre-images are assumed to be sorted.
*
* _Available since v4.4._
*/
function processProof(bytes32[] memory proof, bytes32 leaf) internal pure returns (bytes32) {
bytes32 computedHash = leaf;
for (uint256 i = 0; i < proof.length; i++) {
bytes32 proofElement = proof[i];
if (computedHash <= proofElement) {
// Hash(current computed hash + current element of the proof)
computedHash = _efficientHash(computedHash, proofElement);
} else {
// Hash(current element of the proof + current computed hash)
computedHash = _efficientHash(proofElement, computedHash);
}
}
return computedHash;
}
function _efficientHash(bytes32 a, bytes32 b) private pure returns (bytes32 value) {
assembly {
mstore(0x00, a)
mstore(0x20, b)
value := keccak256(0x00, 0x40)
}
}
}
// File: @openzeppelin/contracts/interfaces/IERC1271.sol
// OpenZeppelin Contracts v4.4.1 (interfaces/IERC1271.sol)
pragma solidity ^0.8.0;
/**
* @dev Interface of the ERC1271 standard signature validation method for
* contracts as defined in https://eips.ethereum.org/EIPS/eip-1271[ERC-1271].
*
* _Available since v4.1._
*/
interface IERC1271 {
/**
* @dev Should return whether the signature provided is valid for the provided data
* @param hash Hash of the data to be signed
* @param signature Signature byte array associated with _data
*/
function isValidSignature(bytes32 hash, bytes memory signature) external view returns (bytes4 magicValue);
}
// File: @openzeppelin/contracts/utils/Address.sol
// OpenZeppelin Contracts (last updated v4.5.0) (utils/Address.sol)
pragma solidity ^0.8.1;
/**
* @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
* ====
*
* [IMPORTANT]
* ====
* You shouldn't rely on `isContract` to protect against flash loan attacks!
*
* Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
* constructor.
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize/address.code.length, which returns 0
// for contracts in construction, since the code is only stored at the end
// of the constructor execution.
return account.code.length > 0;
}
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason, it is bubbled up by this
* function (like regular Solidity function calls).
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*
* _Available since v3.1._
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCall(target, data, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value
) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
require(isContract(target), "Address: call to non-contract");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
require(isContract(target), "Address: static call to non-contract");
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
return functionDelegateCall(target, data, "Address: low-level delegate call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
require(isContract(target), "Address: delegate call to non-contract");
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Tool to verifies that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}
}
// File: @openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol
// OpenZeppelin Contracts v4.4.1 (token/ERC20/utils/SafeERC20.sol)
pragma solidity ^0.8.0;
/**
* @title SafeERC20
* @dev Wrappers around ERC20 operations that throw on failure (when the token
* contract returns false). Tokens that return no value (and instead revert or
* throw on failure) are also supported, non-reverting calls are assumed to be
* successful.
* To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,
* which allows you to call the safe operations as `token.safeTransfer(...)`, etc.
*/
library SafeERC20 {
using Address for address;
function safeTransfer(
IERC20 token,
address to,
uint256 value
) internal {
_callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));
}
function safeTransferFrom(
IERC20 token,
address from,
address to,
uint256 value
) internal {
_callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));
}
/**
* @dev Deprecated. This function has issues similar to the ones found in
* {IERC20-approve}, and its usage is discouraged.
*
* Whenever possible, use {safeIncreaseAllowance} and
* {safeDecreaseAllowance} instead.
*/
function safeApprove(
IERC20 token,
address spender,
uint256 value
) internal {
// safeApprove should only be called when setting an initial allowance,
// or when resetting it to zero. To increase and decrease it, use
// 'safeIncreaseAllowance' and 'safeDecreaseAllowance'
require(
(value == 0) || (token.allowance(address(this), spender) == 0),
"SafeERC20: approve from non-zero to non-zero allowance"
);
_callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));
}
function safeIncreaseAllowance(
IERC20 token,
address spender,
uint256 value
) internal {
uint256 newAllowance = token.allowance(address(this), spender) + value;
_callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));
}
function safeDecreaseAllowance(
IERC20 token,
address spender,
uint256 value
) internal {
unchecked {
uint256 oldAllowance = token.allowance(address(this), spender);
require(oldAllowance >= value, "SafeERC20: decreased allowance below zero");
uint256 newAllowance = oldAllowance - value;
_callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));
}
}
/**
* @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
* on the return value: the return value is optional (but if data is returned, it must not be false).
* @param token The token targeted by the call.
* @param data The call data (encoded using abi.encode or one of its variants).
*/
function _callOptionalReturn(IERC20 token, bytes memory data) private {
// We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since
// we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that
// the target address contains contract code and also asserts for success in the low-level call.
bytes memory returndata = address(token).functionCall(data, "SafeERC20: low-level call failed");
if (returndata.length > 0) {
// Return data is optional
require(abi.decode(returndata, (bool)), "SafeERC20: ERC20 operation did not succeed");
}
}
}
// File: paymentUtil.sol
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
pragma solidity 0.8.14;
library paymentUtil {
using SafeERC20 for IERC20;
function processPayment(address token, uint256 amount) public {
if (token == address(0)) {
require(msg.value >= amount, "invalid payment");
} else {
IERC20(token).safeTransferFrom(msg.sender, address(this), amount);
}
}
}
// File: @openzeppelin/contracts/utils/Strings.sol
// OpenZeppelin Contracts v4.4.1 (utils/Strings.sol)
pragma solidity ^0.8.0;
/**
* @dev String operations.
*/
library Strings {
bytes16 private constant _HEX_SYMBOLS = "0123456789abcdef";
/**
* @dev Converts a `uint256` to its ASCII `string` decimal representation.
*/
function toString(uint256 value) internal pure returns (string memory) {
// Inspired by OraclizeAPI's implementation - MIT licence
// https://github.com/oraclize/ethereum-api/blob/b42146b063c7d6ee1358846c198246239e9360e8/oraclizeAPI_0.4.25.sol
if (value == 0) {
return "0";
}
uint256 temp = value;
uint256 digits;
while (temp != 0) {
digits++;
temp /= 10;
}
bytes memory buffer = new bytes(digits);
while (value != 0) {
digits -= 1;
buffer[digits] = bytes1(uint8(48 + uint256(value % 10)));
value /= 10;
}
return string(buffer);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation.
*/
function toHexString(uint256 value) internal pure returns (string memory) {
if (value == 0) {
return "0x00";
}
uint256 temp = value;
uint256 length = 0;
while (temp != 0) {
length++;
temp >>= 8;
}
return toHexString(value, length);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation with fixed length.
*/
function toHexString(uint256 value, uint256 length) internal pure returns (string memory) {
bytes memory buffer = new bytes(2 * length + 2);
buffer[0] = "0";
buffer[1] = "x";
for (uint256 i = 2 * length + 1; i > 1; --i) {
buffer[i] = _HEX_SYMBOLS[value & 0xf];
value >>= 4;
}
require(value == 0, "Strings: hex length insufficient");
return string(buffer);
}
}
// File: @openzeppelin/contracts/utils/cryptography/ECDSA.sol
// OpenZeppelin Contracts (last updated v4.5.0) (utils/cryptography/ECDSA.sol)
pragma solidity ^0.8.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 {
enum RecoverError {
NoError,
InvalidSignature,
InvalidSignatureLength,
InvalidSignatureS,
InvalidSignatureV
}
function _throwError(RecoverError error) private pure {
if (error == RecoverError.NoError) {
return; // no error: do nothing
} else if (error == RecoverError.InvalidSignature) {
revert("ECDSA: invalid signature");
} else if (error == RecoverError.InvalidSignatureLength) {
revert("ECDSA: invalid signature length");
} else if (error == RecoverError.InvalidSignatureS) {
revert("ECDSA: invalid signature 's' value");
} else if (error == RecoverError.InvalidSignatureV) {
revert("ECDSA: invalid signature 'v' value");
}
}
/**
* @dev Returns the address that signed a hashed message (`hash`) with
* `signature` or error string. 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.
*
* 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.
*
* Documentation for signature generation:
* - with https://web3js.readthedocs.io/en/v1.3.4/web3-eth-accounts.html#sign[Web3.js]
* - with https://docs.ethers.io/v5/api/signer/#Signer-signMessage[ethers]
*
* _Available since v4.3._
*/
function tryRecover(bytes32 hash, bytes memory signature) internal pure returns (address, RecoverError) {
// Check the signature length
// - case 65: r,s,v signature (standard)
// - case 64: r,vs signature (cf https://eips.ethereum.org/EIPS/eip-2098) _Available since v4.1._
if (signature.length == 65) {
bytes32 r;
bytes32 s;
uint8 v;
// ecrecover takes the signature parameters, and the only way to get them
// currently is to use assembly.
assembly {
r := mload(add(signature, 0x20))
s := mload(add(signature, 0x40))
v := byte(0, mload(add(signature, 0x60)))
}
return tryRecover(hash, v, r, s);
} else if (signature.length == 64) {
bytes32 r;
bytes32 vs;
// ecrecover takes the signature parameters, and the only way to get them
// currently is to use assembly.
assembly {
r := mload(add(signature, 0x20))
vs := mload(add(signature, 0x40))
}
return tryRecover(hash, r, vs);
} else {
return (address(0), RecoverError.InvalidSignatureLength);
}
}
/**
* @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.
*
* 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) {
(address recovered, RecoverError error) = tryRecover(hash, signature);
_throwError(error);
return recovered;
}
/**
* @dev Overload of {ECDSA-tryRecover} that receives the `r` and `vs` short-signature fields separately.
*
* See https://eips.ethereum.org/EIPS/eip-2098[EIP-2098 short signatures]
*
* _Available since v4.3._
*/
function tryRecover(
bytes32 hash,
bytes32 r,
bytes32 vs
) internal pure returns (address, RecoverError) {
bytes32 s = vs & bytes32(0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff);
uint8 v = uint8((uint256(vs) >> 255) + 27);
return tryRecover(hash, v, r, s);
}
/**
* @dev Overload of {ECDSA-recover} that receives the `r and `vs` short-signature fields separately.
*
* _Available since v4.2._
*/
function recover(
bytes32 hash,
bytes32 r,
bytes32 vs
) internal pure returns (address) {
(address recovered, RecoverError error) = tryRecover(hash, r, vs);
_throwError(error);
return recovered;
}
/**
* @dev Overload of {ECDSA-tryRecover} that receives the `v`,
* `r` and `s` signature fields separately.
*
* _Available since v4.3._
*/
function tryRecover(
bytes32 hash,
uint8 v,
bytes32 r,
bytes32 s
) internal pure returns (address, RecoverError) {
// 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 (301): 0 < s < secp256k1n ÷ 2 + 1, and for v in (302): 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), RecoverError.InvalidSignatureS);
}
if (v != 27 && v != 28) {
return (address(0), RecoverError.InvalidSignatureV);
}
// If the signature is valid (and not malleable), return the signer address
address signer = ecrecover(hash, v, r, s);
if (signer == address(0)) {
return (address(0), RecoverError.InvalidSignature);
}
return (signer, RecoverError.NoError);
}
/**
* @dev Overload of {ECDSA-recover} that receives the `v`,
* `r` and `s` signature fields separately.
*/
function recover(
bytes32 hash,
uint8 v,
bytes32 r,
bytes32 s
) internal pure returns (address) {
(address recovered, RecoverError error) = tryRecover(hash, v, r, s);
_throwError(error);
return recovered;
}
/**
* @dev Returns an Ethereum Signed Message, created from a `hash`. This
* produces hash corresponding to the one signed with the
* https://eth.wiki/json-rpc/API#eth_sign[`eth_sign`]
* JSON-RPC method as part of EIP-191.
*
* 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));
}
/**
* @dev Returns an Ethereum Signed Message, created from `s`. This
* produces hash corresponding to the one signed with the
* https://eth.wiki/json-rpc/API#eth_sign[`eth_sign`]
* JSON-RPC method as part of EIP-191.
*
* See {recover}.
*/
function toEthSignedMessageHash(bytes memory s) internal pure returns (bytes32) {
return keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n", Strings.toString(s.length), s));
}
/**
* @dev Returns an Ethereum Signed Typed Data, created from a
* `domainSeparator` and a `structHash`. This produces hash corresponding
* to the one signed with the
* https://eips.ethereum.org/EIPS/eip-712[`eth_signTypedData`]
* JSON-RPC method as part of EIP-712.
*
* See {recover}.
*/
function toTypedDataHash(bytes32 domainSeparator, bytes32 structHash) internal pure returns (bytes32) {
return keccak256(abi.encodePacked("\x19\x01", domainSeparator, structHash));
}
}
// File: @openzeppelin/contracts/utils/cryptography/SignatureChecker.sol
// OpenZeppelin Contracts (last updated v4.5.0) (utils/cryptography/SignatureChecker.sol)
pragma solidity ^0.8.0;
/**
* @dev Signature verification helper that can be used instead of `ECDSA.recover` to seamlessly support both ECDSA
* signatures from externally owned accounts (EOAs) as well as ERC1271 signatures from smart contract wallets like
* Argent and Gnosis Safe.
*
* _Available since v4.1._
*/
library SignatureChecker {
/**
* @dev Checks if a signature is valid for a given signer and data hash. If the signer is a smart contract, the
* signature is validated against that smart contract using ERC1271, otherwise it's validated using `ECDSA.recover`.
*
* NOTE: Unlike ECDSA signatures, contract signatures are revocable, and the outcome of this function can thus
* change through time. It could return true at block N and false at block N+1 (or the opposite).
*/
function isValidSignatureNow(
address signer,
bytes32 hash,
bytes memory signature
) internal view returns (bool) {
(address recovered, ECDSA.RecoverError error) = ECDSA.tryRecover(hash, signature);
if (error == ECDSA.RecoverError.NoError && recovered == signer) {
return true;
}
(bool success, bytes memory result) = signer.staticcall(
abi.encodeWithSelector(IERC1271.isValidSignature.selector, hash, signature)
);
return (success && result.length == 32 && abi.decode(result, (bytes4)) == IERC1271.isValidSignature.selector);
}
}
// File: @openzeppelin/contracts-upgradeable/utils/structs/EnumerableSetUpgradeable.sol
// OpenZeppelin Contracts (last updated v4.6.0) (utils/structs/EnumerableSet.sol)
pragma solidity ^0.8.0;
/**
* @dev Library for managing
* https://en.wikipedia.org/wiki/Set_(abstract_data_type)[sets] of primitive
* types.
*
* Sets have the following properties:
*
* - Elements are added, removed, and checked for existence in constant time
* (O(1)).
* - Elements are enumerated in O(n). No guarantees are made on the ordering.
*
* ```
* contract Example {
* // Add the library methods
* using EnumerableSet for EnumerableSet.AddressSet;
*
* // Declare a set state variable
* EnumerableSet.AddressSet private mySet;
* }
* ```
*
* As of v3.3.0, sets of type `bytes32` (`Bytes32Set`), `address` (`AddressSet`)
* and `uint256` (`UintSet`) are supported.
*/
library EnumerableSetUpgradeable {
// To implement this library for multiple types with as little code
// repetition as possible, we write it in terms of a generic Set type with
// bytes32 values.
// The Set implementation uses private functions, and user-facing
// implementations (such as AddressSet) are just wrappers around the
// underlying Set.
// This means that we can only create new EnumerableSets for types that fit
// in bytes32.
struct Set {
// Storage of set values
bytes32[] _values;
// Position of the value in the `values` array, plus 1 because index 0
// means a value is not in the set.
mapping(bytes32 => uint256) _indexes;
}
/**
* @dev Add a value to a set. O(1).
*
* Returns true if the value was added to the set, that is if it was not
* already present.
*/
function _add(Set storage set, bytes32 value) private returns (bool) {
if (!_contains(set, value)) {
set._values.push(value);
// The value is stored at length-1, but we add 1 to all indexes
// and use 0 as a sentinel value
set._indexes[value] = set._values.length;
return true;
} else {
return false;
}
}
/**
* @dev Removes a value from a set. O(1).
*
* Returns true if the value was removed from the set, that is if it was
* present.
*/
function _remove(Set storage set, bytes32 value) private returns (bool) {
// We read and store the value's index to prevent multiple reads from the same storage slot
uint256 valueIndex = set._indexes[value];
if (valueIndex != 0) {
// Equivalent to contains(set, value)
// To delete an element from the _values array in O(1), we swap the element to delete with the last one in
// the array, and then remove the last element (sometimes called as 'swap and pop').
// This modifies the order of the array, as noted in {at}.
uint256 toDeleteIndex = valueIndex - 1;
uint256 lastIndex = set._values.length - 1;
if (lastIndex != toDeleteIndex) {
bytes32 lastValue = set._values[lastIndex];
// Move the last value to the index where the value to delete is
set._values[toDeleteIndex] = lastValue;
// Update the index for the moved value
set._indexes[lastValue] = valueIndex; // Replace lastValue's index to valueIndex
}
// Delete the slot where the moved value was stored
set._values.pop();
// Delete the index for the deleted slot
delete set._indexes[value];
return true;
} else {
return false;
}
}
/**
* @dev Returns true if the value is in the set. O(1).
*/
function _contains(Set storage set, bytes32 value) private view returns (bool) {
return set._indexes[value] != 0;
}
/**
* @dev Returns the number of values on the set. O(1).
*/
function _length(Set storage set) private view returns (uint256) {
return set._values.length;
}
/**
* @dev Returns the value stored at position `index` in the set. O(1).
*
* Note that there are no guarantees on the ordering of values inside the
* array, and it may change when more values are added or removed.
*
* Requirements:
*
* - `index` must be strictly less than {length}.
*/
function _at(Set storage set, uint256 index) private view returns (bytes32) {
return set._values[index];
}
/**
* @dev Return the entire set in an array
*
* WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
* to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
* this function has an unbounded cost, and using it as part of a state-changing function may render the function
* uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
*/
function _values(Set storage set) private view returns (bytes32[] memory) {
return set._values;
}
// Bytes32Set
struct Bytes32Set {
Set _inner;
}
/**
* @dev Add a value to a set. O(1).
*
* Returns true if the value was added to the set, that is if it was not
* already present.
*/
function add(Bytes32Set storage set, bytes32 value) internal returns (bool) {
return _add(set._inner, value);
}
/**
* @dev Removes a value from a set. O(1).
*
* Returns true if the value was removed from the set, that is if it was
* present.
*/
function remove(Bytes32Set storage set, bytes32 value) internal returns (bool) {
return _remove(set._inner, value);
}
/**
* @dev Returns true if the value is in the set. O(1).
*/
function contains(Bytes32Set storage set, bytes32 value) internal view returns (bool) {
return _contains(set._inner, value);
}
/**
* @dev Returns the number of values in the set. O(1).
*/
function length(Bytes32Set storage set) internal view returns (uint256) {
return _length(set._inner);
}
/**
* @dev Returns the value stored at position `index` in the set. O(1).
*
* Note that there are no guarantees on the ordering of values inside the
* array, and it may change when more values are added or removed.
*
* Requirements:
*
* - `index` must be strictly less than {length}.
*/
function at(Bytes32Set storage set, uint256 index) internal view returns (bytes32) {
return _at(set._inner, index);
}
/**
* @dev Return the entire set in an array
*
* WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
* to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
* this function has an unbounded cost, and using it as part of a state-changing function may render the function
* uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
*/
function values(Bytes32Set storage set) internal view returns (bytes32[] memory) {
return _values(set._inner);
}
// AddressSet
struct AddressSet {
Set _inner;
}
/**
* @dev Add a value to a set. O(1).
*
* Returns true if the value was added to the set, that is if it was not
* already present.
*/
function add(AddressSet storage set, address value) internal returns (bool) {
return _add(set._inner, bytes32(uint256(uint160(value))));
}
/**
* @dev Removes a value from a set. O(1).
*
* Returns true if the value was removed from the set, that is if it was
* present.
*/
function remove(AddressSet storage set, address value) internal returns (bool) {
return _remove(set._inner, bytes32(uint256(uint160(value))));
}
/**
* @dev Returns true if the value is in the set. O(1).
*/
function contains(AddressSet storage set, address value) internal view returns (bool) {
return _contains(set._inner, bytes32(uint256(uint160(value))));
}
/**
* @dev Returns the number of values in the set. O(1).
*/
function length(AddressSet storage set) internal view returns (uint256) {
return _length(set._inner);
}
/**
* @dev Returns the value stored at position `index` in the set. O(1).
*
* Note that there are no guarantees on the ordering of values inside the
* array, and it may change when more values are added or removed.
*
* Requirements:
*
* - `index` must be strictly less than {length}.
*/
function at(AddressSet storage set, uint256 index) internal view returns (address) {
return address(uint160(uint256(_at(set._inner, index))));
}
/**
* @dev Return the entire set in an array
*
* WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
* to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
* this function has an unbounded cost, and using it as part of a state-changing function may render the function
* uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
*/
function values(AddressSet storage set) internal view returns (address[] memory) {
bytes32[] memory store = _values(set._inner);
address[] memory result;
assembly {
result := store
}
return result;
}
// UintSet
struct UintSet {
Set _inner;
}
/**
* @dev Add a value to a set. O(1).
*
* Returns true if the value was added to the set, that is if it was not
* already present.
*/
function add(UintSet storage set, uint256 value) internal returns (bool) {
return _add(set._inner, bytes32(value));
}
/**
* @dev Removes a value from a set. O(1).
*
* Returns true if the value was removed from the set, that is if it was
* present.
*/
function remove(UintSet storage set, uint256 value) internal returns (bool) {
return _remove(set._inner, bytes32(value));
}
/**
* @dev Returns true if the value is in the set. O(1).
*/
function contains(UintSet storage set, uint256 value) internal view returns (bool) {
return _contains(set._inner, bytes32(value));
}
/**
* @dev Returns the number of values on the set. O(1).
*/
function length(UintSet storage set) internal view returns (uint256) {
return _length(set._inner);
}
/**
* @dev Returns the value stored at position `index` in the set. O(1).
*
* Note that there are no guarantees on the ordering of values inside the
* array, and it may change when more values are added or removed.
*
* Requirements:
*
* - `index` must be strictly less than {length}.
*/
function at(UintSet storage set, uint256 index) internal view returns (uint256) {
return uint256(_at(set._inner, index));
}
/**
* @dev Return the entire set in an array
*
* WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
* to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
* this function has an unbounded cost, and using it as part of a state-changing function may render the function
* uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
*/
function values(UintSet storage set) internal view returns (uint256[] memory) {
bytes32[] memory store = _values(set._inner);
uint256[] memory result;
assembly {
result := store
}
return result;
}
}
// File: @openzeppelin/contracts-upgradeable/utils/introspection/IERC165Upgradeable.sol
// OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol)
pragma solidity ^0.8.0;
/**
* @dev Interface of the ERC165 standard, as defined in the
* https://eips.ethereum.org/EIPS/eip-165[EIP].
*
* Implementers can declare support of contract interfaces, which can then be
* queried by others ({ERC165Checker}).
*
* For an implementation, see {ERC165}.
*/
interface IERC165Upgradeable {
/**
* @dev Returns true if this contract implements the interface defined by
* `interfaceId`. See the corresponding
* https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]
* to learn more about how these ids are created.
*
* This function call must use less than 30 000 gas.
*/
function supportsInterface(bytes4 interfaceId) external view returns (bool);
}
// File: @openzeppelin/contracts-upgradeable/token/ERC721/IERC721Upgradeable.sol
// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC721/IERC721.sol)
pragma solidity ^0.8.0;
/**
* @dev Required interface of an ERC721 compliant contract.
*/
interface IERC721Upgradeable is IERC165Upgradeable {
/**
* @dev Emitted when `tokenId` token is transferred from `from` to `to`.
*/
event Transfer(address indexed from, address indexed to, uint256 indexed tokenId);
/**
* @dev Emitted when `owner` enables `approved` to manage the `tokenId` token.
*/
event Approval(address indexed owner, address indexed approved, uint256 indexed tokenId);
/**
* @dev Emitted when `owner` enables or disables (`approved`) `operator` to manage all of its assets.
*/
event ApprovalForAll(address indexed owner, address indexed operator, bool approved);
/**
* @dev Returns the number of tokens in ``owner``'s account.
*/
function balanceOf(address owner) external view returns (uint256 balance);
/**
* @dev Returns the owner of the `tokenId` token.
*
* Requirements:
*
* - `tokenId` must exist.
*/
function ownerOf(uint256 tokenId) external view returns (address owner);
/**
* @dev Safely transfers `tokenId` token from `from` to `to`.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must exist and be owned by `from`.
* - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}.
* - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer.
*
* Emits a {Transfer} event.
*/
function safeTransferFrom(
address from,
address to,
uint256 tokenId,
bytes calldata data
) external;
/**
* @dev Safely transfers `tokenId` token from `from` to `to`, checking first that contract recipients
* are aware of the ERC721 protocol to prevent tokens from being forever locked.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must exist and be owned by `from`.
* - If the caller is not `from`, it must be have been allowed to move this token by either {approve} or {setApprovalForAll}.
* - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer.
*
* Emits a {Transfer} event.
*/
function safeTransferFrom(
address from,
address to,
uint256 tokenId
) external;
/**
* @dev Transfers `tokenId` token from `from` to `to`.
*
* WARNING: Usage of this method is discouraged, use {safeTransferFrom} whenever possible.
*
* Requirements:
*
* - `from` cannot be the zero address.
* - `to` cannot be the zero address.
* - `tokenId` token must be owned by `from`.
* - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}.
*
* Emits a {Transfer} event.
*/
function transferFrom(
address from,
address to,
uint256 tokenId
) external;
/**
* @dev Gives permission to `to` to transfer `tokenId` token to another account.
* The approval is cleared when the token is transferred.
*
* Only a single account can be approved at a time, so approving the zero address clears previous approvals.
*
* Requirements:
*
* - The caller must own the token or be an approved operator.
* - `tokenId` must exist.
*
* Emits an {Approval} event.
*/
function approve(address to, uint256 tokenId) external;
/**
* @dev Approve or remove `operator` as an operator for the caller.
* Operators can call {transferFrom} or {safeTransferFrom} for any token owned by the caller.
*
* Requirements:
*
* - The `operator` cannot be the caller.
*
* Emits an {ApprovalForAll} event.
*/
function setApprovalForAll(address operator, bool _approved) external;
/**
* @dev Returns the account approved for `tokenId` token.
*
* Requirements:
*
* - `tokenId` must exist.
*/
function getApproved(uint256 tokenId) external view returns (address operator);
/**
* @dev Returns if the `operator` is allowed to manage all of the assets of `owner`.
*
* See {setApprovalForAll}
*/
function isApprovedForAll(address owner, address operator) external view returns (bool);
}
// File: @openzeppelin/contracts-upgradeable/token/ERC721/extensions/IERC721MetadataUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (token/ERC721/extensions/IERC721Metadata.sol)
pragma solidity ^0.8.0;
/**
* @title ERC-721 Non-Fungible Token Standard, optional metadata extension
* @dev See https://eips.ethereum.org/EIPS/eip-721
*/
interface IERC721MetadataUpgradeable is IERC721Upgradeable {
/**
* @dev Returns the token collection name.
*/
function name() external view returns (string memory);
/**
* @dev Returns the token collection symbol.
*/
function symbol() external view returns (string memory);
/**
* @dev Returns the Uniform Resource Identifier (URI) for `tokenId` token.
*/
function tokenURI(uint256 tokenId) external view returns (string memory);
}
// File: @openzeppelin/contracts-upgradeable/utils/StringsUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (utils/Strings.sol)
pragma solidity ^0.8.0;
/**
* @dev String operations.
*/
library StringsUpgradeable {
bytes16 private constant _HEX_SYMBOLS = "0123456789abcdef";
/**
* @dev Converts a `uint256` to its ASCII `string` decimal representation.
*/
function toString(uint256 value) internal pure returns (string memory) {
// Inspired by OraclizeAPI's implementation - MIT licence
// https://github.com/oraclize/ethereum-api/blob/b42146b063c7d6ee1358846c198246239e9360e8/oraclizeAPI_0.4.25.sol
if (value == 0) {
return "0";
}
uint256 temp = value;
uint256 digits;
while (temp != 0) {
digits++;
temp /= 10;
}
bytes memory buffer = new bytes(digits);
while (value != 0) {
digits -= 1;
buffer[digits] = bytes1(uint8(48 + uint256(value % 10)));
value /= 10;
}
return string(buffer);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation.
*/
function toHexString(uint256 value) internal pure returns (string memory) {
if (value == 0) {
return "0x00";
}
uint256 temp = value;
uint256 length = 0;
while (temp != 0) {
length++;
temp >>= 8;
}
return toHexString(value, length);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation with fixed length.
*/
function toHexString(uint256 value, uint256 length) internal pure returns (string memory) {
bytes memory buffer = new bytes(2 * length + 2);
buffer[0] = "0";
buffer[1] = "x";
for (uint256 i = 2 * length + 1; i > 1; --i) {
buffer[i] = _HEX_SYMBOLS[value & 0xf];
value >>= 4;
}
require(value == 0, "Strings: hex length insufficient");
return string(buffer);
}
}
// File: @openzeppelin/contracts-upgradeable/access/IAccessControlUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (access/IAccessControl.sol)
pragma solidity ^0.8.0;
/**
* @dev External interface of AccessControl declared to support ERC165 detection.
*/
interface IAccessControlUpgradeable {
/**
* @dev Emitted when `newAdminRole` is set as ``role``'s admin role, replacing `previousAdminRole`
*
* `DEFAULT_ADMIN_ROLE` is the starting admin for all roles, despite
* {RoleAdminChanged} not being emitted signaling this.
*
* _Available since v3.1._
*/
event RoleAdminChanged(bytes32 indexed role, bytes32 indexed previousAdminRole, bytes32 indexed newAdminRole);
/**
* @dev Emitted when `account` is granted `role`.
*
* `sender` is the account that originated the contract call, an admin role
* bearer except when using {AccessControl-_setupRole}.
*/
event RoleGranted(bytes32 indexed role, address indexed account, address indexed sender);
/**
* @dev Emitted when `account` is revoked `role`.
*
* `sender` is the account that originated the contract call:
* - if using `revokeRole`, it is the admin role bearer
* - if using `renounceRole`, it is the role bearer (i.e. `account`)
*/
event RoleRevoked(bytes32 indexed role, address indexed account, address indexed sender);
/**
* @dev Returns `true` if `account` has been granted `role`.
*/
function hasRole(bytes32 role, address account) external view returns (bool);
/**
* @dev Returns the admin role that controls `role`. See {grantRole} and
* {revokeRole}.
*
* To change a role's admin, use {AccessControl-_setRoleAdmin}.
*/
function getRoleAdmin(bytes32 role) external view returns (bytes32);
/**
* @dev Grants `role` to `account`.
*
* If `account` had not been already granted `role`, emits a {RoleGranted}
* event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function grantRole(bytes32 role, address account) external;
/**
* @dev Revokes `role` from `account`.
*
* If `account` had been granted `role`, emits a {RoleRevoked} event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function revokeRole(bytes32 role, address account) external;
/**
* @dev Revokes `role` from the calling account.
*
* Roles are often managed via {grantRole} and {revokeRole}: this function's
* purpose is to provide a mechanism for accounts to lose their privileges
* if they are compromised (such as when a trusted device is misplaced).
*
* If the calling account had been granted `role`, emits a {RoleRevoked}
* event.
*
* Requirements:
*
* - the caller must be `account`.
*/
function renounceRole(bytes32 role, address account) external;
}
// File: @openzeppelin/contracts-upgradeable/access/IAccessControlEnumerableUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (access/IAccessControlEnumerable.sol)
pragma solidity ^0.8.0;
/**
* @dev External interface of AccessControlEnumerable declared to support ERC165 detection.
*/
interface IAccessControlEnumerableUpgradeable is IAccessControlUpgradeable {
/**
* @dev Returns one of the accounts that have `role`. `index` must be a
* value between 0 and {getRoleMemberCount}, non-inclusive.
*
* Role bearers are not sorted in any particular way, and their ordering may
* change at any point.
*
* WARNING: When using {getRoleMember} and {getRoleMemberCount}, make sure
* you perform all queries on the same block. See the following
* https://forum.openzeppelin.com/t/iterating-over-elements-on-enumerableset-in-openzeppelin-contracts/2296[forum post]
* for more information.
*/
function getRoleMember(bytes32 role, uint256 index) external view returns (address);
/**
* @dev Returns the number of accounts that have `role`. Can be used
* together with {getRoleMember} to enumerate all bearers of a role.
*/
function getRoleMemberCount(bytes32 role) external view returns (uint256);
}
// File: @openzeppelin/contracts-upgradeable/utils/AddressUpgradeable.sol
// OpenZeppelin Contracts (last updated v4.5.0) (utils/Address.sol)
pragma solidity ^0.8.1;
/**
* @dev Collection of functions related to the address type
*/
library AddressUpgradeable {
/**
* @dev Returns true if `account` is a contract.
*
* [IMPORTANT]
* ====
* It is unsafe to assume that an address for which this function returns
* false is an externally-owned account (EOA) and not a contract.
*
* Among others, `isContract` will return false for the following
* types of addresses:
*
* - an externally-owned account
* - a contract in construction
* - an address where a contract will be created
* - an address where a contract lived, but was destroyed
* ====
*
* [IMPORTANT]
* ====
* You shouldn't rely on `isContract` to protect against flash loan attacks!
*
* Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
* constructor.
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize/address.code.length, which returns 0
// for contracts in construction, since the code is only stored at the end
// of the constructor execution.
return account.code.length > 0;
}
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason, it is bubbled up by this
* function (like regular Solidity function calls).
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*
* _Available since v3.1._
*/
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCall(target, data, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value
) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
require(isContract(target), "Address: call to non-contract");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
require(isContract(target), "Address: static call to non-contract");
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Tool to verifies that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}
}
// File: @openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol
// OpenZeppelin Contracts (last updated v4.6.0) (proxy/utils/Initializable.sol)
pragma solidity ^0.8.2;
/**
* @dev This is a base contract to aid in writing upgradeable contracts, or any kind of contract that will be deployed
* behind a proxy. Since proxied contracts do not make use of a constructor, it's common to move constructor logic to an
* external initializer function, usually called `initialize`. It then becomes necessary to protect this initializer
* function so it can only be called once. The {initializer} modifier provided by this contract will have this effect.
*
* The initialization functions use a version number. Once a version number is used, it is consumed and cannot be
* reused. This mechanism prevents re-execution of each "step" but allows the creation of new initialization steps in
* case an upgrade adds a module that needs to be initialized.
*
* For example:
*
* [.hljs-theme-light.nopadding]
* ```
* contract MyToken is ERC20Upgradeable {
* function initialize() initializer public {
* __ERC20_init("MyToken", "MTK");
* }
* }
* contract MyTokenV2 is MyToken, ERC20PermitUpgradeable {
* function initializeV2() reinitializer(2) public {
* __ERC20Permit_init("MyToken");
* }
* }
* ```
*
* TIP: To avoid leaving the proxy in an uninitialized state, the initializer function should be called as early as
* possible by providing the encoded function call as the `_data` argument to {ERC1967Proxy-constructor}.
*
* CAUTION: When used with inheritance, manual care must be taken to not invoke a parent initializer twice, or to ensure
* that all initializers are idempotent. This is not verified automatically as constructors are by Solidity.
*
* [CAUTION]
* ====
* Avoid leaving a contract uninitialized.
*
* An uninitialized contract can be taken over by an attacker. This applies to both a proxy and its implementation
* contract, which may impact the proxy. To prevent the implementation contract from being used, you should invoke
* the {_disableInitializers} function in the constructor to automatically lock it when it is deployed:
*
* [.hljs-theme-light.nopadding]
* ```
* /// @custom:oz-upgrades-unsafe-allow constructor
* constructor() {
* _disableInitializers();
* }
* ```
* ====
*/
abstract contract Initializable {
/**
* @dev Indicates that the contract has been initialized.
* @custom:oz-retyped-from bool
*/
uint8 private _initialized;
/**
* @dev Indicates that the contract is in the process of being initialized.
*/
bool private _initializing;
/**
* @dev Triggered when the contract has been initialized or reinitialized.
*/
event Initialized(uint8 version);
/**
* @dev A modifier that defines a protected initializer function that can be invoked at most once. In its scope,
* `onlyInitializing` functions can be used to initialize parent contracts. Equivalent to `reinitializer(1)`.
*/
modifier initializer() {
bool isTopLevelCall = _setInitializedVersion(1);
if (isTopLevelCall) {
_initializing = true;
}
_;
if (isTopLevelCall) {
_initializing = false;
emit Initialized(1);
}
}
/**
* @dev A modifier that defines a protected reinitializer function that can be invoked at most once, and only if the
* contract hasn't been initialized to a greater version before. In its scope, `onlyInitializing` functions can be
* used to initialize parent contracts.
*
* `initializer` is equivalent to `reinitializer(1)`, so a reinitializer may be used after the original
* initialization step. This is essential to configure modules that are added through upgrades and that require
* initialization.
*
* Note that versions can jump in increments greater than 1; this implies that if multiple reinitializers coexist in
* a contract, executing them in the right order is up to the developer or operator.
*/
modifier reinitializer(uint8 version) {
bool isTopLevelCall = _setInitializedVersion(version);
if (isTopLevelCall) {
_initializing = true;
}
_;
if (isTopLevelCall) {
_initializing = false;
emit Initialized(version);
}
}
/**
* @dev Modifier to protect an initialization function so that it can only be invoked by functions with the
* {initializer} and {reinitializer} modifiers, directly or indirectly.
*/
modifier onlyInitializing() {
require(_initializing, "Initializable: contract is not initializing");
_;
}
/**
* @dev Locks the contract, preventing any future reinitialization. This cannot be part of an initializer call.
* Calling this in the constructor of a contract will prevent that contract from being initialized or reinitialized
* to any version. It is recommended to use this to lock implementation contracts that are designed to be called
* through proxies.
*/
function _disableInitializers() internal virtual {
_setInitializedVersion(type(uint8).max);
}
function _setInitializedVersion(uint8 version) private returns (bool) {
// If the contract is initializing we ignore whether _initialized is set in order to support multiple
// inheritance patterns, but we only do this in the context of a constructor, and for the lowest level
// of initializers, because in other contexts the contract may have been reentered.
if (_initializing) {
require(
version == 1 && !AddressUpgradeable.isContract(address(this)),
"Initializable: contract is already initialized"
);
return false;
} else {
require(_initialized < version, "Initializable: contract is already initialized");
_initialized = version;
return true;
}
}
}
// File: @openzeppelin/contracts-upgradeable/utils/introspection/ERC165Upgradeable.sol
// OpenZeppelin Contracts v4.4.1 (utils/introspection/ERC165.sol)
pragma solidity ^0.8.0;
/**
* @dev Implementation of the {IERC165} interface.
*
* Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check
* for the additional interface id that will be supported. For example:
*
* ```solidity
* function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
* return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId);
* }
* ```
*
* Alternatively, {ERC165Storage} provides an easier to use but more expensive implementation.
*/
abstract contract ERC165Upgradeable is Initializable, IERC165Upgradeable {
function __ERC165_init() internal onlyInitializing {
}
function __ERC165_init_unchained() internal onlyInitializing {
}
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
return interfaceId == type(IERC165Upgradeable).interfaceId;
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[50] private __gap;
}
// File: @openzeppelin/contracts-upgradeable/utils/ContextUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)
pragma solidity ^0.8.0;
/**
* @dev Provides information about the current execution context, including the
* sender of the transaction and its data. While these are generally available
* via msg.sender and msg.data, they should not be accessed in such a direct
* manner, since when dealing with meta-transactions the account sending and
* paying for execution may not be the actual sender (as far as an application
* is concerned).
*
* This contract is only required for intermediate, library-like contracts.
*/
abstract contract ContextUpgradeable is Initializable {
function __Context_init() internal onlyInitializing {
}
function __Context_init_unchained() internal onlyInitializing {
}
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[50] private __gap;
}
// File: ERC721ASBUpgradable.sol
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
// ERC721A Creator: Chiru Labs
// GJ mate. interesting design :)
pragma solidity 0.8.14;
error ApprovalCallerNotOwnerNorApproved();
error ApprovalQueryForNonexistentToken();
error ApproveToCaller();
error ApprovalToCurrentOwner();
error BalanceQueryForZeroAddress();
error MintToZeroAddress();
error MintZeroQuantity();
error OwnerQueryForNonexistentToken();
error TransferCallerNotOwnerNorApproved();
error TransferFromIncorrectOwner();
error TransferToNonERC721ReceiverImplementer();
error TransferToZeroAddress();
error URIQueryForNonexistentToken();
error AllOwnershipsHaveBeenSet();
error QuantityMustBeNonZero();
error NoTokensMintedYet();
error InvalidQueryRange();
/**
* @dev Implementation of https://eips.ethereum.org/EIPS/eip-721[ERC721] Non-Fungible Token Standard, including
* the Metadata extension. Built to optimize for lower gas during batch mints.
*
* Assumes serials are sequentially minted starting at _startTokenId() (defaults to 0, e.g. 0, 1, 2, 3..).
*
* Assumes that an owner cannot have more than 2**64 - 1 (max value of uint64) of supply.
*
* Assumes that the maximum token id cannot exceed 2**256 - 1 (max value of uint256).
*
* Speedboat team modified version of ERC721A - upgradable
*/
contract ERC721ASBUpgradable is
Initializable,
ContextUpgradeable,
ERC165Upgradeable,
IERC721Upgradeable,
IERC721MetadataUpgradeable
{
using Address for address;
using Strings for uint256;
// Compiler will pack this into a single 256bit word.
struct TokenOwnership {
// The address of the owner.
address addr;
// Keeps track of the start time of ownership with minimal overhead for tokenomics.
uint64 startTimestamp;
// Whether the token has been burned.
bool burned;
}
// Compiler will pack this into a single 256bit word.
struct AddressData {
// Realistically, 2**64-1 is more than enough.
uint64 balance;
// Keeps track of mint count with minimal overhead for tokenomics.
uint64 numberMinted;
// Keeps track of burn count with minimal overhead for tokenomics.
uint64 numberBurned;
// For miscellaneous variable(s) pertaining to the address
// (e.g. number of whitelist mint slots used).
// If there are multiple variables, please pack them into a uint64.
uint64 aux;
}
// The tokenId of the next token to be minted.
uint256 internal _currentIndex;
// The number of tokens burned.
uint256 internal _burnCounter;
// Token name
string private _name;
// Token symbol
string private _symbol;
// Mapping from token ID to ownership details
// An empty struct value does not necessarily mean the token is unowned. See _ownershipOf implementation for details.
mapping(uint256 => TokenOwnership) internal _ownerships;
// Mapping owner address to address data
mapping(address => AddressData) private _addressData;
// Mapping from token ID to approved address
mapping(uint256 => address) private _tokenApprovals;
// Mapping from owner to operator approvals
mapping(address => mapping(address => bool)) private _operatorApprovals;
uint256 public nextOwnerToExplicitlySet;
/**
* @dev Explicitly set `owners` to eliminate loops in future calls of ownerOf().
* SB: change to public. anyone are free to pay the gas lol :P
*/
function setOwnersExplicit(uint256 quantity) public {
if (quantity == 0) revert QuantityMustBeNonZero();
if (_currentIndex == _startTokenId()) revert NoTokensMintedYet();
uint256 _nextOwnerToExplicitlySet = nextOwnerToExplicitlySet;
if (_nextOwnerToExplicitlySet == 0) {
_nextOwnerToExplicitlySet = _startTokenId();
}
if (_nextOwnerToExplicitlySet >= _currentIndex)
revert AllOwnershipsHaveBeenSet();
// Index underflow is impossible.
// Counter or index overflow is incredibly unrealistic.
unchecked {
uint256 endIndex = _nextOwnerToExplicitlySet + quantity - 1;
// Set the end index to be the last token index
if (endIndex + 1 > _currentIndex) {
endIndex = _currentIndex - 1;
}
for (uint256 i = _nextOwnerToExplicitlySet; i <= endIndex; i++) {
if (
_ownerships[i].addr == address(0) && !_ownerships[i].burned
) {
TokenOwnership memory ownership = _ownershipOf(i);
_ownerships[i].addr = ownership.addr;
_ownerships[i].startTimestamp = ownership.startTimestamp;
}
}
nextOwnerToExplicitlySet = endIndex + 1;
}
}
/**
* @dev Returns the `TokenOwnership` struct at `tokenId` without reverting.
*
* If the `tokenId` is out of bounds:
* - `addr` = `address(0)`
* - `startTimestamp` = `0`
* - `burned` = `false`
*
* If the `tokenId` is burned:
* - `addr` = `<Address of owner before token was burned>`
* - `startTimestamp` = `<Timestamp when token was burned>`
* - `burned = `true`
*
* Otherwise:
* - `addr` = `<Address of owner>`
* - `startTimestamp` = `<Timestamp of start of ownership>`
* - `burned = `false`
*/
function explicitOwnershipOf(uint256 tokenId)
public
view
returns (TokenOwnership memory)
{
TokenOwnership memory ownership;
if (tokenId < _startTokenId() || tokenId >= _currentIndex) {
return ownership;
}
ownership = _ownerships[tokenId];
if (ownership.burned) {
return ownership;
}
return _ownershipOf(tokenId);
}
/**
* @dev Returns an array of `TokenOwnership` structs at `tokenIds` in order.
* See {ERC721AQueryable-explicitOwnershipOf}
*/
function explicitOwnershipsOf(uint256[] memory tokenIds)
external
view
returns (TokenOwnership[] memory)
{
unchecked {
uint256 tokenIdsLength = tokenIds.length;
TokenOwnership[] memory ownerships = new TokenOwnership[](
tokenIdsLength
);
for (uint256 i; i != tokenIdsLength; ++i) {
ownerships[i] = explicitOwnershipOf(tokenIds[i]);
}
return ownerships;
}
}
/**
* @dev Returns an array of token IDs owned by `owner`,
* in the range [`start`, `stop`)
* (i.e. `start <= tokenId < stop`).
*
* This function allows for tokens to be queried if the collection
* grows too big for a single call of {ERC721AQueryable-tokensOfOwner}.
*
* Requirements:
*
* - `start` < `stop`
*/
function tokensOfOwnerIn(
address owner,
uint256 start,
uint256 stop
) external view returns (uint256[] memory) {
unchecked {
if (start >= stop) revert InvalidQueryRange();
uint256 tokenIdsIdx;
uint256 stopLimit = _currentIndex;
// Set `start = max(start, _startTokenId())`.
if (start < _startTokenId()) {
start = _startTokenId();
}
// Set `stop = min(stop, _currentIndex)`.
if (stop > stopLimit) {
stop = stopLimit;
}
uint256 tokenIdsMaxLength = balanceOf(owner);
// Set `tokenIdsMaxLength = min(balanceOf(owner), stop - start)`,
// to cater for cases where `balanceOf(owner)` is too big.
if (start < stop) {
uint256 rangeLength = stop - start;
if (rangeLength < tokenIdsMaxLength) {
tokenIdsMaxLength = rangeLength;
}
} else {
tokenIdsMaxLength = 0;
}
uint256[] memory tokenIds = new uint256[](tokenIdsMaxLength);
if (tokenIdsMaxLength == 0) {
return tokenIds;
}
// We need to call `explicitOwnershipOf(start)`,
// because the slot at `start` may not be initialized.
TokenOwnership memory ownership = explicitOwnershipOf(start);
address currOwnershipAddr;
// If the starting slot exists (i.e. not burned), initialize `currOwnershipAddr`.
// `ownership.address` will not be zero, as `start` is clamped to the valid token ID range.
if (!ownership.burned) {
currOwnershipAddr = ownership.addr;
}
for (
uint256 i = start;
i != stop && tokenIdsIdx != tokenIdsMaxLength;
++i
) {
ownership = _ownerships[i];
if (ownership.burned) {
continue;
}
if (ownership.addr != address(0)) {
currOwnershipAddr = ownership.addr;
}
if (currOwnershipAddr == owner) {
tokenIds[tokenIdsIdx++] = i;
}
}
// Downsize the array to fit.
assembly {
mstore(tokenIds, tokenIdsIdx)
}
return tokenIds;
}
}
/**
* @dev Returns an array of token IDs owned by `owner`.
*
* This function scans the ownership mapping and is O(totalSupply) in complexity.
* It is meant to be called off-chain.
*
* See {ERC721AQueryable-tokensOfOwnerIn} for splitting the scan into
* multiple smaller scans if the collection is large enough to cause
* an out-of-gas error (10K pfp collections should be fine).
*/
function tokensOfOwner(address owner)
public
view
returns (uint256[] memory)
{
unchecked {
uint256 tokenIdsIdx;
address currOwnershipAddr;
uint256 tokenIdsLength = balanceOf(owner);
uint256[] memory tokenIds = new uint256[](tokenIdsLength);
TokenOwnership memory ownership;
for (
uint256 i = _startTokenId();
tokenIdsIdx != tokenIdsLength;
++i
) {
ownership = _ownerships[i];
if (ownership.burned) {
continue;
}
if (ownership.addr != address(0)) {
currOwnershipAddr = ownership.addr;
}
if (currOwnershipAddr == owner) {
tokenIds[tokenIdsIdx++] = i;
}
}
return tokenIds;
}
}
function __ERC721A_init(string memory name_, string memory symbol_) public {
__Context_init_unchained();
__ERC165_init_unchained();
_name = name_;
_symbol = symbol_;
_currentIndex = _startTokenId();
}
/**
* To change the starting tokenId, please override this function.
*/
function _startTokenId() internal view virtual returns (uint256) {
return 1; // SB: change to start from 1 - modified from original 0. since others SB's code reserve 0 for a random stuff
}
/**
* @dev Burned tokens are calculated here, use _totalMinted() if you want to count just minted tokens.
*/
function totalSupply() public view returns (uint256) {
// Counter underflow is impossible as _burnCounter cannot be incremented
// more than _currentIndex - _startTokenId() times
unchecked {
return _currentIndex - _burnCounter - _startTokenId();
}
}
/**
* Returns the total amount of tokens minted in the contract.
*/
function _totalMinted() internal view returns (uint256) {
// Counter underflow is impossible as _currentIndex does not decrement,
// and it is initialized to _startTokenId()
unchecked {
return _currentIndex - _startTokenId();
}
}
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(bytes4 interfaceId)
public
view
virtual
override(ERC165Upgradeable, IERC165Upgradeable)
returns (bool)
{
return
interfaceId == type(IERC721Upgradeable).interfaceId ||
interfaceId == type(IERC721MetadataUpgradeable).interfaceId ||
super.supportsInterface(interfaceId);
}
/**
* @dev See {IERC721-balanceOf}.
*/
function balanceOf(address owner) public view override returns (uint256) {
if (owner == address(0)) revert BalanceQueryForZeroAddress();
return uint256(_addressData[owner].balance);
}
/**
* Returns the number of tokens minted by `owner`.
*/
function _numberMinted(address owner) internal view returns (uint256) {
return uint256(_addressData[owner].numberMinted);
}
/**
* Returns the number of tokens burned by or on behalf of `owner`.
*/
function _numberBurned(address owner) internal view returns (uint256) {
return uint256(_addressData[owner].numberBurned);
}
/**
* Returns the auxillary data for `owner`. (e.g. number of whitelist mint slots used).
*/
function _getAux(address owner) internal view returns (uint64) {
return _addressData[owner].aux;
}
/**
* Sets the auxillary data for `owner`. (e.g. number of whitelist mint slots used).
* If there are multiple variables, please pack them into a uint64.
*/
function _setAux(address owner, uint64 aux) internal {
_addressData[owner].aux = aux;
}
/**
* Gas spent here starts off proportional to the maximum mint batch size.
* It gradually moves to O(1) as tokens get transferred around in the collection over time.
*/
function _ownershipOf(uint256 tokenId)
internal
view
returns (TokenOwnership memory)
{
uint256 curr = tokenId;
unchecked {
if (_startTokenId() <= curr && curr < _currentIndex) {
TokenOwnership memory ownership = _ownerships[curr];
if (!ownership.burned) {
if (ownership.addr != address(0)) {
return ownership;
}
// Invariant:
// There will always be an ownership that has an address and is not burned
// before an ownership that does not have an address and is not burned.
// Hence, curr will not underflow.
while (true) {
curr--;
ownership = _ownerships[curr];
if (ownership.addr != address(0)) {
return ownership;
}
}
}
}
}
revert OwnerQueryForNonexistentToken();
}
/**
* @dev See {IERC721-ownerOf}.
*/
function ownerOf(uint256 tokenId) public view override returns (address) {
return _ownershipOf(tokenId).addr;
}
/**
* @dev See {IERC721Metadata-name}.
*/
function name() public view virtual override returns (string memory) {
return _name;
}
/**
* @dev See {IERC721Metadata-symbol}.
*/
function symbol() public view virtual override returns (string memory) {
return _symbol;
}
/**
* @dev See {IERC721Metadata-tokenURI}.
*/
function tokenURI(uint256 tokenId)
public
view
virtual
override
returns (string memory)
{
if (!_exists(tokenId)) revert URIQueryForNonexistentToken();
string memory baseURI = _baseURI();
return
bytes(baseURI).length != 0
? string(abi.encodePacked(baseURI, tokenId.toString()))
: "";
}
/**
* @dev Base URI for computing {tokenURI}. If set, the resulting URI for each
* token will be the concatenation of the `baseURI` and the `tokenId`. Empty
* by default, can be overriden in child contracts.
*/
function _baseURI() internal view virtual returns (string memory) {
return "";
}
/**
* @dev See {IERC721-approve}.
*/
function approve(address to, uint256 tokenId) public override {
address owner = ownerOf(tokenId);
if (to == owner) revert ApprovalToCurrentOwner();
if (_msgSender() != owner && !isApprovedForAll(owner, _msgSender())) {
revert ApprovalCallerNotOwnerNorApproved();
}
_approve(to, tokenId, owner);
}
/**
* @dev See {IERC721-getApproved}.
*/
function getApproved(uint256 tokenId)
public
view
override
returns (address)
{
if (!_exists(tokenId)) revert ApprovalQueryForNonexistentToken();
return _tokenApprovals[tokenId];
}
/**
* @dev See {IERC721-setApprovalForAll}.
*/
function setApprovalForAll(address operator, bool approved)
public
virtual
override
{
if (operator == _msgSender()) revert ApproveToCaller();
_operatorApprovals[_msgSender()][operator] = approved;
emit ApprovalForAll(_msgSender(), operator, approved);
}
/**
* @dev See {IERC721-isApprovedForAll}.
*/
function isApprovedForAll(address owner, address operator)
public
view
virtual
override
returns (bool)
{
return _operatorApprovals[owner][operator];
}
/**
* @dev See {IERC721-transferFrom}.
*/
function transferFrom(
address from,
address to,
uint256 tokenId
) public virtual override {
_transfer(from, to, tokenId);
}
/**
* @dev See {IERC721-safeTransferFrom}.
*/
function safeTransferFrom(
address from,
address to,
uint256 tokenId
) public virtual override {
safeTransferFrom(from, to, tokenId, "");
}
/**
* @dev See {IERC721-safeTransferFrom}.
*/
function safeTransferFrom(
address from,
address to,
uint256 tokenId,
bytes memory _data
) public virtual override {
_transfer(from, to, tokenId);
if (
to.isContract() &&
!_checkContractOnERC721Received(from, to, tokenId, _data)
) {
revert TransferToNonERC721ReceiverImplementer();
}
}
/**
* @dev Returns whether `tokenId` exists.
*
* Tokens can be managed by their owner or approved accounts via {approve} or {setApprovalForAll}.
*
* Tokens start existing when they are minted (`_mint`),
*/
function _exists(uint256 tokenId) internal view returns (bool) {
return
_startTokenId() <= tokenId &&
tokenId < _currentIndex &&
!_ownerships[tokenId].burned;
}
/**
* @dev Equivalent to `_safeMint(to, quantity, '')`.
*/
function _safeMint(address to, uint256 quantity) internal {
_safeMint(to, quantity, "");
}
/**
* @dev Safely mints `quantity` tokens and transfers them to `to`.
*
* Requirements:
*
* - If `to` refers to a smart contract, it must implement
* {IERC721Receiver-onERC721Received}, which is called for each safe transfer.
* - `quantity` must be greater than 0.
*
* Emits a {Transfer} event.
*/
function _safeMint(
address to,
uint256 quantity,
bytes memory _data
) internal {
uint256 startTokenId = _currentIndex;
if (to == address(0)) revert MintToZeroAddress();
if (quantity == 0) revert MintZeroQuantity();
_beforeTokenTransfers(address(0), to, startTokenId, quantity);
// Overflows are incredibly unrealistic.
// balance or numberMinted overflow if current value of either + quantity > 1.8e19 (2**64) - 1
// updatedIndex overflows if _currentIndex + quantity > 1.2e77 (2**256) - 1
unchecked {
_addressData[to].balance += uint64(quantity);
_addressData[to].numberMinted += uint64(quantity);
_ownerships[startTokenId].addr = to;
_ownerships[startTokenId].startTimestamp = uint64(block.timestamp);
uint256 updatedIndex = startTokenId;
uint256 end = updatedIndex + quantity;
if (to.isContract()) {
do {
emit Transfer(address(0), to, updatedIndex);
if (
!_checkContractOnERC721Received(
address(0),
to,
updatedIndex++,
_data
)
) {
revert TransferToNonERC721ReceiverImplementer();
}
} while (updatedIndex != end);
// Reentrancy protection
if (_currentIndex != startTokenId) revert();
} else {
do {
emit Transfer(address(0), to, updatedIndex++);
} while (updatedIndex != end);
}
_currentIndex = updatedIndex;
}
_afterTokenTransfers(address(0), to, startTokenId, quantity);
}
/**
* @dev Mints `quantity` tokens and transfers them to `to`.
*
* Requirements:
*
* - `to` cannot be the zero address.
* - `quantity` must be greater than 0.
*
* Emits a {Transfer} event.
*/
function _mint(address to, uint256 quantity) internal {
uint256 startTokenId = _currentIndex;
if (to == address(0)) revert MintToZeroAddress();
if (quantity == 0) revert MintZeroQuantity();
_beforeTokenTransfers(address(0), to, startTokenId, quantity);
// Overflows are incredibly unrealistic.
// balance or numberMinted overflow if current value of either + quantity > 1.8e19 (2**64) - 1
// updatedIndex overflows if _currentIndex + quantity > 1.2e77 (2**256) - 1
unchecked {
_addressData[to].balance += uint64(quantity);
_addressData[to].numberMinted += uint64(quantity);
_ownerships[startTokenId].addr = to;
_ownerships[startTokenId].startTimestamp = uint64(block.timestamp);
uint256 updatedIndex = startTokenId;
uint256 end = updatedIndex + quantity;
do {
emit Transfer(address(0), to, updatedIndex++);
} while (updatedIndex != end);
_currentIndex = updatedIndex;
}
_afterTokenTransfers(address(0), to, startTokenId, quantity);
}
/**
* @dev Transfers `tokenId` from `from` to `to`.
*
* Requirements:
*
* - `to` cannot be the zero address.
* - `tokenId` token must be owned by `from`.
*
* Emits a {Transfer} event.
*/
function _transfer(
address from,
address to,
uint256 tokenId
) private {
TokenOwnership memory prevOwnership = _ownershipOf(tokenId);
if (prevOwnership.addr != from) revert TransferFromIncorrectOwner();
bool isApprovedOrOwner = (_msgSender() == from ||
isApprovedForAll(from, _msgSender()) ||
getApproved(tokenId) == _msgSender());
if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved();
if (to == address(0)) revert TransferToZeroAddress();
_beforeTokenTransfers(from, to, tokenId, 1);
// Clear approvals from the previous owner
_approve(address(0), tokenId, from);
// Underflow of the sender's balance is impossible because we check for
// ownership above and the recipient's balance can't realistically overflow.
// Counter overflow is incredibly unrealistic as tokenId would have to be 2**256.
unchecked {
_addressData[from].balance -= 1;
_addressData[to].balance += 1;
TokenOwnership storage currSlot = _ownerships[tokenId];
currSlot.addr = to;
currSlot.startTimestamp = uint64(block.timestamp);
// If the ownership slot of tokenId+1 is not explicitly set, that means the transfer initiator owns it.
// Set the slot of tokenId+1 explicitly in storage to maintain correctness for ownerOf(tokenId+1) calls.
uint256 nextTokenId = tokenId + 1;
TokenOwnership storage nextSlot = _ownerships[nextTokenId];
if (nextSlot.addr == address(0)) {
// This will suffice for checking _exists(nextTokenId),
// as a burned slot cannot contain the zero address.
if (nextTokenId != _currentIndex) {
nextSlot.addr = from;
nextSlot.startTimestamp = prevOwnership.startTimestamp;
}
}
}
emit Transfer(from, to, tokenId);
_afterTokenTransfers(from, to, tokenId, 1);
}
/**
* @dev Equivalent to `_burn(tokenId, false)`.
*/
function _burn(uint256 tokenId) internal virtual {
_burn(tokenId, false);
}
/**
* @dev Destroys `tokenId`.
* The approval is cleared when the token is burned.
*
* Requirements:
*
* - `tokenId` must exist.
*
* Emits a {Transfer} event.
*/
function _burn(uint256 tokenId, bool approvalCheck) internal virtual {
TokenOwnership memory prevOwnership = _ownershipOf(tokenId);
address from = prevOwnership.addr;
if (approvalCheck) {
bool isApprovedOrOwner = (_msgSender() == from ||
isApprovedForAll(from, _msgSender()) ||
getApproved(tokenId) == _msgSender());
if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved();
}
_beforeTokenTransfers(from, address(0), tokenId, 1);
// Clear approvals from the previous owner
_approve(address(0), tokenId, from);
// Underflow of the sender's balance is impossible because we check for
// ownership above and the recipient's balance can't realistically overflow.
// Counter overflow is incredibly unrealistic as tokenId would have to be 2**256.
unchecked {
AddressData storage addressData = _addressData[from];
addressData.balance -= 1;
addressData.numberBurned += 1;
// Keep track of who burned the token, and the timestamp of burning.
TokenOwnership storage currSlot = _ownerships[tokenId];
currSlot.addr = from;
currSlot.startTimestamp = uint64(block.timestamp);
currSlot.burned = true;
// If the ownership slot of tokenId+1 is not explicitly set, that means the burn initiator owns it.
// Set the slot of tokenId+1 explicitly in storage to maintain correctness for ownerOf(tokenId+1) calls.
uint256 nextTokenId = tokenId + 1;
TokenOwnership storage nextSlot = _ownerships[nextTokenId];
if (nextSlot.addr == address(0)) {
// This will suffice for checking _exists(nextTokenId),
// as a burned slot cannot contain the zero address.
if (nextTokenId != _currentIndex) {
nextSlot.addr = from;
nextSlot.startTimestamp = prevOwnership.startTimestamp;
}
}
}
emit Transfer(from, address(0), tokenId);
_afterTokenTransfers(from, address(0), tokenId, 1);
// Overflow not possible, as _burnCounter cannot be exceed _currentIndex times.
unchecked {
_burnCounter++;
}
}
/**
* @dev Approve `to` to operate on `tokenId`
*
* Emits a {Approval} event.
*/
function _approve(
address to,
uint256 tokenId,
address owner
) private {
_tokenApprovals[tokenId] = to;
emit Approval(owner, to, tokenId);
}
/**
* @dev Internal function to invoke {IERC721Receiver-onERC721Received} on a target contract.
*
* @param from address representing the previous owner of the given token ID
* @param to target address that will receive the tokens
* @param tokenId uint256 ID of the token to be transferred
* @param _data bytes optional data to send along with the call
* @return bool whether the call correctly returned the expected magic value
*/
function _checkContractOnERC721Received(
address from,
address to,
uint256 tokenId,
bytes memory _data
) private returns (bool) {
try
IERC721Receiver(to).onERC721Received(
_msgSender(),
from,
tokenId,
_data
)
returns (bytes4 retval) {
return retval == IERC721Receiver(to).onERC721Received.selector;
} catch (bytes memory reason) {
if (reason.length == 0) {
revert TransferToNonERC721ReceiverImplementer();
} else {
assembly {
revert(add(32, reason), mload(reason))
}
}
}
}
/**
* @dev Hook that is called before a set of serially-ordered token ids are about to be transferred. This includes minting.
* And also called before burning one token.
*
* startTokenId - the first token id to be transferred
* quantity - the amount to be transferred
*
* Calling conditions:
*
* - When `from` and `to` are both non-zero, `from`'s `tokenId` will be
* transferred to `to`.
* - When `from` is zero, `tokenId` will be minted for `to`.
* - When `to` is zero, `tokenId` will be burned by `from`.
* - `from` and `to` are never both zero.
*/
function _beforeTokenTransfers(
address from,
address to,
uint256 startTokenId,
uint256 quantity
) internal virtual {}
/**
* @dev Hook that is called after a set of serially-ordered token ids have been transferred. This includes
* minting.
* And also called after one token has been burned.
*
* startTokenId - the first token id to be transferred
* quantity - the amount to be transferred
*
* Calling conditions:
*
* - When `from` and `to` are both non-zero, `from`'s `tokenId` has been
* transferred to `to`.
* - When `from` is zero, `tokenId` has been minted for `to`.
* - When `to` is zero, `tokenId` has been burned by `from`.
* - `from` and `to` are never both zero.
*/
function _afterTokenTransfers(
address from,
address to,
uint256 startTokenId,
uint256 quantity
) internal virtual {}
}
// File: @openzeppelin/contracts-upgradeable/access/AccessControlUpgradeable.sol
// OpenZeppelin Contracts (last updated v4.6.0) (access/AccessControl.sol)
pragma solidity ^0.8.0;
/**
* @dev Contract module that allows children to implement role-based access
* control mechanisms. This is a lightweight version that doesn't allow enumerating role
* members except through off-chain means by accessing the contract event logs. Some
* applications may benefit from on-chain enumerability, for those cases see
* {AccessControlEnumerable}.
*
* Roles are referred to by their `bytes32` identifier. These should be exposed
* in the external API and be unique. The best way to achieve this is by
* using `public constant` hash digests:
*
* ```
* bytes32 public constant MY_ROLE = keccak256("MY_ROLE");
* ```
*
* Roles can be used to represent a set of permissions. To restrict access to a
* function call, use {hasRole}:
*
* ```
* function foo() public {
* require(hasRole(MY_ROLE, msg.sender));
* ...
* }
* ```
*
* Roles can be granted and revoked dynamically via the {grantRole} and
* {revokeRole} functions. Each role has an associated admin role, and only
* accounts that have a role's admin role can call {grantRole} and {revokeRole}.
*
* By default, the admin role for all roles is `DEFAULT_ADMIN_ROLE`, which means
* that only accounts with this role will be able to grant or revoke other
* roles. More complex role relationships can be created by using
* {_setRoleAdmin}.
*
* WARNING: The `DEFAULT_ADMIN_ROLE` is also its own admin: it has permission to
* grant and revoke this role. Extra precautions should be taken to secure
* accounts that have been granted it.
*/
abstract contract AccessControlUpgradeable is Initializable, ContextUpgradeable, IAccessControlUpgradeable, ERC165Upgradeable {
function __AccessControl_init() internal onlyInitializing {
}
function __AccessControl_init_unchained() internal onlyInitializing {
}
struct RoleData {
mapping(address => bool) members;
bytes32 adminRole;
}
mapping(bytes32 => RoleData) private _roles;
bytes32 public constant DEFAULT_ADMIN_ROLE = 0x00;
/**
* @dev Modifier that checks that an account has a specific role. Reverts
* with a standardized message including the required role.
*
* The format of the revert reason is given by the following regular expression:
*
* /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
*
* _Available since v4.1._
*/
modifier onlyRole(bytes32 role) {
_checkRole(role);
_;
}
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
return interfaceId == type(IAccessControlUpgradeable).interfaceId || super.supportsInterface(interfaceId);
}
/**
* @dev Returns `true` if `account` has been granted `role`.
*/
function hasRole(bytes32 role, address account) public view virtual override returns (bool) {
return _roles[role].members[account];
}
/**
* @dev Revert with a standard message if `_msgSender()` is missing `role`.
* Overriding this function changes the behavior of the {onlyRole} modifier.
*
* Format of the revert message is described in {_checkRole}.
*
* _Available since v4.6._
*/
function _checkRole(bytes32 role) internal view virtual {
_checkRole(role, _msgSender());
}
/**
* @dev Revert with a standard message if `account` is missing `role`.
*
* The format of the revert reason is given by the following regular expression:
*
* /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
*/
function _checkRole(bytes32 role, address account) internal view virtual {
if (!hasRole(role, account)) {
revert(
string(
abi.encodePacked(
"AccessControl: account ",
StringsUpgradeable.toHexString(uint160(account), 20),
" is missing role ",
StringsUpgradeable.toHexString(uint256(role), 32)
)
)
);
}
}
/**
* @dev Returns the admin role that controls `role`. See {grantRole} and
* {revokeRole}.
*
* To change a role's admin, use {_setRoleAdmin}.
*/
function getRoleAdmin(bytes32 role) public view virtual override returns (bytes32) {
return _roles[role].adminRole;
}
/**
* @dev Grants `role` to `account`.
*
* If `account` had not been already granted `role`, emits a {RoleGranted}
* event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function grantRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) {
_grantRole(role, account);
}
/**
* @dev Revokes `role` from `account`.
*
* If `account` had been granted `role`, emits a {RoleRevoked} event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function revokeRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) {
_revokeRole(role, account);
}
/**
* @dev Revokes `role` from the calling account.
*
* Roles are often managed via {grantRole} and {revokeRole}: this function's
* purpose is to provide a mechanism for accounts to lose their privileges
* if they are compromised (such as when a trusted device is misplaced).
*
* If the calling account had been revoked `role`, emits a {RoleRevoked}
* event.
*
* Requirements:
*
* - the caller must be `account`.
*/
function renounceRole(bytes32 role, address account) public virtual override {
require(account == _msgSender(), "AccessControl: can only renounce roles for self");
_revokeRole(role, account);
}
/**
* @dev Grants `role` to `account`.
*
* If `account` had not been already granted `role`, emits a {RoleGranted}
* event. Note that unlike {grantRole}, this function doesn't perform any
* checks on the calling account.
*
* [WARNING]
* ====
* This function should only be called from the constructor when setting
* up the initial roles for the system.
*
* Using this function in any other way is effectively circumventing the admin
* system imposed by {AccessControl}.
* ====
*
* NOTE: This function is deprecated in favor of {_grantRole}.
*/
function _setupRole(bytes32 role, address account) internal virtual {
_grantRole(role, account);
}
/**
* @dev Sets `adminRole` as ``role``'s admin role.
*
* Emits a {RoleAdminChanged} event.
*/
function _setRoleAdmin(bytes32 role, bytes32 adminRole) internal virtual {
bytes32 previousAdminRole = getRoleAdmin(role);
_roles[role].adminRole = adminRole;
emit RoleAdminChanged(role, previousAdminRole, adminRole);
}
/**
* @dev Grants `role` to `account`.
*
* Internal function without access restriction.
*/
function _grantRole(bytes32 role, address account) internal virtual {
if (!hasRole(role, account)) {
_roles[role].members[account] = true;
emit RoleGranted(role, account, _msgSender());
}
}
/**
* @dev Revokes `role` from `account`.
*
* Internal function without access restriction.
*/
function _revokeRole(bytes32 role, address account) internal virtual {
if (hasRole(role, account)) {
_roles[role].members[account] = false;
emit RoleRevoked(role, account, _msgSender());
}
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[49] private __gap;
}
// File: @openzeppelin/contracts-upgradeable/access/AccessControlEnumerableUpgradeable.sol
// OpenZeppelin Contracts (last updated v4.5.0) (access/AccessControlEnumerable.sol)
pragma solidity ^0.8.0;
/**
* @dev Extension of {AccessControl} that allows enumerating the members of each role.
*/
abstract contract AccessControlEnumerableUpgradeable is Initializable, IAccessControlEnumerableUpgradeable, AccessControlUpgradeable {
function __AccessControlEnumerable_init() internal onlyInitializing {
}
function __AccessControlEnumerable_init_unchained() internal onlyInitializing {
}
using EnumerableSetUpgradeable for EnumerableSetUpgradeable.AddressSet;
mapping(bytes32 => EnumerableSetUpgradeable.AddressSet) private _roleMembers;
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
return interfaceId == type(IAccessControlEnumerableUpgradeable).interfaceId || super.supportsInterface(interfaceId);
}
/**
* @dev Returns one of the accounts that have `role`. `index` must be a
* value between 0 and {getRoleMemberCount}, non-inclusive.
*
* Role bearers are not sorted in any particular way, and their ordering may
* change at any point.
*
* WARNING: When using {getRoleMember} and {getRoleMemberCount}, make sure
* you perform all queries on the same block. See the following
* https://forum.openzeppelin.com/t/iterating-over-elements-on-enumerableset-in-openzeppelin-contracts/2296[forum post]
* for more information.
*/
function getRoleMember(bytes32 role, uint256 index) public view virtual override returns (address) {
return _roleMembers[role].at(index);
}
/**
* @dev Returns the number of accounts that have `role`. Can be used
* together with {getRoleMember} to enumerate all bearers of a role.
*/
function getRoleMemberCount(bytes32 role) public view virtual override returns (uint256) {
return _roleMembers[role].length();
}
/**
* @dev Overload {_grantRole} to track enumerable memberships
*/
function _grantRole(bytes32 role, address account) internal virtual override {
super._grantRole(role, account);
_roleMembers[role].add(account);
}
/**
* @dev Overload {_revokeRole} to track enumerable memberships
*/
function _revokeRole(bytes32 role, address account) internal virtual override {
super._revokeRole(role, account);
_roleMembers[role].remove(account);
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[49] private __gap;
}
// File: @openzeppelin/contracts-upgradeable/security/ReentrancyGuardUpgradeable.sol
// OpenZeppelin Contracts v4.4.1 (security/ReentrancyGuard.sol)
pragma solidity ^0.8.0;
/**
* @dev Contract module that helps prevent reentrant calls to a function.
*
* Inheriting from `ReentrancyGuard` will make the {nonReentrant} modifier
* available, which can be applied to functions to make sure there are no nested
* (reentrant) calls to them.
*
* Note that because there is a single `nonReentrant` guard, functions marked as
* `nonReentrant` may not call one another. This can be worked around by making
* those functions `private`, and then adding `external` `nonReentrant` entry
* points to them.
*
* TIP: If you would like to learn more about reentrancy and alternative ways
* to protect against it, check out our blog post
* https://blog.openzeppelin.com/reentrancy-after-istanbul/[Reentrancy After Istanbul].
*/
abstract contract ReentrancyGuardUpgradeable is Initializable {
// Booleans are more expensive than uint256 or any type that takes up a full
// word because each write operation emits an extra SLOAD to first read the
// slot's contents, replace the bits taken up by the boolean, and then write
// back. This is the compiler's defense against contract upgrades and
// pointer aliasing, and it cannot be disabled.
// The values being non-zero value makes deployment a bit more expensive,
// but in exchange the refund on every call to nonReentrant will be lower in
// amount. Since refunds are capped to a percentage of the total
// transaction's gas, it is best to keep them low in cases like this one, to
// increase the likelihood of the full refund coming into effect.
uint256 private constant _NOT_ENTERED = 1;
uint256 private constant _ENTERED = 2;
uint256 private _status;
function __ReentrancyGuard_init() internal onlyInitializing {
__ReentrancyGuard_init_unchained();
}
function __ReentrancyGuard_init_unchained() internal onlyInitializing {
_status = _NOT_ENTERED;
}
/**
* @dev Prevents a contract from calling itself, directly or indirectly.
* Calling a `nonReentrant` function from another `nonReentrant`
* function is not supported. It is possible to prevent this from happening
* by making the `nonReentrant` function external, and making it call a
* `private` function that does the actual work.
*/
modifier nonReentrant() {
// On the first call to nonReentrant, _notEntered will be true
require(_status != _ENTERED, "ReentrancyGuard: reentrant call");
// Any calls to nonReentrant after this point will fail
_status = _ENTERED;
_;
// By storing the original value once again, a refund is triggered (see
// https://eips.ethereum.org/EIPS/eip-2200)
_status = _NOT_ENTERED;
}
/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[49] private __gap;
}
// File: SBII721A.sol
// author: yoyoismee.eth -- it's opensource but also feel free to send me coffee/beer.
// ╔═╗┌─┐┌─┐┌─┐┌┬┐┌┐ ┌─┐┌─┐┌┬┐┌─┐┌┬┐┬ ┬┌┬┐┬┌─┐
// ╚═╗├─┘├┤ ├┤ ││├┴┐│ │├─┤ │ └─┐ │ │ │ ││││ │
// ╚═╝┴ └─┘└─┘─┴┘└─┘└─┘┴ ┴ ┴o└─┘ ┴ └─┘─┴┘┴└─┘
pragma solidity 0.8.14;
// @dev speedboat v2 erc721A = modified SBII721A
// @dev should treat this code as experimental.
contract SBII721A is
Initializable,
ERC721ASBUpgradable,
ReentrancyGuardUpgradeable,
AccessControlEnumerableUpgradeable,
ISBMintable,
ISBShipable
{
using EnumerableSetUpgradeable for EnumerableSetUpgradeable.AddressSet;
using StringsUpgradeable for uint256;
using SafeERC20 for IERC20;
bytes32 public constant MINTER_ROLE = keccak256("MINTER_ROLE");
string public constant MODEL = "SBII-721A-0";
struct Round {
uint128 price;
uint32 quota;
uint16 amountPerUser;
bool isActive;
bool isPublic;
bool isMerkleMode; // merkleMode will override price, amountPerUser, and TokenID if specify
bool exist;
address tokenAddress; // 0 for base asset
}
struct Conf {
bool allowNFTUpdate;
bool allowConfUpdate;
bool allowContract;
bool allowPrivilege;
bool randomAccessMode;
bool allowTarget;
bool allowLazySell;
uint64 maxSupply;
}
Conf public config;
string[] public roundNames;
mapping(bytes32 => EnumerableSetUpgradeable.AddressSet) private walletList;
mapping(bytes32 => bytes32) private merkleRoot;
mapping(bytes32 => Round) private roundData;
mapping(uint256 => bool) public nonceUsed;
mapping(bytes32 => mapping(address => uint256)) mintedInRound;
string private _baseTokenURI;
address private feeReceiver;
uint256 private bip;
address public beneficiary;
function listRole()
public
pure
returns (string[] memory names, bytes32[] memory code)
{
names = new string[](2);
code = new bytes32[](2);
names[0] = "MINTER";
names[1] = "ADMIN";
code[0] = MINTER_ROLE;
code[1] = DEFAULT_ADMIN_ROLE;
}
function grantRoles(bytes32 role, address[] calldata accounts) public {
for (uint256 i = 0; i < accounts.length; i++) {
super.grantRole(role, accounts[i]);
}
}
function revokeRoles(bytes32 role, address[] calldata accounts) public {
for (uint256 i = 0; i < accounts.length; i++) {
super.revokeRole(role, accounts[i]);
}
}
function setBeneficiary(address _beneficiary)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
require(beneficiary == address(0), "as");
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
beneficiary = _beneficiary;
}
// 0 = unlimited, can only set once.
function setMaxSupply(uint64 _maxSupply)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
require(config.maxSupply == 0, "as");
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
config.maxSupply = _maxSupply;
}
function listRoleWallet(bytes32 role)
public
view
returns (address[] memory roleMembers)
{
uint256 count = getRoleMemberCount(role);
roleMembers = new address[](count);
for (uint256 i = 0; i < count; i++) {
roleMembers[i] = getRoleMember(role, i);
}
}
function listToken(address wallet)
public
view
returns (uint256[] memory tokenList)
{
return tokensOfOwner(wallet);
}
function listRounds() public view returns (string[] memory) {
return roundNames;
}
function roundInfo(string memory roundName)
public
view
returns (Round memory)
{
return roundData[keccak256(abi.encodePacked(roundName))];
}
function massMint(address[] calldata wallets, uint256[] calldata amount)
public
{
require(config.allowPrivilege, "disabled feature");
require(hasRole(MINTER_ROLE, msg.sender), "pd");
for (uint256 i = 0; i < wallets.length; i++) {
mintNext(wallets[i], amount[i]);
}
}
function mintNext(address reciever, uint256 amount) public override {
require(config.allowPrivilege, "disabled feature");
require(hasRole(MINTER_ROLE, msg.sender), "pd");
_mintNext(reciever, amount);
}
function _mintNext(address reciever, uint256 amount) internal {
if (config.maxSupply != 0) {
require(totalSupply() + amount <= config.maxSupply);
}
_safeMint(reciever, amount); // 721A mint
}
function _random(address ad, uint256 num) internal returns (uint256) {
revert("not supported by 721a la");
}
function updateURI(string memory newURI)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
require(config.allowNFTUpdate, "na");
_baseTokenURI = newURI;
}
function mintTarget(address reciever, uint256 target) public override {
revert("not supported by 721a la");
}
function requestMint(Round storage thisRound, uint256 amount) internal {
require(thisRound.isActive, "not active");
require(thisRound.quota >= amount, "out of stock");
if (!config.allowContract) {
require(tx.origin == msg.sender);
}
thisRound.quota -= uint32(amount);
}
/// magic overload
function mint(string memory roundName, uint256 amount)
public
payable
nonReentrant
{
bytes32 key = keccak256(abi.encodePacked(roundName));
Round storage thisRound = roundData[key];
requestMint(thisRound, amount);
// require(thisRound.isActive, "not active");
// require(thisRound.quota >= amount, "out of stock");
// if (!config.allowContract) {
// require(tx.origin == msg.sender, "not allow contract");
// }
// thisRound.quota -= uint32(amount);
require(!thisRound.isMerkleMode, "wrong data");
if (!thisRound.isPublic) {
require(walletList[key].contains(msg.sender));
require(
mintedInRound[key][msg.sender] + amount <=
thisRound.amountPerUser,
"out of quota"
);
mintedInRound[key][msg.sender] += amount;
} else {
require(amount <= thisRound.amountPerUser, "nope"); // public round can mint multiple time
}
paymentUtil.processPayment(
thisRound.tokenAddress,
thisRound.price * amount
);
_mintNext(msg.sender, amount);
}
function mint(
string memory roundName,
address wallet,
uint256 amount,
uint256 tokenID,
uint256 nonce,
uint256 pricePerUnit,
address denominatedAsset,
bytes32[] memory proof
) public payable {
bytes32 key = keccak256(abi.encodePacked(roundName));
Round storage thisRound = roundData[key];
requestMint(thisRound, amount);
// require(thisRound.isActive, "not active");
// require(thisRound.quota >= amount, "out of quota");
// thisRound.quota -= uint32(amount);
require(thisRound.isMerkleMode, "invalid");
bytes32 data = hash(
wallet,
amount,
tokenID,
nonce,
pricePerUnit,
denominatedAsset,
address(this),
block.chainid
);
require(_merkleCheck(data, merkleRoot[key], proof), "fail merkle");
_useNonce(nonce);
if (wallet != address(0)) {
require(wallet == msg.sender, "nope");
}
require(amount > 0, "pick one"); // such a lazy check lol
require(tokenID == 0, "nope"); // such a lazy check lol
paymentUtil.processPayment(denominatedAsset, pricePerUnit * amount);
_mintNext(wallet, amount);
}
function mint(
address wallet,
uint256 amount,
uint256 tokenID,
uint256 nonce,
uint256 pricePerUnit,
address denominatedAsset,
bytes memory signature
) public payable {
bytes32 data = hash(
wallet,
amount,
tokenID,
nonce,
pricePerUnit,
denominatedAsset,
address(this),
block.chainid
);
require(config.allowLazySell, "na");
require(config.allowPrivilege, "na");
require(_verifySig(data, signature));
_useNonce(nonce);
if (wallet != address(0)) {
require(wallet == msg.sender, "nope");
}
require(amount > 0, "pick one"); // such a lazy check lol
require(tokenID == 0, "nope"); // such a lazy check lol
paymentUtil.processPayment(denominatedAsset, pricePerUnit * amount);
_mintNext(wallet, amount);
}
/// magic overload end
// this is 721 version. in 20 or 1155 will use the same format but different interpretation
// wallet = 0 mean any
// tokenID = 0 mean next
// amount will overide tokenID
// denominatedAsset = 0 mean chain token (e.g. eth)
// chainID is to prevent replay attack
function hash(
address wallet,
uint256 amount,
uint256 tokenID,
uint256 nonce,
uint256 pricePerUnit,
address denominatedAsset,
address refPorject,
uint256 chainID
) public pure returns (bytes32) {
return
keccak256(
abi.encodePacked(
wallet,
amount,
tokenID,
nonce,
pricePerUnit,
denominatedAsset,
refPorject,
chainID
)
);
}
function _toSignedHash(bytes32 data) internal pure returns (bytes32) {
return ECDSA.toEthSignedMessageHash(data);
}
function _verifySig(bytes32 data, bytes memory signature)
public
view
returns (bool)
{
return
hasRole(MINTER_ROLE, ECDSA.recover(_toSignedHash(data), signature));
}
function _merkleCheck(
bytes32 data,
bytes32 root,
bytes32[] memory merkleProof
) internal pure returns (bool) {
return MerkleProof.verify(merkleProof, root, data);
}
/// ROUND
function newRound(
string memory roundName,
uint128 _price,
uint32 _quota,
uint16 _amountPerUser,
bool _isActive,
bool _isPublic,
bool _isMerkle,
address _tokenAddress
) public onlyRole(DEFAULT_ADMIN_ROLE) {
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
require(!roundData[key].exist, "already exist");
roundNames.push(roundName);
roundData[key] = Round({
price: _price,
quota: _quota,
amountPerUser: _amountPerUser,
isActive: _isActive,
isPublic: _isPublic,
isMerkleMode: _isMerkle,
tokenAddress: _tokenAddress,
exist: true
});
}
function triggerRound(string memory roundName, bool _isActive)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
roundData[key].isActive = _isActive;
}
function setMerkleRoot(string memory roundName, bytes32 root)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
merkleRoot[key] = root;
}
function updateRound(
string memory roundName,
uint128 _price,
uint32 _quota,
uint16 _amountPerUser,
bool _isPublic
) public onlyRole(DEFAULT_ADMIN_ROLE) {
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
roundData[key].price = _price;
roundData[key].quota = _quota;
roundData[key].amountPerUser = _amountPerUser;
roundData[key].isPublic = _isPublic;
}
function addRoundWallet(string memory roundName, address[] memory wallets)
public
onlyRole(DEFAULT_ADMIN_ROLE)
{
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
for (uint256 i = 0; i < wallets.length; i++) {
walletList[key].add(wallets[i]);
}
}
function removeRoundWallet(
string memory roundName,
address[] memory wallets
) public onlyRole(DEFAULT_ADMIN_ROLE) {
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
bytes32 key = keccak256(abi.encodePacked(roundName));
for (uint256 i = 0; i < wallets.length; i++) {
walletList[key].remove(wallets[i]);
}
}
function getRoundWallet(string memory roundName)
public
view
returns (address[] memory)
{
return walletList[keccak256(abi.encodePacked(roundName))].values();
}
function isQualify(address wallet, string memory roundName)
public
view
returns (bool)
{
Round memory x = roundInfo(roundName);
if (!x.isActive) {
return false;
}
if (x.quota == 0) {
return false;
}
bytes32 key = keccak256(abi.encodePacked(roundName));
if (!x.isPublic && !walletList[key].contains(wallet)) {
return false;
}
if (mintedInRound[key][wallet] >= x.amountPerUser) {
return false;
}
return true;
}
function listQualifiedRound(address wallet)
public
view
returns (string[] memory)
{
string[] memory valid = new string[](roundNames.length);
for (uint256 i = 0; i < roundNames.length; i++) {
if (isQualify(wallet, roundNames[i])) {
valid[i] = roundNames[i];
}
}
return valid;
}
function setNonce(uint256[] calldata nonces, bool status)
external
onlyRole(DEFAULT_ADMIN_ROLE)
{
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
require(config.allowPrivilege, "df");
for (uint256 i = 0; i < nonces.length; i++) {
nonceUsed[nonces[i]] = status;
}
}
function _useNonce(uint256 nonce) internal {
require(!nonceUsed[nonce], "used");
nonceUsed[nonce] = true;
}
/// ROUND end ///
function initialize(
bytes calldata initArg,
uint128 _bip,
address _feeReceiver
) public initializer {
feeReceiver = _feeReceiver;
bip = _bip;
(
string memory name,
string memory symbol,
string memory baseTokenURI,
address owner,
bool _allowNFTUpdate,
bool _allowConfUpdate,
bool _allowContract,
bool _allowPrivilege,
bool _randomAccessMode,
bool _allowTarget,
bool _allowLazySell
) = abi.decode(
initArg,
(
string,
string,
string,
address,
bool,
bool,
bool,
bool,
bool,
bool,
bool
)
);
__721AInit(name, symbol);
_setupRole(DEFAULT_ADMIN_ROLE, owner);
_setupRole(MINTER_ROLE, owner);
_baseTokenURI = baseTokenURI;
config = Conf({
allowNFTUpdate: _allowNFTUpdate,
allowConfUpdate: _allowConfUpdate,
allowContract: _allowContract,
allowPrivilege: _allowPrivilege,
randomAccessMode: _randomAccessMode,
allowTarget: _allowTarget,
allowLazySell: _allowLazySell,
maxSupply: 0
});
}
function updateConfig(
bool _allowNFTUpdate,
bool _allowConfUpdate,
bool _allowContract,
bool _allowPrivilege,
bool _allowTarget,
bool _allowLazySell
) public onlyRole(DEFAULT_ADMIN_ROLE) {
require(config.allowConfUpdate);
// require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
config.allowNFTUpdate = _allowNFTUpdate;
config.allowConfUpdate = _allowConfUpdate;
config.allowContract = _allowContract;
config.allowPrivilege = _allowPrivilege;
config.allowTarget = _allowTarget;
config.allowLazySell = _allowLazySell;
}
function withdraw(address tokenAddress) public {
address reviver = beneficiary;
if (beneficiary == address(0)) {
require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "admin only");
reviver = msg.sender;
}
if (tokenAddress == address(0)) {
payable(feeReceiver).transfer(
(address(this).balance * bip) / 10000
);
payable(reviver).transfer(address(this).balance);
} else {
IERC20 token = IERC20(tokenAddress);
token.safeTransfer(
feeReceiver,
(token.balanceOf(address(this)) * bip) / 10000
);
token.safeTransfer(reviver, token.balanceOf(address(this)));
}
}
function contractURI() external view returns (string memory) {
string memory baseURI = _baseURI();
return string(abi.encodePacked(baseURI, "contract_uri"));
}
function tokenURI(uint256 tokenId)
public
view
virtual
override
returns (string memory)
{
require(_exists(tokenId), "nonexistent token");
string memory baseURI = _baseURI();
return string(abi.encodePacked(baseURI, "uri/", tokenId.toString()));
}
// @dev boring section -------------------
function __721AInit(string memory name, string memory symbol) internal {
__ReentrancyGuard_init_unchained();
__ERC721A_init(name, symbol);
__AccessControlEnumerable_init_unchained();
}
function _baseURI() internal view virtual override returns (string memory) {
return _baseTokenURI;
}
function supportsInterface(bytes4 interfaceId)
public
view
virtual
override(AccessControlEnumerableUpgradeable, ERC721ASBUpgradable)
returns (bool)
{
return
interfaceId == type(IERC721Upgradeable).interfaceId ||
interfaceId == type(IERC721MetadataUpgradeable).interfaceId ||
super.supportsInterface(interfaceId);
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[],"name":"AllOwnershipsHaveBeenSet","type":"error"},{"inputs":[],"name":"ApprovalCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"ApprovalQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"ApprovalToCurrentOwner","type":"error"},{"inputs":[],"name":"ApproveToCaller","type":"error"},{"inputs":[],"name":"BalanceQueryForZeroAddress","type":"error"},{"inputs":[],"name":"InvalidQueryRange","type":"error"},{"inputs":[],"name":"MintToZeroAddress","type":"error"},{"inputs":[],"name":"MintZeroQuantity","type":"error"},{"inputs":[],"name":"NoTokensMintedYet","type":"error"},{"inputs":[],"name":"OwnerQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"QuantityMustBeNonZero","type":"error"},{"inputs":[],"name":"TransferCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"TransferFromIncorrectOwner","type":"error"},{"inputs":[],"name":"TransferToNonERC721ReceiverImplementer","type":"error"},{"inputs":[],"name":"TransferToZeroAddress","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"approved","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint8","name":"version","type":"uint8"}],"name":"Initialized","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"previousAdminRole","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"newAdminRole","type":"bytes32"}],"name":"RoleAdminChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleGranted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleRevoked","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"inputs":[],"name":"DEFAULT_ADMIN_ROLE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"MINTER_ROLE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"MODEL","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"name_","type":"string"},{"internalType":"string","name":"symbol_","type":"string"}],"name":"__ERC721A_init","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"data","type":"bytes32"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"_verifySig","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"address[]","name":"wallets","type":"address[]"}],"name":"addRoundWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"beneficiary","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"config","outputs":[{"internalType":"bool","name":"allowNFTUpdate","type":"bool"},{"internalType":"bool","name":"allowConfUpdate","type":"bool"},{"internalType":"bool","name":"allowContract","type":"bool"},{"internalType":"bool","name":"allowPrivilege","type":"bool"},{"internalType":"bool","name":"randomAccessMode","type":"bool"},{"internalType":"bool","name":"allowTarget","type":"bool"},{"internalType":"bool","name":"allowLazySell","type":"bool"},{"internalType":"uint64","name":"maxSupply","type":"uint64"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"contractURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"explicitOwnershipOf","outputs":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint64","name":"startTimestamp","type":"uint64"},{"internalType":"bool","name":"burned","type":"bool"}],"internalType":"struct ERC721ASBUpgradable.TokenOwnership","name":"","type":"tuple"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"}],"name":"explicitOwnershipsOf","outputs":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint64","name":"startTimestamp","type":"uint64"},{"internalType":"bool","name":"burned","type":"bool"}],"internalType":"struct ERC721ASBUpgradable.TokenOwnership[]","name":"","type":"tuple[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"getRoleAdmin","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"uint256","name":"index","type":"uint256"}],"name":"getRoleMember","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"getRoleMemberCount","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"}],"name":"getRoundWallet","outputs":[{"internalType":"address[]","name":"","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"grantRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address[]","name":"accounts","type":"address[]"}],"name":"grantRoles","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"hasRole","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"uint256","name":"tokenID","type":"uint256"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"uint256","name":"pricePerUnit","type":"uint256"},{"internalType":"address","name":"denominatedAsset","type":"address"},{"internalType":"address","name":"refPorject","type":"address"},{"internalType":"uint256","name":"chainID","type":"uint256"}],"name":"hash","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"bytes","name":"initArg","type":"bytes"},{"internalType":"uint128","name":"_bip","type":"uint128"},{"internalType":"address","name":"_feeReceiver","type":"address"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"},{"internalType":"string","name":"roundName","type":"string"}],"name":"isQualify","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"}],"name":"listQualifiedRound","outputs":[{"internalType":"string[]","name":"","type":"string[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"listRole","outputs":[{"internalType":"string[]","name":"names","type":"string[]"},{"internalType":"bytes32[]","name":"code","type":"bytes32[]"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"listRoleWallet","outputs":[{"internalType":"address[]","name":"roleMembers","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"listRounds","outputs":[{"internalType":"string[]","name":"","type":"string[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"}],"name":"listToken","outputs":[{"internalType":"uint256[]","name":"tokenList","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"wallets","type":"address[]"},{"internalType":"uint256[]","name":"amount","type":"uint256[]"}],"name":"massMint","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"mint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"uint256","name":"tokenID","type":"uint256"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"uint256","name":"pricePerUnit","type":"uint256"},{"internalType":"address","name":"denominatedAsset","type":"address"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"mint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"address","name":"wallet","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"uint256","name":"tokenID","type":"uint256"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"uint256","name":"pricePerUnit","type":"uint256"},{"internalType":"address","name":"denominatedAsset","type":"address"},{"internalType":"bytes32[]","name":"proof","type":"bytes32[]"}],"name":"mint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"reciever","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"mintNext","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"reciever","type":"address"},{"internalType":"uint256","name":"target","type":"uint256"}],"name":"mintTarget","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"uint128","name":"_price","type":"uint128"},{"internalType":"uint32","name":"_quota","type":"uint32"},{"internalType":"uint16","name":"_amountPerUser","type":"uint16"},{"internalType":"bool","name":"_isActive","type":"bool"},{"internalType":"bool","name":"_isPublic","type":"bool"},{"internalType":"bool","name":"_isMerkle","type":"bool"},{"internalType":"address","name":"_tokenAddress","type":"address"}],"name":"newRound","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"nextOwnerToExplicitlySet","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"nonceUsed","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"ownerOf","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"address[]","name":"wallets","type":"address[]"}],"name":"removeRoundWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"renounceRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"revokeRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address[]","name":"accounts","type":"address[]"}],"name":"revokeRoles","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"}],"name":"roundInfo","outputs":[{"components":[{"internalType":"uint128","name":"price","type":"uint128"},{"internalType":"uint32","name":"quota","type":"uint32"},{"internalType":"uint16","name":"amountPerUser","type":"uint16"},{"internalType":"bool","name":"isActive","type":"bool"},{"internalType":"bool","name":"isPublic","type":"bool"},{"internalType":"bool","name":"isMerkleMode","type":"bool"},{"internalType":"bool","name":"exist","type":"bool"},{"internalType":"address","name":"tokenAddress","type":"address"}],"internalType":"struct SBII721A.Round","name":"","type":"tuple"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"roundNames","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"_data","type":"bytes"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_beneficiary","type":"address"}],"name":"setBeneficiary","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint64","name":"_maxSupply","type":"uint64"}],"name":"setMaxSupply","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"bytes32","name":"root","type":"bytes32"}],"name":"setMerkleRoot","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"nonces","type":"uint256[]"},{"internalType":"bool","name":"status","type":"bool"}],"name":"setNonce","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"quantity","type":"uint256"}],"name":"setOwnersExplicit","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"tokensOfOwner","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"uint256","name":"start","type":"uint256"},{"internalType":"uint256","name":"stop","type":"uint256"}],"name":"tokensOfOwnerIn","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"bool","name":"_isActive","type":"bool"}],"name":"triggerRound","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bool","name":"_allowNFTUpdate","type":"bool"},{"internalType":"bool","name":"_allowConfUpdate","type":"bool"},{"internalType":"bool","name":"_allowContract","type":"bool"},{"internalType":"bool","name":"_allowPrivilege","type":"bool"},{"internalType":"bool","name":"_allowTarget","type":"bool"},{"internalType":"bool","name":"_allowLazySell","type":"bool"}],"name":"updateConfig","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"roundName","type":"string"},{"internalType":"uint128","name":"_price","type":"uint128"},{"internalType":"uint32","name":"_quota","type":"uint32"},{"internalType":"uint16","name":"_amountPerUser","type":"uint16"},{"internalType":"bool","name":"_isPublic","type":"bool"}],"name":"updateRound","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"newURI","type":"string"}],"name":"updateURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"tokenAddress","type":"address"}],"name":"withdraw","outputs":[],"stateMutability":"nonpayable","type":"function"}]Contract Creation Code
608060405234801561001057600080fd5b50615f0a80620000216000396000f3fe6080604052600436106102f45760003560e01c806301ffc9a7146102f9578063056b01ce1461032e57806306fdde0314610343578063081812fc14610365578063095ea7b3146103925780630e4bef5a146103b25780631234170d146103d2578063137fdac0146103f457806318160ddd14610414578063196f0f62146104375780631bb3624c146104575780631c31f710146104775780631fc1e25f1461049757806323b872dd146104c4578063248a9ca3146104e45780632d20fb60146105045780632f2ff15d14610524578063338bd19a1461054457806336568abe14610571578063373f68711461059157806338af3eed146105b15780633f651786146105d257806342842e0e146105f2578063449e14c61461061257806346e410541461062557806351cff8d914610638578063541b47f4146106585780635bbb2177146106785780635e95a47b146106a55780636352211e146106c557806370a08231146106e557806379502c55146107055780637ee5a0a6146107bb578063823b92f7146107db5780638462151c146107fb5780639010d07c1461081b57806391d148541461083b57806394d0d3a61461085b57806395d89b411461088c5780639606d076146108a157806396478cfd146108c157806397d017b6146108e157806398ea15721461090157806399a2557a1461092e5780639c4f3d0a1461094e578063a217fddf1461096e578063a22cb46514610983578063b7582c1a146109a3578063b7aafa87146109c6578063b88d4fde146109e6578063bf65df9b14610a06578063c23dc68f14610a26578063c30f4a5a14610a53578063c87b56dd14610a73578063c99323a014610a93578063ca15c87314610ab3578063d2f01f1914610ad3578063d539139314610af3578063d547741f14610b15578063d7224ba014610b35578063deb9a3a214610b4b578063e0cfc8ef14610b6b578063e8a3d48514610b8b578063e985e9c514610ba0578063f4990d9414610be9578063f7eb983f14610c09578063fe88a71d14610c40575b600080fd5b34801561030557600080fd5b50610319610314366004614a3a565b610c60565b60405190151581526020015b60405180910390f35b61034161033c366004614b0c565b610ca6565b005b34801561034f57600080fd5b50610358610f38565b6040516103259190614ba8565b34801561037157600080fd5b50610385610380366004614bbb565b610fca565b6040516103259190614bd4565b34801561039e57600080fd5b506103416103ad366004614bfd565b61100e565b3480156103be57600080fd5b506103586103cd366004614bbb565b61109b565b3480156103de57600080fd5b506103e7611148565b6040516103259190614c7e565b34801561040057600080fd5b5061034161040f366004614cb4565b611222565b34801561042057600080fd5b506104296112bd565b604051908152602001610325565b34801561044357600080fd5b50610341610452366004614dc0565b6112cb565b34801561046357600080fd5b50610319610472366004614e0b565b611319565b34801561048357600080fd5b50610341610492366004614e51565b611346565b3480156104a357600080fd5b506104b76104b2366004614e51565b61139f565b6040516103259190614e6e565b3480156104d057600080fd5b506103416104df366004614ea6565b6113aa565b3480156104f057600080fd5b506104296104ff366004614bbb565b6113b5565b34801561051057600080fd5b5061034161051f366004614bbb565b6113ca565b34801561053057600080fd5b5061034161053f366004614ee7565b61150b565b34801561055057600080fd5b5061056461055f366004614f17565b611527565b6040516103259190614f4b565b34801561057d57600080fd5b5061034161058c366004614ee7565b61156b565b34801561059d57600080fd5b506103416105ac366004614fe2565b6115e9565b3480156105bd57600080fd5b5061010e54610385906001600160a01b031681565b3480156105de57600080fd5b506103416105ed366004614bfd565b611696565b3480156105fe57600080fd5b5061034161060d366004614ea6565b6116d9565b610341610620366004615065565b6116f4565b6103416106333660046150ed565b611874565b34801561064457600080fd5b50610341610653366004614e51565b611a6d565b34801561066457600080fd5b506103416106733660046151f3565b611c7b565b34801561068457600080fd5b506106986106933660046152ae565b611ef4565b6040516103259190615360565b3480156106b157600080fd5b506103416106c03660046153a2565b611fa8565b3480156106d157600080fd5b506103856106e0366004614bbb565b612044565b3480156106f157600080fd5b50610429610700366004614e51565b612056565b34801561071157600080fd5b506101045461076b9060ff80821691610100810482169162010000820481169163010000008104821691600160201b8204811691600160281b8104821691600160301b82041690600160381b90046001600160401b031688565b604080519815158952961515602089015294151595870195909552911515606086015215156080850152151560a084015290151560c08301526001600160401b031660e082015261010001610325565b3480156107c757600080fd5b506103e76107d6366004614e51565b6120a4565b3480156107e757600080fd5b506104296107f6366004615424565b61229c565b34801561080757600080fd5b506104b7610816366004614e51565b612314565b34801561082757600080fd5b506103856108363660046154a0565b61243e565b34801561084757600080fd5b50610319610856366004614ee7565b612456565b34801561086757600080fd5b50610319610876366004614bbb565b6101096020526000908152604090205460ff1681565b34801561089857600080fd5b50610358612481565b3480156108ad57600080fd5b506103416108bc3660046154c2565b612490565b3480156108cd57600080fd5b506105646108dc366004614bbb565b61269a565b3480156108ed57600080fd5b506103416108fc366004614bfd565b612745565b34801561090d57600080fd5b5061092161091c366004614f17565b6127ad565b6040516103259190615555565b34801561093a57600080fd5b506104b76109493660046155e8565b6128c4565b34801561095a57600080fd5b5061034161096936600461561d565b612a85565b34801561097a57600080fd5b50610429600081565b34801561098f57600080fd5b5061034161099e366004615646565b612aef565b3480156109af57600080fd5b506109b8612b84565b604051610325929190615674565b3480156109d257600080fd5b506103416109e1366004614b0c565b612ca2565b3480156109f257600080fd5b50610341610a013660046156cb565b612cee565b348015610a1257600080fd5b50610319610a21366004615736565b612d3e565b348015610a3257600080fd5b50610a46610a41366004614bbb565b612e28565b604051610325919061576f565b348015610a5f57600080fd5b50610341610a6e366004614f17565b612ebd565b348015610a7f57600080fd5b50610358610a8e366004614bbb565b612eff565b348015610a9f57600080fd5b50610341610aae36600461577d565b612f88565b348015610abf57600080fd5b50610429610ace366004614bbb565b61304b565b348015610adf57600080fd5b50610341610aee3660046157e8565b613062565b348015610aff57600080fd5b50610429600080516020615e9583398151915281565b348015610b2157600080fd5b50610341610b30366004614ee7565b6130a3565b348015610b4157600080fd5b50610429606d5481565b348015610b5757600080fd5b50610341610b66366004614dc0565b6130bf565b348015610b7757600080fd5b50610341610b86366004615841565b613107565b348015610b9757600080fd5b506103586131b3565b348015610bac57600080fd5b50610319610bbb366004615897565b6001600160a01b039182166000908152606c6020908152604080832093909416825291909152205460ff1690565b348015610bf557600080fd5b50610341610c04366004614cb4565b6131e7565b348015610c1557600080fd5b506103586040518060400160405280600b81526020016a0534249492d373231412d360ac1b81525081565b348015610c4c57600080fd5b50610341610c5b3660046158c5565b61327b565b60006001600160e01b031982166380ac58cd60e01b1480610c9157506001600160e01b03198216635b5e139f60e01b145b80610ca05750610ca0826132de565b92915050565b6002606e5403610cfd5760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c0060448201526064015b60405180910390fd5b6002606e55604051600090610d1690849060200161590b565b60408051601f19818403018152918152815160209283012060008181526101089093529120909150610d488184613303565b8054600160c01b900460ff1615610d8e5760405162461bcd60e51b815260206004820152600a60248201526977726f6e67206461746160b01b6044820152606401610cf4565b8054600160b81b900460ff16610e6757600082815261010660205260409020610db790336133f5565b610dc057600080fd5b8054600083815261010a60209081526040808320338452909152902054600160a01b90910461ffff1690610df590859061593d565b1115610e325760405162461bcd60e51b815260206004820152600c60248201526b6f7574206f662071756f746160a01b6044820152606401610cf4565b600082815261010a6020908152604080832033845290915281208054859290610e5c90849061593d565b90915550610e939050565b8054600160a01b900461ffff16831115610e935760405162461bcd60e51b8152600401610cf490615955565b600181015481547335603bb6ae52be0dbf419bdf454e5b8e06437ed591630b63fe95916001600160a01b0390911690610ed69087906001600160801b0316615973565b6040518363ffffffff1660e01b8152600401610ef3929190615992565b60006040518083038186803b158015610f0b57600080fd5b505af4158015610f1f573d6000803e3d6000fd5b50505050610f2d338461340a565b50506001606e555050565b606060678054610f47906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054610f73906159ab565b8015610fc05780601f10610f9557610100808354040283529160200191610fc0565b820191906000526020600020905b815481529060010190602001808311610fa357829003601f168201915b5050505050905090565b6000610fd58261345f565b610ff2576040516333d1c03960e21b815260040160405180910390fd5b506000908152606b60205260409020546001600160a01b031690565b600061101982612044565b9050806001600160a01b0316836001600160a01b03160361104d5760405163250fdee360e21b815260040160405180910390fd5b336001600160a01b0382161480159061106d575061106b8133610bbb565b155b1561108b576040516367d9dca160e11b815260040160405180910390fd5b611096838383613498565b505050565b61010581815481106110ac57600080fd5b9060005260206000200160009150905080546110c7906159ab565b80601f01602080910402602001604051908101604052809291908181526020018280546110f3906159ab565b80156111405780601f1061111557610100808354040283529160200191611140565b820191906000526020600020905b81548152906001019060200180831161112357829003601f168201915b505050505081565b6060610105805480602002602001604051908101604052809291908181526020016000905b8282101561121957838290600052602060002001805461118c906159ab565b80601f01602080910402602001604051908101604052809291908181526020018280546111b8906159ab565b80156112055780601f106111da57610100808354040283529160200191611205565b820191906000526020600020905b8154815290600101906020018083116111e857829003601f168201915b50505050508152602001906001019061116d565b50505050905090565b600061122d816134f4565b600083604051602001611240919061590b565b60405160208183030381529060405280519060200120905060005b83518110156112b6576112a3848281518110611279576112796159e5565b6020026020010151610106600085815260200190815260200160002061350190919063ffffffff16565b50806112ae816159fb565b91505061125b565b5050505050565b606654606554036000190190565b60005b8181101561131357611301848484848181106112ec576112ec6159e5565b9050602002016020810190610b309190614e51565b8061130b816159fb565b9150506112ce565b50505050565b600061133f600080516020615e9583398151915261085661133986613516565b8561356e565b9392505050565b6000611351816134f4565b61010e546001600160a01b03161561137b5760405162461bcd60e51b8152600401610cf490615a14565b5061010e80546001600160a01b0319166001600160a01b0392909216919091179055565b6060610ca082612314565b61109683838361358a565b600090815260a0602052604090206001015490565b806000036113eb576040516356be441560e01b815260040160405180910390fd5b60016065540361140e5760405163c0367cab60e01b815260040160405180910390fd5b606d54600081900361141e575060015b6065548110611440576040516370e89b1b60e01b815260040160405180910390fd5b606554828201600019810191101561145b5750606554600019015b815b818111611500576000818152606960205260409020546001600160a01b031615801561149f5750600081815260696020526040902054600160e01b900460ff16155b156114f85760006114af82613762565b80516000848152606960209081526040909120805491909301516001600160401b0316600160a01b026001600160e01b03199091166001600160a01b0390921691909117179055505b60010161145d565b50600101606d555050565b611514826113b5565b61151d816134f4565b6110968383613874565b6060610ca0610106600084604051602001611542919061590b565b604051602081830303815290604052805190602001208152602001908152602001600020613896565b6001600160a01b03811633146115db5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b6064820152608401610cf4565b6115e582826138a3565b5050565b60006115f4816134f4565b600086604051602001611607919061590b565b60408051601f198184030181529181528151602092830120600090815261010890925290208054931515600160b81b0260ff60b81b1961ffff909616600160a01b029590951663ff00ffff60a01b1963ffffffff909716600160801b026001600160a01b03199095166001600160801b0390981697909717939093179490941694909417919091179055505050565b60405162461bcd60e51b81526020600482015260186024820152776e6f7420737570706f727465642062792037323161206c6160401b6044820152606401610cf4565b61109683838360405180602001604052806000815250612cee565b6000611706888888888888304661229c565b61010454909150600160301b900460ff166117335760405162461bcd60e51b8152600401610cf490615a30565b610104546301000000900460ff1661175d5760405162461bcd60e51b8152600401610cf490615a30565b6117678183611319565b61177057600080fd5b611779856138c5565b6001600160a01b038816156117b0576001600160a01b03881633146117b05760405162461bcd60e51b8152600401610cf490615955565b600087116117d05760405162461bcd60e51b8152600401610cf490615a4c565b85156117ee5760405162461bcd60e51b8152600401610cf490615955565b7335603bb6ae52be0dbf419bdf454e5b8e06437ed5630b63fe95846118138a88615973565b6040518363ffffffff1660e01b8152600401611830929190615992565b60006040518083038186803b15801561184857600080fd5b505af415801561185c573d6000803e3d6000fd5b5050505061186a888861340a565b5050505050505050565b600088604051602001611887919061590b565b60408051601f198184030181529181528151602092830120600081815261010890935291209091506118b98189613303565b8054600160c01b900460ff166118fb5760405162461bcd60e51b81526020600482015260076024820152661a5b9d985b1a5960ca1b6044820152606401610cf4565b600061190d8a8a8a8a8a8a304661229c565b6000848152610107602052604090205490915061192c9082908661392a565b6119665760405162461bcd60e51b815260206004820152600b60248201526a6661696c206d65726b6c6560a81b6044820152606401610cf4565b61196f876138c5565b6001600160a01b038a16156119a6576001600160a01b038a1633146119a65760405162461bcd60e51b8152600401610cf490615955565b600089116119c65760405162461bcd60e51b8152600401610cf490615a4c565b87156119e45760405162461bcd60e51b8152600401610cf490615955565b7335603bb6ae52be0dbf419bdf454e5b8e06437ed5630b63fe9586611a098c8a615973565b6040518363ffffffff1660e01b8152600401611a26929190615992565b60006040518083038186803b158015611a3e57600080fd5b505af4158015611a52573d6000803e3d6000fd5b50505050611a608a8a61340a565b5050505050505050505050565b61010e546001600160a01b031680611ac657611a8a600033612456565b611ac35760405162461bcd60e51b815260206004820152600a60248201526961646d696e206f6e6c7960b01b6044820152606401610cf4565b50335b6001600160a01b038216611b625761010c5461010d546001600160a01b03909116906108fc9061271090611afa9047615973565b611b049190615a84565b6040518115909202916000818181858888f19350505050158015611b2c573d6000803e3d6000fd5b506040516001600160a01b038216904780156108fc02916000818181858888f19350505050158015611096573d6000803e3d6000fd5b61010c5461010d546040516370a0823160e01b81528492611c0a926001600160a01b0391821692612710928616906370a0823190611ba4903090600401614bd4565b602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190615a98565b611bef9190615973565b611bf99190615a84565b6001600160a01b038416919061393f565b61109682826001600160a01b03166370a08231306040518263ffffffff1660e01b8152600401611c3a9190614bd4565b602060405180830381865afa158015611c57573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611bf99190615a98565b6000611c86816134f4565b600089604051602001611c99919061590b565b60408051808303601f1901815291815281516020928301206000818152610108909352912054909150600160c81b900460ff1615611d095760405162461bcd60e51b815260206004820152600d60248201526c185b1c9958591e48195e1a5cdd609a1b6044820152606401610cf4565b61010580546001810182556000919091528a51611d4d917ffc62abc8c0fc47c2d92f5aec99bf8b60f375828e14394d89345cae11a9867371019060208d019061496b565b506040518061010001604052808a6001600160801b031681526020018963ffffffff1681526020018861ffff168152602001871515815260200186151581526020018515158152602001600115158152602001846001600160a01b0316815250610108600083815260200190815260200160002060008201518160000160006101000a8154816001600160801b0302191690836001600160801b0316021790555060208201518160000160106101000a81548163ffffffff021916908363ffffffff16021790555060408201518160000160146101000a81548161ffff021916908361ffff16021790555060608201518160000160166101000a81548160ff02191690831515021790555060808201518160000160176101000a81548160ff02191690831515021790555060a08201518160000160186101000a81548160ff02191690831515021790555060c08201518160000160196101000a81548160ff02191690831515021790555060e08201518160010160006101000a8154816001600160a01b0302191690836001600160a01b0316021790555090505050505050505050505050565b80516060906000816001600160401b03811115611f1357611f13614a57565b604051908082528060200260200182016040528015611f4c57816020015b611f396149ef565b815260200190600190039081611f315790505b50905060005b828114611fa057611f7b858281518110611f6e57611f6e6159e5565b6020026020010151612e28565b828281518110611f8d57611f8d6159e5565b6020908102919091010152600101611f52565b509392505050565b6000611fb3816134f4565b61010454610100900460ff16611fc857600080fd5b50610104805461ffff191696151561ff00191696909617610100951515959095029490941763ffff00001916620100009315159390930263ff0000001916929092176301000000911515919091021761ffff60281b1916600160281b9115159190910260ff60301b191617600160301b91151591909102179055565b600061204f82613762565b5192915050565b60006001600160a01b03821661207f576040516323d3ad8160e21b815260040160405180910390fd5b506001600160a01b03166000908152606a60205260409020546001600160401b031690565b610105546060906000906001600160401b038111156120c5576120c5614a57565b6040519080825280602002602001820160405280156120f857816020015b60608152602001906001900390816120e35790505b50905060005b61010554811015612295576121b9846101058381548110612121576121216159e5565b906000526020600020018054612136906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054612162906159ab565b80156121af5780601f10612184576101008083540402835291602001916121af565b820191906000526020600020905b81548152906001019060200180831161219257829003601f168201915b5050505050612d3e565b156122835761010581815481106121d2576121d26159e5565b9060005260206000200180546121e7906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054612213906159ab565b80156122605780601f1061223557610100808354040283529160200191612260565b820191906000526020600020905b81548152906001019060200180831161224357829003601f168201915b5050505050828281518110612277576122776159e5565b60200260200101819052505b8061228d816159fb565b9150506120fe565b5092915050565b6040516001600160601b031960608a811b82166020840152603483018a905260548301899052607483018890526094830187905285811b821660b484015284901b1660c882015260dc810182905260009060fc0160405160208183030381529060405280519060200120905098975050505050505050565b6060600080600061232485612056565b90506000816001600160401b0381111561234057612340614a57565b604051908082528060200260200182016040528015612369578160200160208202803683370190505b5090506123746149ef565b60015b83861461243257600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161515918101829052925061242a5781516001600160a01b0316156123eb57815194505b876001600160a01b0316856001600160a01b03160361242a578083878060010198508151811061241d5761241d6159e5565b6020026020010181815250505b600101612377565b50909695505050505050565b600082815260d26020526040812061133f9083613995565b600091825260a0602090815260408084206001600160a01b0393909316845291905290205460ff1690565b606060688054610f47906159ab565b600061249c60016139a1565b905080156124b4576000805461ff0019166101001790555b8161010c60006101000a8154816001600160a01b0302191690836001600160a01b03160217905550826001600160801b031661010d8190555060008060008060008060008060008060008f8f81019061250d9190615abc565b9a509a509a509a509a509a509a509a509a509a509a5061252d8b8b613a35565b612538600089613a4f565b612550600080516020615e9583398151915289613a4f565b88516125649061010b9060208c019061496b565b5060408051610100808201835298151580825297151560208201819052961515918101829052941515606086018190529315156080860181905292151560a0860181905291151560c08601819052600060e090960195909552610104805461ffff191661ff001990981697909717959097029490941763ffff000019166201000090960263ff00000019169590951763010000009091021761ffff60201b1916600160201b90940260ff60281b191693909317600160281b90910217600160301b600160781b031916600160301b909202600160381b600160781b0319169190911790555050821591506112b69050576000805461ff0019169055604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb38474024989060200160405180910390a15050505050565b606060006126a78361304b565b9050806001600160401b038111156126c1576126c1614a57565b6040519080825280602002602001820160405280156126ea578160200160208202803683370190505b50915060005b8181101561273e57612702848261243e565b838281518110612714576127146159e5565b6001600160a01b039092166020928302919091019091015280612736816159fb565b9150506126f0565b5050919050565b610104546301000000900460ff1661276f5760405162461bcd60e51b8152600401610cf490615bcd565b612787600080516020615e9583398151915233612456565b6127a35760405162461bcd60e51b8152600401610cf490615bf7565b6115e5828261340a565b6040805161010081018252600080825260208201819052918101829052606081018290526080810182905260a0810182905260c0810182905260e0810191909152610108600083604051602001612804919061590b565b60408051601f19818403018152918152815160209283012083528282019390935290820160002082516101008101845281546001600160801b038116825263ffffffff600160801b8204169382019390935261ffff600160a01b8404169381019390935260ff600160b01b8304811615156060850152600160b81b8304811615156080850152600160c01b83048116151560a0850152600160c81b909204909116151560c0830152600101546001600160a01b031660e082015292915050565b60608183106128e657604051631960ccad60e11b815260040160405180910390fd5b60655460009060018510156128fa57600194505b80841115612906578093505b600061291187612056565b905084861015612930578585038181101561292a578091505b50612934565b5060005b6000816001600160401b0381111561294e5761294e614a57565b604051908082528060200260200182016040528015612977578160200160208202803683370190505b5090508160000361298d57935061133f92505050565b600061299888612e28565b9050600081604001516129a9575080515b885b8881141580156129bb5750848714155b15612a7457600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff1615159181018290529350612a6c5782516001600160a01b031615612a2d57825191505b8a6001600160a01b0316826001600160a01b031603612a6c5780848880600101995081518110612a5f57612a5f6159e5565b6020026020010181815250505b6001016129ab565b505050928352509095945050505050565b6000612a90816134f4565b61010454600160381b90046001600160401b031615612ac15760405162461bcd60e51b8152600401610cf490615a14565b5061010480546001600160401b03909216600160381b02600160381b600160781b0319909216919091179055565b336001600160a01b03831603612b185760405163b06307db60e01b815260040160405180910390fd5b336000818152606c602090815260408083206001600160a01b03871680855290835292819020805460ff191686151590811790915590519081529192917f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a35050565b6040805160028082526060828101909352829190816020015b6060815260200190600190039081612b9d57505060408051600280825260608201835292945091906020830190803683370190505090506040518060400160405280600681526020016526a4a72a22a960d11b81525082600081518110612c0657612c066159e5565b60200260200101819052506040518060400160405280600581526020016420a226a4a760d91b81525082600181518110612c4257612c426159e5565b6020026020010181905250600080516020615e9583398151915281600081518110612c6f57612c6f6159e5565b6020026020010181815250506000801b81600181518110612c9257612c926159e5565b6020026020010181815250509091565b6000612cad816134f4565b600083604051602001612cc0919061590b565b60408051601f1981840301815291815281516020928301206000908152610107909252902092909255505050565b612cf984848461358a565b612d0b836001600160a01b0316613a59565b8015612d205750612d1e84848484613a68565b155b15611313576040516368d2bf6b60e11b815260040160405180910390fd5b600080612d4a836127ad565b90508060600151612d5f576000915050610ca0565b806020015163ffffffff16600003612d7b576000915050610ca0565b600083604051602001612d8e919061590b565b6040516020818303038152906040528051906020012090508160800151158015612dce5750600081815261010660205260409020612dcc90866133f5565b155b15612dde57600092505050610ca0565b604080830151600083815261010a60209081528382206001600160a01b038a1683529052919091205461ffff90911611612e1d57600092505050610ca0565b506001949350505050565b612e306149ef565b612e386149ef565b6001831080612e4957506065548310155b15612e545792915050565b50600082815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161580159282019290925290612eb45792915050565b61133f83613762565b6000612ec8816134f4565b6101045460ff16612eeb5760405162461bcd60e51b8152600401610cf490615a30565b81516110969061010b90602085019061496b565b6060612f0a8261345f565b612f4a5760405162461bcd60e51b81526020600482015260116024820152703737b732bc34b9ba32b73a103a37b5b2b760791b6044820152606401610cf4565b6000612f54613b53565b905080612f6084613b63565b604051602001612f71929190615c13565b604051602081830303815290604052915050919050565b610104546301000000900460ff16612fb25760405162461bcd60e51b8152600401610cf490615bcd565b612fca600080516020615e9583398151915233612456565b612fe65760405162461bcd60e51b8152600401610cf490615bf7565b60005b838110156112b657613039858583818110613006576130066159e5565b905060200201602081019061301b9190614e51565b84848481811061302d5761302d6159e5565b90506020020135612745565b80613043816159fb565b915050612fe9565b600081815260d260205260408120610ca090613c63565b61306a613c6d565b613072613c6d565b815161308590606790602085019061496b565b50805161309990606890602084019061496b565b5060016065555050565b6130ac826113b5565b6130b5816134f4565b61109683836138a3565b60005b81811015611313576130f5848484848181106130e0576130e06159e5565b905060200201602081019061053f9190614e51565b806130ff816159fb565b9150506130c2565b6000613112816134f4565b610104546301000000900460ff166131515760405162461bcd60e51b8152602060048201526002602482015261323360f11b6044820152606401610cf4565b60005b838110156112b657826101096000878785818110613174576131746159e5565b90506020020135815260200190815260200160002060006101000a81548160ff02191690831515021790555080806131ab906159fb565b915050613154565b606060006131bf613b53565b9050806040516020016131d29190615c52565b60405160208183030381529060405291505090565b60006131f2816134f4565b600083604051602001613205919061590b565b60405160208183030381529060405280519060200120905060005b83518110156112b65761326884828151811061323e5761323e6159e5565b60200260200101516101066000858152602001908152602001600020613c9690919063ffffffff16565b5080613273816159fb565b915050613220565b6000613286816134f4565b600083604051602001613299919061590b565b60408051601f198184030181529181528151602092830120600090815261010890925290208054931515600160b01b0260ff60b01b1990941693909317909255505050565b60006001600160e01b03198216635a05180f60e01b1480610ca05750610ca082613cab565b8154600160b01b900460ff166133485760405162461bcd60e51b815260206004820152600a6024820152696e6f742061637469766560b01b6044820152606401610cf4565b8154600160801b900463ffffffff168111156133955760405162461bcd60e51b815260206004820152600c60248201526b6f7574206f662073746f636b60a01b6044820152606401610cf4565b6101045462010000900460ff166133b2573233146133b257600080fd5b8154819083906010906133d3908490600160801b900463ffffffff16615c82565b92506101000a81548163ffffffff021916908363ffffffff1602179055505050565b600061133f836001600160a01b038416613cd0565b61010454600160381b90046001600160401b0316156134555761010454600160381b90046001600160401b0316816134406112bd565b61344a919061593d565b111561345557600080fd5b6115e58282613ce8565b600081600111158015613473575060655482105b8015610ca0575050600090815260696020526040902054600160e01b900460ff161590565b6000828152606b602052604080822080546001600160a01b0319166001600160a01b0387811691821790925591518593918516917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591a4505050565b6134fe8133613d02565b50565b600061133f836001600160a01b038416613d66565b6000610ca0826040517b0ca2ba3432b932bab69029b4b3b732b21026b2b9b9b0b3b29d05199960211b6020820152603c8101829052600090605c01604051602081830303815290604052805190602001209050919050565b600080600061357d8585613db0565b91509150611fa081613e1e565b600061359582613762565b9050836001600160a01b031681600001516001600160a01b0316146135cc5760405162a1148160e81b815260040160405180910390fd5b6000336001600160a01b03861614806135ea57506135ea8533610bbb565b806136055750336135fa84610fca565b6001600160a01b0316145b90508061362557604051632ce44b5f60e11b815260040160405180910390fd5b6001600160a01b03841661364c57604051633a954ecd60e21b815260040160405180910390fd5b61365860008487613498565b6001600160a01b038581166000908152606a6020908152604080832080546001600160401b03198082166001600160401b0392831660001901831617909255898616808652838620805493841693831660019081018416949094179055898652606990945282852080546001600160e01b031916909417600160a01b4290921691909102178355870180845292208054919390911661372b57606554821461372b57805460208601516001600160401b0316600160a01b026001600160e01b03199091166001600160a01b038a16171781555b50505082846001600160a01b0316866001600160a01b0316600080516020615eb583398151915260405160405180910390a46112b6565b61376a6149ef565b818060011115801561377d575060655481105b1561385b57600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161515918101829052906138595780516001600160a01b0316156137f0579392505050565b5060001901600081815260696020908152604091829020825160608101845290546001600160a01b038116808352600160a01b82046001600160401b031693830193909352600160e01b900460ff1615159281019290925215613854579392505050565b6137f0565b505b604051636f96cda160e11b815260040160405180910390fd5b61387e8282613fcf565b600082815260d2602052604090206110969082613501565b6060600061133f83614055565b6138ad82826140b1565b600082815260d2602052604090206110969082613c96565b6000818152610109602052604090205460ff161561390e5760405162461bcd60e51b8152600401610cf4906020808252600490820152631d5cd95960e21b604082015260600190565b600090815261010960205260409020805460ff19166001179055565b6000613937828486614118565b949350505050565b6110968363a9059cbb60e01b848460405160240161395e929190615992565b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915261412e565b600061133f8383614200565b60008054610100900460ff16156139ef578160ff1660011480156139cb57506139c930613a59565b155b6139e75760405162461bcd60e51b8152600401610cf490615ca7565b506000919050565b60005460ff808416911610613a165760405162461bcd60e51b8152600401610cf490615ca7565b506000805460ff191660ff92909216919091179055600190565b919050565b613a3d61422a565b613a478282613062565b6115e5613c6d565b6115e58282613874565b6001600160a01b03163b151590565b604051630a85bd0160e11b81526000906001600160a01b0385169063150b7a0290613a9d903390899088908890600401615cf5565b6020604051808303816000875af1925050508015613ad8575060408051601f3d908101601f19168201909252613ad591810190615d32565b60015b613b36573d808015613b06576040519150601f19603f3d011682016040523d82523d6000602084013e613b0b565b606091505b508051600003613b2e576040516368d2bf6b60e11b815260040160405180910390fd5b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050949350505050565b606061010b8054610f47906159ab565b606081600003613b8a5750506040805180820190915260018152600360fc1b602082015290565b8160005b8115613bb45780613b9e816159fb565b9150613bad9050600a83615a84565b9150613b8e565b6000816001600160401b03811115613bce57613bce614a57565b6040519080825280601f01601f191660200182016040528015613bf8576020820181803683370190505b5090505b841561393757613c0d600183615d4f565b9150613c1a600a86615d66565b613c2590603061593d565b60f81b818381518110613c3a57613c3a6159e5565b60200101906001600160f81b031916908160001a905350613c5c600a86615a84565b9450613bfc565b6000610ca0825490565b600054610100900460ff16613c945760405162461bcd60e51b8152600401610cf490615d7a565b565b600061133f836001600160a01b038416614258565b60006001600160e01b03198216637965db0b60e01b1480610ca05750610ca08261434b565b60009081526001919091016020526040902054151590565b6115e582826040518060200160405280600081525061439b565b613d0c8282612456565b6115e557613d24816001600160a01b03166014614536565b613d2f836020614536565b604051602001613d40929190615dc5565b60408051601f198184030181529082905262461bcd60e51b8252610cf491600401614ba8565b6000613d728383613cd0565b613da857508154600181810184556000848152602080822090930184905584548482528286019093526040902091909155610ca0565b506000610ca0565b6000808251604103613de65760208301516040840151606085015160001a613dda878285856146d1565b94509450505050613e17565b8251604003613e0f5760208301516040840151613e048683836147b4565b935093505050613e17565b506000905060025b9250929050565b6000816004811115613e3257613e32615e34565b03613e3a5750565b6001816004811115613e4e57613e4e615e34565b03613e965760405162461bcd60e51b815260206004820152601860248201527745434453413a20696e76616c6964207369676e617475726560401b6044820152606401610cf4565b6002816004811115613eaa57613eaa615e34565b03613ef75760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610cf4565b6003816004811115613f0b57613f0b615e34565b03613f635760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c604482015261756560f01b6064820152608401610cf4565b6004816004811115613f7757613f77615e34565b036134fe5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c604482015261756560f01b6064820152608401610cf4565b613fd98282612456565b6115e557600082815260a0602090815260408083206001600160a01b03851684529091529020805460ff191660011790556140113390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b6060816000018054806020026020016040519081016040528092919081815260200182805480156140a557602002820191906000526020600020905b815481526020019060010190808311614091575b50505050509050919050565b6140bb8282612456565b156115e557600082815260a0602090815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b60008261412585846147ed565b14949350505050565b6000614183826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166148599092919063ffffffff16565b80519091501561109657808060200190518101906141a19190615e4a565b6110965760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610cf4565b6000826000018281548110614217576142176159e5565b9060005260206000200154905092915050565b600054610100900460ff166142515760405162461bcd60e51b8152600401610cf490615d7a565b6001606e55565b6000818152600183016020526040812054801561434157600061427c600183615d4f565b855490915060009061429090600190615d4f565b90508181146142f55760008660000182815481106142b0576142b06159e5565b90600052602060002001549050808760000184815481106142d3576142d36159e5565b6000918252602080832090910192909255918252600188019052604090208390555b855486908061430657614306615e67565b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050610ca0565b6000915050610ca0565b60006001600160e01b031982166380ac58cd60e01b148061437c57506001600160e01b03198216635b5e139f60e01b145b80610ca057506301ffc9a760e01b6001600160e01b0319831614610ca0565b6065546001600160a01b0384166143c457604051622e076360e81b815260040160405180910390fd5b826000036143e55760405163b562e8dd60e01b815260040160405180910390fd5b6001600160a01b0384166000818152606a6020908152604080832080546001600160801b031981166001600160401b038083168b018116918217600160401b6001600160401b031990941690921783900481168b01811690920217909155858452606990925290912080546001600160e01b0319168317600160a01b429093169290920291909117905581908185019061447e90613a59565b156144f4575b60405182906001600160a01b03881690600090600080516020615eb5833981519152908290a46144bd6000878480600101955087613a68565b6144da576040516368d2bf6b60e11b815260040160405180910390fd5b8082036144845782606554146144ef57600080fd5b614527565b5b6040516001830192906001600160a01b03881690600090600080516020615eb5833981519152908290a48082036144f5575b50606555611313600085838684565b60606000614545836002615973565b61455090600261593d565b6001600160401b0381111561456757614567614a57565b6040519080825280601f01601f191660200182016040528015614591576020820181803683370190505b509050600360fc1b816000815181106145ac576145ac6159e5565b60200101906001600160f81b031916908160001a905350600f60fb1b816001815181106145db576145db6159e5565b60200101906001600160f81b031916908160001a90535060006145ff846002615973565b61460a90600161593d565b90505b6001811115614682576f181899199a1a9b1b9c1cb0b131b232b360811b85600f166010811061463e5761463e6159e5565b1a60f81b828281518110614654576146546159e5565b60200101906001600160f81b031916908160001a90535060049490941c9361467b81615e7d565b905061460d565b50831561133f5760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e746044820152606401610cf4565b6000806fa2a8918ca85bafe22016d0b997e4df60600160ff1b038311156146fe57506000905060036147ab565b8460ff16601b1415801561471657508460ff16601c14155b1561472757506000905060046147ab565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa15801561477b573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b0381166147a4576000600192509250506147ab565b9150600090505b94509492505050565b6000806001600160ff1b038316816147d160ff86901c601b61593d565b90506147df878288856146d1565b935093505050935093915050565b600081815b8451811015611fa057600085828151811061480f5761480f6159e5565b602002602001015190508083116148355760008381526020829052604090209250614846565b600081815260208490526040902092505b5080614851816159fb565b9150506147f2565b606061393784846000858561486d85613a59565b6148b95760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610cf4565b600080866001600160a01b031685876040516148d5919061590b565b60006040518083038185875af1925050503d8060008114614912576040519150601f19603f3d011682016040523d82523d6000602084013e614917565b606091505b5091509150614927828286614932565b979650505050505050565b6060831561494157508161133f565b8251156149515782518084602001fd5b8160405162461bcd60e51b8152600401610cf49190614ba8565b828054614977906159ab565b90600052602060002090601f01602090048101928261499957600085556149df565b82601f106149b257805160ff19168380011785556149df565b828001600101855582156149df579182015b828111156149df5782518255916020019190600101906149c4565b506149eb929150614a0f565b5090565b604080516060810182526000808252602082018190529181019190915290565b5b808211156149eb5760008155600101614a10565b6001600160e01b0319811681146134fe57600080fd5b600060208284031215614a4c57600080fd5b813561133f81614a24565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715614a9557614a95614a57565b604052919050565b600082601f830112614aae57600080fd5b81356001600160401b03811115614ac757614ac7614a57565b614ada601f8201601f1916602001614a6d565b818152846020838601011115614aef57600080fd5b816020850160208301376000918101602001919091529392505050565b60008060408385031215614b1f57600080fd5b82356001600160401b03811115614b3557600080fd5b614b4185828601614a9d565b95602094909401359450505050565b60005b83811015614b6b578181015183820152602001614b53565b838111156113135750506000910152565b60008151808452614b94816020860160208601614b50565b601f01601f19169290920160200192915050565b60208152600061133f6020830184614b7c565b600060208284031215614bcd57600080fd5b5035919050565b6001600160a01b0391909116815260200190565b6001600160a01b03811681146134fe57600080fd5b60008060408385031215614c1057600080fd5b8235614c1b81614be8565b946020939093013593505050565b600081518084526020808501808196508360051b8101915082860160005b85811015614c71578284038952614c5f848351614b7c565b98850198935090840190600101614c47565b5091979650505050505050565b60208152600061133f6020830184614c29565b60006001600160401b03821115614caa57614caa614a57565b5060051b60200190565b60008060408385031215614cc757600080fd5b82356001600160401b0380821115614cde57600080fd5b614cea86838701614a9d565b9350602091508185013581811115614d0157600080fd5b85019050601f81018613614d1457600080fd5b8035614d27614d2282614c91565b614a6d565b81815260059190911b82018301908381019088831115614d4657600080fd5b928401925b82841015614d6d578335614d5e81614be8565b82529284019290840190614d4b565b80955050505050509250929050565b60008083601f840112614d8e57600080fd5b5081356001600160401b03811115614da557600080fd5b6020830191508360208260051b8501011115613e1757600080fd5b600080600060408486031215614dd557600080fd5b8335925060208401356001600160401b03811115614df257600080fd5b614dfe86828701614d7c565b9497909650939450505050565b60008060408385031215614e1e57600080fd5b8235915060208301356001600160401b03811115614e3b57600080fd5b614e4785828601614a9d565b9150509250929050565b600060208284031215614e6357600080fd5b813561133f81614be8565b6020808252825182820181905260009190848201906040850190845b8181101561243257835183529284019291840191600101614e8a565b600080600060608486031215614ebb57600080fd5b8335614ec681614be8565b92506020840135614ed681614be8565b929592945050506040919091013590565b60008060408385031215614efa57600080fd5b823591506020830135614f0c81614be8565b809150509250929050565b600060208284031215614f2957600080fd5b81356001600160401b03811115614f3f57600080fd5b61393784828501614a9d565b6020808252825182820181905260009190848201906040850190845b818110156124325783516001600160a01b031683529284019291840191600101614f67565b80356001600160801b0381168114613a3057600080fd5b803563ffffffff81168114613a3057600080fd5b803561ffff81168114613a3057600080fd5b80151581146134fe57600080fd5b8035613a3081614fc9565b600080600080600060a08688031215614ffa57600080fd5b85356001600160401b0381111561501057600080fd5b61501c88828901614a9d565b95505061502b60208701614f8c565b935061503960408701614fa3565b925061504760608701614fb7565b9150608086013561505781614fc9565b809150509295509295909350565b600080600080600080600060e0888a03121561508057600080fd5b873561508b81614be8565b96506020880135955060408801359450606088013593506080880135925060a08801356150b781614be8565b915060c08801356001600160401b038111156150d257600080fd5b6150de8a828b01614a9d565b91505092959891949750929550565b600080600080600080600080610100898b03121561510a57600080fd5b88356001600160401b038082111561512157600080fd5b61512d8c838d01614a9d565b995060209150818b013561514081614be8565b985060408b0135975060608b0135965060808b0135955060a08b0135945060c08b013561516c81614be8565b935060e08b01358181111561518057600080fd5b8b019050601f81018c1361519357600080fd5b80356151a1614d2282614c91565b81815260059190911b8201830190838101908e8311156151c057600080fd5b928401925b828410156151de578335825292840192908401906151c5565b80955050505050509295985092959890939650565b600080600080600080600080610100898b03121561521057600080fd5b88356001600160401b0381111561522657600080fd5b6152328b828c01614a9d565b98505061524160208a01614f8c565b965061524f60408a01614fa3565b955061525d60608a01614fb7565b9450608089013561526d81614fc9565b935060a089013561527d81614fc9565b925060c089013561528d81614fc9565b915060e089013561529d81614be8565b809150509295985092959890939650565b600060208083850312156152c157600080fd5b82356001600160401b038111156152d757600080fd5b8301601f810185136152e857600080fd5b80356152f6614d2282614c91565b81815260059190911b8201830190838101908783111561531557600080fd5b928401925b828410156149275783358252928401929084019061531a565b80516001600160a01b031682526020808201516001600160401b0316908301526040908101511515910152565b6020808252825182820181905260009190848201906040850190845b818110156124325761538f838551615333565b928401926060929092019160010161537c565b60008060008060008060c087890312156153bb57600080fd5b86356153c681614fc9565b955060208701356153d681614fc9565b945060408701356153e681614fc9565b935060608701356153f681614fc9565b9250608087013561540681614fc9565b915060a087013561541681614fc9565b809150509295509295509295565b600080600080600080600080610100898b03121561544157600080fd5b883561544c81614be8565b97506020890135965060408901359550606089013594506080890135935060a089013561547881614be8565b925060c089013561548881614be8565b8092505060e089013590509295985092959890939650565b600080604083850312156154b357600080fd5b50508035926020909101359150565b600080600080606085870312156154d857600080fd5b84356001600160401b03808211156154ef57600080fd5b818701915087601f83011261550357600080fd5b81358181111561551257600080fd5b88602082850101111561552457600080fd5b60209283019650945061553a9187019050614f8c565b9150604085013561554a81614be8565b939692955090935050565b81516001600160801b0316815260208083015163ffffffff169082015260408083015161ffff16908201526060808301511515908201526080828101516101008301916155a59084018215159052565b5060a08301516155b960a084018215159052565b5060c08301516155cd60c084018215159052565b5060e083015161229560e08401826001600160a01b03169052565b6000806000606084860312156155fd57600080fd5b833561560881614be8565b95602085013595506040909401359392505050565b60006020828403121561562f57600080fd5b81356001600160401b038116811461133f57600080fd5b6000806040838503121561565957600080fd5b823561566481614be8565b91506020830135614f0c81614fc9565b6040815260006156876040830185614c29565b82810360208481019190915284518083528582019282019060005b818110156156be578451835293830193918301916001016156a2565b5090979650505050505050565b600080600080608085870312156156e157600080fd5b84356156ec81614be8565b935060208501356156fc81614be8565b92506040850135915060608501356001600160401b0381111561571e57600080fd5b61572a87828801614a9d565b91505092959194509250565b6000806040838503121561574957600080fd5b823561575481614be8565b915060208301356001600160401b03811115614e3b57600080fd5b60608101610ca08284615333565b6000806000806040858703121561579357600080fd5b84356001600160401b03808211156157aa57600080fd5b6157b688838901614d7c565b909650945060208701359150808211156157cf57600080fd5b506157dc87828801614d7c565b95989497509550505050565b600080604083850312156157fb57600080fd5b82356001600160401b038082111561581257600080fd5b61581e86838701614a9d565b9350602085013591508082111561583457600080fd5b50614e4785828601614a9d565b60008060006040848603121561585657600080fd5b83356001600160401b0381111561586c57600080fd5b61587886828701614d7c565b909450925050602084013561588c81614fc9565b809150509250925092565b600080604083850312156158aa57600080fd5b82356158b581614be8565b91506020830135614f0c81614be8565b600080604083850312156158d857600080fd5b82356001600160401b038111156158ee57600080fd5b6158fa85828601614a9d565b9250506020830135614f0c81614fc9565b6000825161591d818460208701614b50565b9190910192915050565b634e487b7160e01b600052601160045260246000fd5b6000821982111561595057615950615927565b500190565b6020808252600490820152636e6f706560e01b604082015260600190565b600081600019048311821515161561598d5761598d615927565b500290565b6001600160a01b03929092168252602082015260400190565b600181811c908216806159bf57607f821691505b6020821081036159df57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b600060018201615a0d57615a0d615927565b5060010190565b602080825260029082015261617360f01b604082015260600190565b6020808252600290820152616e6160f01b604082015260600190565b6020808252600890820152677069636b206f6e6560c01b604082015260600190565b634e487b7160e01b600052601260045260246000fd5b600082615a9357615a93615a6e565b500490565b600060208284031215615aaa57600080fd5b5051919050565b8035613a3081614be8565b60008060008060008060008060008060006101608c8e031215615ade57600080fd5b6001600160401b038c35811015615af457600080fd5b615b018e8e358f01614a9d565b9b508060208e01351115615b1457600080fd5b615b248e60208f01358f01614a9d565b9a508060408e01351115615b3757600080fd5b50615b488d60408e01358e01614a9d565b9850615b5660608d01615ab1565b9750615b6460808d01614fd7565b9650615b7260a08d01614fd7565b9550615b8060c08d01614fd7565b9450615b8e60e08d01614fd7565b9350615b9d6101008d01614fd7565b9250615bac6101208d01614fd7565b9150615bbb6101408d01614fd7565b90509295989b509295989b9093969950565b60208082526010908201526f64697361626c6564206665617475726560801b604082015260600190565b6020808252600290820152611c1960f21b604082015260600190565b60008351615c25818460208801614b50565b637572692f60e01b9083019081528351615c46816004840160208801614b50565b01600401949350505050565b60008251615c64818460208701614b50565b6b636f6e74726163745f75726960a01b920191825250600c01919050565b600063ffffffff83811690831681811015615c9f57615c9f615927565b039392505050565b6020808252602e908201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160408201526d191e481a5b9a5d1a585b1a5e995960921b606082015260800190565b6001600160a01b0385811682528416602082015260408101839052608060608201819052600090615d2890830184614b7c565b9695505050505050565b600060208284031215615d4457600080fd5b815161133f81614a24565b600082821015615d6157615d61615927565b500390565b600082615d7557615d75615a6e565b500690565b6020808252602b908201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960408201526a6e697469616c697a696e6760a81b606082015260800190565b76020b1b1b2b9b9a1b7b73a3937b61d1030b1b1b7bab73a1604d1b815260008351615df7816017850160208801614b50565b7001034b99036b4b9b9b4b733903937b6329607d1b6017918401918201528351615e28816028840160208801614b50565b01602801949350505050565b634e487b7160e01b600052602160045260246000fd5b600060208284031215615e5c57600080fd5b815161133f81614fc9565b634e487b7160e01b600052603160045260246000fd5b600081615e8c57615e8c615927565b50600019019056fe9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6ddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3efa2646970667358221220ba7a5819153347ac16b12abec993315040aecbf1a3587d6c255beef969d616b864736f6c634300080e0033
Deployed Bytecode
0x6080604052600436106102f45760003560e01c806301ffc9a7146102f9578063056b01ce1461032e57806306fdde0314610343578063081812fc14610365578063095ea7b3146103925780630e4bef5a146103b25780631234170d146103d2578063137fdac0146103f457806318160ddd14610414578063196f0f62146104375780631bb3624c146104575780631c31f710146104775780631fc1e25f1461049757806323b872dd146104c4578063248a9ca3146104e45780632d20fb60146105045780632f2ff15d14610524578063338bd19a1461054457806336568abe14610571578063373f68711461059157806338af3eed146105b15780633f651786146105d257806342842e0e146105f2578063449e14c61461061257806346e410541461062557806351cff8d914610638578063541b47f4146106585780635bbb2177146106785780635e95a47b146106a55780636352211e146106c557806370a08231146106e557806379502c55146107055780637ee5a0a6146107bb578063823b92f7146107db5780638462151c146107fb5780639010d07c1461081b57806391d148541461083b57806394d0d3a61461085b57806395d89b411461088c5780639606d076146108a157806396478cfd146108c157806397d017b6146108e157806398ea15721461090157806399a2557a1461092e5780639c4f3d0a1461094e578063a217fddf1461096e578063a22cb46514610983578063b7582c1a146109a3578063b7aafa87146109c6578063b88d4fde146109e6578063bf65df9b14610a06578063c23dc68f14610a26578063c30f4a5a14610a53578063c87b56dd14610a73578063c99323a014610a93578063ca15c87314610ab3578063d2f01f1914610ad3578063d539139314610af3578063d547741f14610b15578063d7224ba014610b35578063deb9a3a214610b4b578063e0cfc8ef14610b6b578063e8a3d48514610b8b578063e985e9c514610ba0578063f4990d9414610be9578063f7eb983f14610c09578063fe88a71d14610c40575b600080fd5b34801561030557600080fd5b50610319610314366004614a3a565b610c60565b60405190151581526020015b60405180910390f35b61034161033c366004614b0c565b610ca6565b005b34801561034f57600080fd5b50610358610f38565b6040516103259190614ba8565b34801561037157600080fd5b50610385610380366004614bbb565b610fca565b6040516103259190614bd4565b34801561039e57600080fd5b506103416103ad366004614bfd565b61100e565b3480156103be57600080fd5b506103586103cd366004614bbb565b61109b565b3480156103de57600080fd5b506103e7611148565b6040516103259190614c7e565b34801561040057600080fd5b5061034161040f366004614cb4565b611222565b34801561042057600080fd5b506104296112bd565b604051908152602001610325565b34801561044357600080fd5b50610341610452366004614dc0565b6112cb565b34801561046357600080fd5b50610319610472366004614e0b565b611319565b34801561048357600080fd5b50610341610492366004614e51565b611346565b3480156104a357600080fd5b506104b76104b2366004614e51565b61139f565b6040516103259190614e6e565b3480156104d057600080fd5b506103416104df366004614ea6565b6113aa565b3480156104f057600080fd5b506104296104ff366004614bbb565b6113b5565b34801561051057600080fd5b5061034161051f366004614bbb565b6113ca565b34801561053057600080fd5b5061034161053f366004614ee7565b61150b565b34801561055057600080fd5b5061056461055f366004614f17565b611527565b6040516103259190614f4b565b34801561057d57600080fd5b5061034161058c366004614ee7565b61156b565b34801561059d57600080fd5b506103416105ac366004614fe2565b6115e9565b3480156105bd57600080fd5b5061010e54610385906001600160a01b031681565b3480156105de57600080fd5b506103416105ed366004614bfd565b611696565b3480156105fe57600080fd5b5061034161060d366004614ea6565b6116d9565b610341610620366004615065565b6116f4565b6103416106333660046150ed565b611874565b34801561064457600080fd5b50610341610653366004614e51565b611a6d565b34801561066457600080fd5b506103416106733660046151f3565b611c7b565b34801561068457600080fd5b506106986106933660046152ae565b611ef4565b6040516103259190615360565b3480156106b157600080fd5b506103416106c03660046153a2565b611fa8565b3480156106d157600080fd5b506103856106e0366004614bbb565b612044565b3480156106f157600080fd5b50610429610700366004614e51565b612056565b34801561071157600080fd5b506101045461076b9060ff80821691610100810482169162010000820481169163010000008104821691600160201b8204811691600160281b8104821691600160301b82041690600160381b90046001600160401b031688565b604080519815158952961515602089015294151595870195909552911515606086015215156080850152151560a084015290151560c08301526001600160401b031660e082015261010001610325565b3480156107c757600080fd5b506103e76107d6366004614e51565b6120a4565b3480156107e757600080fd5b506104296107f6366004615424565b61229c565b34801561080757600080fd5b506104b7610816366004614e51565b612314565b34801561082757600080fd5b506103856108363660046154a0565b61243e565b34801561084757600080fd5b50610319610856366004614ee7565b612456565b34801561086757600080fd5b50610319610876366004614bbb565b6101096020526000908152604090205460ff1681565b34801561089857600080fd5b50610358612481565b3480156108ad57600080fd5b506103416108bc3660046154c2565b612490565b3480156108cd57600080fd5b506105646108dc366004614bbb565b61269a565b3480156108ed57600080fd5b506103416108fc366004614bfd565b612745565b34801561090d57600080fd5b5061092161091c366004614f17565b6127ad565b6040516103259190615555565b34801561093a57600080fd5b506104b76109493660046155e8565b6128c4565b34801561095a57600080fd5b5061034161096936600461561d565b612a85565b34801561097a57600080fd5b50610429600081565b34801561098f57600080fd5b5061034161099e366004615646565b612aef565b3480156109af57600080fd5b506109b8612b84565b604051610325929190615674565b3480156109d257600080fd5b506103416109e1366004614b0c565b612ca2565b3480156109f257600080fd5b50610341610a013660046156cb565b612cee565b348015610a1257600080fd5b50610319610a21366004615736565b612d3e565b348015610a3257600080fd5b50610a46610a41366004614bbb565b612e28565b604051610325919061576f565b348015610a5f57600080fd5b50610341610a6e366004614f17565b612ebd565b348015610a7f57600080fd5b50610358610a8e366004614bbb565b612eff565b348015610a9f57600080fd5b50610341610aae36600461577d565b612f88565b348015610abf57600080fd5b50610429610ace366004614bbb565b61304b565b348015610adf57600080fd5b50610341610aee3660046157e8565b613062565b348015610aff57600080fd5b50610429600080516020615e9583398151915281565b348015610b2157600080fd5b50610341610b30366004614ee7565b6130a3565b348015610b4157600080fd5b50610429606d5481565b348015610b5757600080fd5b50610341610b66366004614dc0565b6130bf565b348015610b7757600080fd5b50610341610b86366004615841565b613107565b348015610b9757600080fd5b506103586131b3565b348015610bac57600080fd5b50610319610bbb366004615897565b6001600160a01b039182166000908152606c6020908152604080832093909416825291909152205460ff1690565b348015610bf557600080fd5b50610341610c04366004614cb4565b6131e7565b348015610c1557600080fd5b506103586040518060400160405280600b81526020016a0534249492d373231412d360ac1b81525081565b348015610c4c57600080fd5b50610341610c5b3660046158c5565b61327b565b60006001600160e01b031982166380ac58cd60e01b1480610c9157506001600160e01b03198216635b5e139f60e01b145b80610ca05750610ca0826132de565b92915050565b6002606e5403610cfd5760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c0060448201526064015b60405180910390fd5b6002606e55604051600090610d1690849060200161590b565b60408051601f19818403018152918152815160209283012060008181526101089093529120909150610d488184613303565b8054600160c01b900460ff1615610d8e5760405162461bcd60e51b815260206004820152600a60248201526977726f6e67206461746160b01b6044820152606401610cf4565b8054600160b81b900460ff16610e6757600082815261010660205260409020610db790336133f5565b610dc057600080fd5b8054600083815261010a60209081526040808320338452909152902054600160a01b90910461ffff1690610df590859061593d565b1115610e325760405162461bcd60e51b815260206004820152600c60248201526b6f7574206f662071756f746160a01b6044820152606401610cf4565b600082815261010a6020908152604080832033845290915281208054859290610e5c90849061593d565b90915550610e939050565b8054600160a01b900461ffff16831115610e935760405162461bcd60e51b8152600401610cf490615955565b600181015481547335603bb6ae52be0dbf419bdf454e5b8e06437ed591630b63fe95916001600160a01b0390911690610ed69087906001600160801b0316615973565b6040518363ffffffff1660e01b8152600401610ef3929190615992565b60006040518083038186803b158015610f0b57600080fd5b505af4158015610f1f573d6000803e3d6000fd5b50505050610f2d338461340a565b50506001606e555050565b606060678054610f47906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054610f73906159ab565b8015610fc05780601f10610f9557610100808354040283529160200191610fc0565b820191906000526020600020905b815481529060010190602001808311610fa357829003601f168201915b5050505050905090565b6000610fd58261345f565b610ff2576040516333d1c03960e21b815260040160405180910390fd5b506000908152606b60205260409020546001600160a01b031690565b600061101982612044565b9050806001600160a01b0316836001600160a01b03160361104d5760405163250fdee360e21b815260040160405180910390fd5b336001600160a01b0382161480159061106d575061106b8133610bbb565b155b1561108b576040516367d9dca160e11b815260040160405180910390fd5b611096838383613498565b505050565b61010581815481106110ac57600080fd5b9060005260206000200160009150905080546110c7906159ab565b80601f01602080910402602001604051908101604052809291908181526020018280546110f3906159ab565b80156111405780601f1061111557610100808354040283529160200191611140565b820191906000526020600020905b81548152906001019060200180831161112357829003601f168201915b505050505081565b6060610105805480602002602001604051908101604052809291908181526020016000905b8282101561121957838290600052602060002001805461118c906159ab565b80601f01602080910402602001604051908101604052809291908181526020018280546111b8906159ab565b80156112055780601f106111da57610100808354040283529160200191611205565b820191906000526020600020905b8154815290600101906020018083116111e857829003601f168201915b50505050508152602001906001019061116d565b50505050905090565b600061122d816134f4565b600083604051602001611240919061590b565b60405160208183030381529060405280519060200120905060005b83518110156112b6576112a3848281518110611279576112796159e5565b6020026020010151610106600085815260200190815260200160002061350190919063ffffffff16565b50806112ae816159fb565b91505061125b565b5050505050565b606654606554036000190190565b60005b8181101561131357611301848484848181106112ec576112ec6159e5565b9050602002016020810190610b309190614e51565b8061130b816159fb565b9150506112ce565b50505050565b600061133f600080516020615e9583398151915261085661133986613516565b8561356e565b9392505050565b6000611351816134f4565b61010e546001600160a01b03161561137b5760405162461bcd60e51b8152600401610cf490615a14565b5061010e80546001600160a01b0319166001600160a01b0392909216919091179055565b6060610ca082612314565b61109683838361358a565b600090815260a0602052604090206001015490565b806000036113eb576040516356be441560e01b815260040160405180910390fd5b60016065540361140e5760405163c0367cab60e01b815260040160405180910390fd5b606d54600081900361141e575060015b6065548110611440576040516370e89b1b60e01b815260040160405180910390fd5b606554828201600019810191101561145b5750606554600019015b815b818111611500576000818152606960205260409020546001600160a01b031615801561149f5750600081815260696020526040902054600160e01b900460ff16155b156114f85760006114af82613762565b80516000848152606960209081526040909120805491909301516001600160401b0316600160a01b026001600160e01b03199091166001600160a01b0390921691909117179055505b60010161145d565b50600101606d555050565b611514826113b5565b61151d816134f4565b6110968383613874565b6060610ca0610106600084604051602001611542919061590b565b604051602081830303815290604052805190602001208152602001908152602001600020613896565b6001600160a01b03811633146115db5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b6064820152608401610cf4565b6115e582826138a3565b5050565b60006115f4816134f4565b600086604051602001611607919061590b565b60408051601f198184030181529181528151602092830120600090815261010890925290208054931515600160b81b0260ff60b81b1961ffff909616600160a01b029590951663ff00ffff60a01b1963ffffffff909716600160801b026001600160a01b03199095166001600160801b0390981697909717939093179490941694909417919091179055505050565b60405162461bcd60e51b81526020600482015260186024820152776e6f7420737570706f727465642062792037323161206c6160401b6044820152606401610cf4565b61109683838360405180602001604052806000815250612cee565b6000611706888888888888304661229c565b61010454909150600160301b900460ff166117335760405162461bcd60e51b8152600401610cf490615a30565b610104546301000000900460ff1661175d5760405162461bcd60e51b8152600401610cf490615a30565b6117678183611319565b61177057600080fd5b611779856138c5565b6001600160a01b038816156117b0576001600160a01b03881633146117b05760405162461bcd60e51b8152600401610cf490615955565b600087116117d05760405162461bcd60e51b8152600401610cf490615a4c565b85156117ee5760405162461bcd60e51b8152600401610cf490615955565b7335603bb6ae52be0dbf419bdf454e5b8e06437ed5630b63fe95846118138a88615973565b6040518363ffffffff1660e01b8152600401611830929190615992565b60006040518083038186803b15801561184857600080fd5b505af415801561185c573d6000803e3d6000fd5b5050505061186a888861340a565b5050505050505050565b600088604051602001611887919061590b565b60408051601f198184030181529181528151602092830120600081815261010890935291209091506118b98189613303565b8054600160c01b900460ff166118fb5760405162461bcd60e51b81526020600482015260076024820152661a5b9d985b1a5960ca1b6044820152606401610cf4565b600061190d8a8a8a8a8a8a304661229c565b6000848152610107602052604090205490915061192c9082908661392a565b6119665760405162461bcd60e51b815260206004820152600b60248201526a6661696c206d65726b6c6560a81b6044820152606401610cf4565b61196f876138c5565b6001600160a01b038a16156119a6576001600160a01b038a1633146119a65760405162461bcd60e51b8152600401610cf490615955565b600089116119c65760405162461bcd60e51b8152600401610cf490615a4c565b87156119e45760405162461bcd60e51b8152600401610cf490615955565b7335603bb6ae52be0dbf419bdf454e5b8e06437ed5630b63fe9586611a098c8a615973565b6040518363ffffffff1660e01b8152600401611a26929190615992565b60006040518083038186803b158015611a3e57600080fd5b505af4158015611a52573d6000803e3d6000fd5b50505050611a608a8a61340a565b5050505050505050505050565b61010e546001600160a01b031680611ac657611a8a600033612456565b611ac35760405162461bcd60e51b815260206004820152600a60248201526961646d696e206f6e6c7960b01b6044820152606401610cf4565b50335b6001600160a01b038216611b625761010c5461010d546001600160a01b03909116906108fc9061271090611afa9047615973565b611b049190615a84565b6040518115909202916000818181858888f19350505050158015611b2c573d6000803e3d6000fd5b506040516001600160a01b038216904780156108fc02916000818181858888f19350505050158015611096573d6000803e3d6000fd5b61010c5461010d546040516370a0823160e01b81528492611c0a926001600160a01b0391821692612710928616906370a0823190611ba4903090600401614bd4565b602060405180830381865afa158015611bc1573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611be59190615a98565b611bef9190615973565b611bf99190615a84565b6001600160a01b038416919061393f565b61109682826001600160a01b03166370a08231306040518263ffffffff1660e01b8152600401611c3a9190614bd4565b602060405180830381865afa158015611c57573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611bf99190615a98565b6000611c86816134f4565b600089604051602001611c99919061590b565b60408051808303601f1901815291815281516020928301206000818152610108909352912054909150600160c81b900460ff1615611d095760405162461bcd60e51b815260206004820152600d60248201526c185b1c9958591e48195e1a5cdd609a1b6044820152606401610cf4565b61010580546001810182556000919091528a51611d4d917ffc62abc8c0fc47c2d92f5aec99bf8b60f375828e14394d89345cae11a9867371019060208d019061496b565b506040518061010001604052808a6001600160801b031681526020018963ffffffff1681526020018861ffff168152602001871515815260200186151581526020018515158152602001600115158152602001846001600160a01b0316815250610108600083815260200190815260200160002060008201518160000160006101000a8154816001600160801b0302191690836001600160801b0316021790555060208201518160000160106101000a81548163ffffffff021916908363ffffffff16021790555060408201518160000160146101000a81548161ffff021916908361ffff16021790555060608201518160000160166101000a81548160ff02191690831515021790555060808201518160000160176101000a81548160ff02191690831515021790555060a08201518160000160186101000a81548160ff02191690831515021790555060c08201518160000160196101000a81548160ff02191690831515021790555060e08201518160010160006101000a8154816001600160a01b0302191690836001600160a01b0316021790555090505050505050505050505050565b80516060906000816001600160401b03811115611f1357611f13614a57565b604051908082528060200260200182016040528015611f4c57816020015b611f396149ef565b815260200190600190039081611f315790505b50905060005b828114611fa057611f7b858281518110611f6e57611f6e6159e5565b6020026020010151612e28565b828281518110611f8d57611f8d6159e5565b6020908102919091010152600101611f52565b509392505050565b6000611fb3816134f4565b61010454610100900460ff16611fc857600080fd5b50610104805461ffff191696151561ff00191696909617610100951515959095029490941763ffff00001916620100009315159390930263ff0000001916929092176301000000911515919091021761ffff60281b1916600160281b9115159190910260ff60301b191617600160301b91151591909102179055565b600061204f82613762565b5192915050565b60006001600160a01b03821661207f576040516323d3ad8160e21b815260040160405180910390fd5b506001600160a01b03166000908152606a60205260409020546001600160401b031690565b610105546060906000906001600160401b038111156120c5576120c5614a57565b6040519080825280602002602001820160405280156120f857816020015b60608152602001906001900390816120e35790505b50905060005b61010554811015612295576121b9846101058381548110612121576121216159e5565b906000526020600020018054612136906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054612162906159ab565b80156121af5780601f10612184576101008083540402835291602001916121af565b820191906000526020600020905b81548152906001019060200180831161219257829003601f168201915b5050505050612d3e565b156122835761010581815481106121d2576121d26159e5565b9060005260206000200180546121e7906159ab565b80601f0160208091040260200160405190810160405280929190818152602001828054612213906159ab565b80156122605780601f1061223557610100808354040283529160200191612260565b820191906000526020600020905b81548152906001019060200180831161224357829003601f168201915b5050505050828281518110612277576122776159e5565b60200260200101819052505b8061228d816159fb565b9150506120fe565b5092915050565b6040516001600160601b031960608a811b82166020840152603483018a905260548301899052607483018890526094830187905285811b821660b484015284901b1660c882015260dc810182905260009060fc0160405160208183030381529060405280519060200120905098975050505050505050565b6060600080600061232485612056565b90506000816001600160401b0381111561234057612340614a57565b604051908082528060200260200182016040528015612369578160200160208202803683370190505b5090506123746149ef565b60015b83861461243257600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161515918101829052925061242a5781516001600160a01b0316156123eb57815194505b876001600160a01b0316856001600160a01b03160361242a578083878060010198508151811061241d5761241d6159e5565b6020026020010181815250505b600101612377565b50909695505050505050565b600082815260d26020526040812061133f9083613995565b600091825260a0602090815260408084206001600160a01b0393909316845291905290205460ff1690565b606060688054610f47906159ab565b600061249c60016139a1565b905080156124b4576000805461ff0019166101001790555b8161010c60006101000a8154816001600160a01b0302191690836001600160a01b03160217905550826001600160801b031661010d8190555060008060008060008060008060008060008f8f81019061250d9190615abc565b9a509a509a509a509a509a509a509a509a509a509a5061252d8b8b613a35565b612538600089613a4f565b612550600080516020615e9583398151915289613a4f565b88516125649061010b9060208c019061496b565b5060408051610100808201835298151580825297151560208201819052961515918101829052941515606086018190529315156080860181905292151560a0860181905291151560c08601819052600060e090960195909552610104805461ffff191661ff001990981697909717959097029490941763ffff000019166201000090960263ff00000019169590951763010000009091021761ffff60201b1916600160201b90940260ff60281b191693909317600160281b90910217600160301b600160781b031916600160301b909202600160381b600160781b0319169190911790555050821591506112b69050576000805461ff0019169055604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb38474024989060200160405180910390a15050505050565b606060006126a78361304b565b9050806001600160401b038111156126c1576126c1614a57565b6040519080825280602002602001820160405280156126ea578160200160208202803683370190505b50915060005b8181101561273e57612702848261243e565b838281518110612714576127146159e5565b6001600160a01b039092166020928302919091019091015280612736816159fb565b9150506126f0565b5050919050565b610104546301000000900460ff1661276f5760405162461bcd60e51b8152600401610cf490615bcd565b612787600080516020615e9583398151915233612456565b6127a35760405162461bcd60e51b8152600401610cf490615bf7565b6115e5828261340a565b6040805161010081018252600080825260208201819052918101829052606081018290526080810182905260a0810182905260c0810182905260e0810191909152610108600083604051602001612804919061590b565b60408051601f19818403018152918152815160209283012083528282019390935290820160002082516101008101845281546001600160801b038116825263ffffffff600160801b8204169382019390935261ffff600160a01b8404169381019390935260ff600160b01b8304811615156060850152600160b81b8304811615156080850152600160c01b83048116151560a0850152600160c81b909204909116151560c0830152600101546001600160a01b031660e082015292915050565b60608183106128e657604051631960ccad60e11b815260040160405180910390fd5b60655460009060018510156128fa57600194505b80841115612906578093505b600061291187612056565b905084861015612930578585038181101561292a578091505b50612934565b5060005b6000816001600160401b0381111561294e5761294e614a57565b604051908082528060200260200182016040528015612977578160200160208202803683370190505b5090508160000361298d57935061133f92505050565b600061299888612e28565b9050600081604001516129a9575080515b885b8881141580156129bb5750848714155b15612a7457600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff1615159181018290529350612a6c5782516001600160a01b031615612a2d57825191505b8a6001600160a01b0316826001600160a01b031603612a6c5780848880600101995081518110612a5f57612a5f6159e5565b6020026020010181815250505b6001016129ab565b505050928352509095945050505050565b6000612a90816134f4565b61010454600160381b90046001600160401b031615612ac15760405162461bcd60e51b8152600401610cf490615a14565b5061010480546001600160401b03909216600160381b02600160381b600160781b0319909216919091179055565b336001600160a01b03831603612b185760405163b06307db60e01b815260040160405180910390fd5b336000818152606c602090815260408083206001600160a01b03871680855290835292819020805460ff191686151590811790915590519081529192917f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a35050565b6040805160028082526060828101909352829190816020015b6060815260200190600190039081612b9d57505060408051600280825260608201835292945091906020830190803683370190505090506040518060400160405280600681526020016526a4a72a22a960d11b81525082600081518110612c0657612c066159e5565b60200260200101819052506040518060400160405280600581526020016420a226a4a760d91b81525082600181518110612c4257612c426159e5565b6020026020010181905250600080516020615e9583398151915281600081518110612c6f57612c6f6159e5565b6020026020010181815250506000801b81600181518110612c9257612c926159e5565b6020026020010181815250509091565b6000612cad816134f4565b600083604051602001612cc0919061590b565b60408051601f1981840301815291815281516020928301206000908152610107909252902092909255505050565b612cf984848461358a565b612d0b836001600160a01b0316613a59565b8015612d205750612d1e84848484613a68565b155b15611313576040516368d2bf6b60e11b815260040160405180910390fd5b600080612d4a836127ad565b90508060600151612d5f576000915050610ca0565b806020015163ffffffff16600003612d7b576000915050610ca0565b600083604051602001612d8e919061590b565b6040516020818303038152906040528051906020012090508160800151158015612dce5750600081815261010660205260409020612dcc90866133f5565b155b15612dde57600092505050610ca0565b604080830151600083815261010a60209081528382206001600160a01b038a1683529052919091205461ffff90911611612e1d57600092505050610ca0565b506001949350505050565b612e306149ef565b612e386149ef565b6001831080612e4957506065548310155b15612e545792915050565b50600082815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161580159282019290925290612eb45792915050565b61133f83613762565b6000612ec8816134f4565b6101045460ff16612eeb5760405162461bcd60e51b8152600401610cf490615a30565b81516110969061010b90602085019061496b565b6060612f0a8261345f565b612f4a5760405162461bcd60e51b81526020600482015260116024820152703737b732bc34b9ba32b73a103a37b5b2b760791b6044820152606401610cf4565b6000612f54613b53565b905080612f6084613b63565b604051602001612f71929190615c13565b604051602081830303815290604052915050919050565b610104546301000000900460ff16612fb25760405162461bcd60e51b8152600401610cf490615bcd565b612fca600080516020615e9583398151915233612456565b612fe65760405162461bcd60e51b8152600401610cf490615bf7565b60005b838110156112b657613039858583818110613006576130066159e5565b905060200201602081019061301b9190614e51565b84848481811061302d5761302d6159e5565b90506020020135612745565b80613043816159fb565b915050612fe9565b600081815260d260205260408120610ca090613c63565b61306a613c6d565b613072613c6d565b815161308590606790602085019061496b565b50805161309990606890602084019061496b565b5060016065555050565b6130ac826113b5565b6130b5816134f4565b61109683836138a3565b60005b81811015611313576130f5848484848181106130e0576130e06159e5565b905060200201602081019061053f9190614e51565b806130ff816159fb565b9150506130c2565b6000613112816134f4565b610104546301000000900460ff166131515760405162461bcd60e51b8152602060048201526002602482015261323360f11b6044820152606401610cf4565b60005b838110156112b657826101096000878785818110613174576131746159e5565b90506020020135815260200190815260200160002060006101000a81548160ff02191690831515021790555080806131ab906159fb565b915050613154565b606060006131bf613b53565b9050806040516020016131d29190615c52565b60405160208183030381529060405291505090565b60006131f2816134f4565b600083604051602001613205919061590b565b60405160208183030381529060405280519060200120905060005b83518110156112b65761326884828151811061323e5761323e6159e5565b60200260200101516101066000858152602001908152602001600020613c9690919063ffffffff16565b5080613273816159fb565b915050613220565b6000613286816134f4565b600083604051602001613299919061590b565b60408051601f198184030181529181528151602092830120600090815261010890925290208054931515600160b01b0260ff60b01b1990941693909317909255505050565b60006001600160e01b03198216635a05180f60e01b1480610ca05750610ca082613cab565b8154600160b01b900460ff166133485760405162461bcd60e51b815260206004820152600a6024820152696e6f742061637469766560b01b6044820152606401610cf4565b8154600160801b900463ffffffff168111156133955760405162461bcd60e51b815260206004820152600c60248201526b6f7574206f662073746f636b60a01b6044820152606401610cf4565b6101045462010000900460ff166133b2573233146133b257600080fd5b8154819083906010906133d3908490600160801b900463ffffffff16615c82565b92506101000a81548163ffffffff021916908363ffffffff1602179055505050565b600061133f836001600160a01b038416613cd0565b61010454600160381b90046001600160401b0316156134555761010454600160381b90046001600160401b0316816134406112bd565b61344a919061593d565b111561345557600080fd5b6115e58282613ce8565b600081600111158015613473575060655482105b8015610ca0575050600090815260696020526040902054600160e01b900460ff161590565b6000828152606b602052604080822080546001600160a01b0319166001600160a01b0387811691821790925591518593918516917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591a4505050565b6134fe8133613d02565b50565b600061133f836001600160a01b038416613d66565b6000610ca0826040517b0ca2ba3432b932bab69029b4b3b732b21026b2b9b9b0b3b29d05199960211b6020820152603c8101829052600090605c01604051602081830303815290604052805190602001209050919050565b600080600061357d8585613db0565b91509150611fa081613e1e565b600061359582613762565b9050836001600160a01b031681600001516001600160a01b0316146135cc5760405162a1148160e81b815260040160405180910390fd5b6000336001600160a01b03861614806135ea57506135ea8533610bbb565b806136055750336135fa84610fca565b6001600160a01b0316145b90508061362557604051632ce44b5f60e11b815260040160405180910390fd5b6001600160a01b03841661364c57604051633a954ecd60e21b815260040160405180910390fd5b61365860008487613498565b6001600160a01b038581166000908152606a6020908152604080832080546001600160401b03198082166001600160401b0392831660001901831617909255898616808652838620805493841693831660019081018416949094179055898652606990945282852080546001600160e01b031916909417600160a01b4290921691909102178355870180845292208054919390911661372b57606554821461372b57805460208601516001600160401b0316600160a01b026001600160e01b03199091166001600160a01b038a16171781555b50505082846001600160a01b0316866001600160a01b0316600080516020615eb583398151915260405160405180910390a46112b6565b61376a6149ef565b818060011115801561377d575060655481105b1561385b57600081815260696020908152604091829020825160608101845290546001600160a01b0381168252600160a01b81046001600160401b031692820192909252600160e01b90910460ff161515918101829052906138595780516001600160a01b0316156137f0579392505050565b5060001901600081815260696020908152604091829020825160608101845290546001600160a01b038116808352600160a01b82046001600160401b031693830193909352600160e01b900460ff1615159281019290925215613854579392505050565b6137f0565b505b604051636f96cda160e11b815260040160405180910390fd5b61387e8282613fcf565b600082815260d2602052604090206110969082613501565b6060600061133f83614055565b6138ad82826140b1565b600082815260d2602052604090206110969082613c96565b6000818152610109602052604090205460ff161561390e5760405162461bcd60e51b8152600401610cf4906020808252600490820152631d5cd95960e21b604082015260600190565b600090815261010960205260409020805460ff19166001179055565b6000613937828486614118565b949350505050565b6110968363a9059cbb60e01b848460405160240161395e929190615992565b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915261412e565b600061133f8383614200565b60008054610100900460ff16156139ef578160ff1660011480156139cb57506139c930613a59565b155b6139e75760405162461bcd60e51b8152600401610cf490615ca7565b506000919050565b60005460ff808416911610613a165760405162461bcd60e51b8152600401610cf490615ca7565b506000805460ff191660ff92909216919091179055600190565b919050565b613a3d61422a565b613a478282613062565b6115e5613c6d565b6115e58282613874565b6001600160a01b03163b151590565b604051630a85bd0160e11b81526000906001600160a01b0385169063150b7a0290613a9d903390899088908890600401615cf5565b6020604051808303816000875af1925050508015613ad8575060408051601f3d908101601f19168201909252613ad591810190615d32565b60015b613b36573d808015613b06576040519150601f19603f3d011682016040523d82523d6000602084013e613b0b565b606091505b508051600003613b2e576040516368d2bf6b60e11b815260040160405180910390fd5b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050949350505050565b606061010b8054610f47906159ab565b606081600003613b8a5750506040805180820190915260018152600360fc1b602082015290565b8160005b8115613bb45780613b9e816159fb565b9150613bad9050600a83615a84565b9150613b8e565b6000816001600160401b03811115613bce57613bce614a57565b6040519080825280601f01601f191660200182016040528015613bf8576020820181803683370190505b5090505b841561393757613c0d600183615d4f565b9150613c1a600a86615d66565b613c2590603061593d565b60f81b818381518110613c3a57613c3a6159e5565b60200101906001600160f81b031916908160001a905350613c5c600a86615a84565b9450613bfc565b6000610ca0825490565b600054610100900460ff16613c945760405162461bcd60e51b8152600401610cf490615d7a565b565b600061133f836001600160a01b038416614258565b60006001600160e01b03198216637965db0b60e01b1480610ca05750610ca08261434b565b60009081526001919091016020526040902054151590565b6115e582826040518060200160405280600081525061439b565b613d0c8282612456565b6115e557613d24816001600160a01b03166014614536565b613d2f836020614536565b604051602001613d40929190615dc5565b60408051601f198184030181529082905262461bcd60e51b8252610cf491600401614ba8565b6000613d728383613cd0565b613da857508154600181810184556000848152602080822090930184905584548482528286019093526040902091909155610ca0565b506000610ca0565b6000808251604103613de65760208301516040840151606085015160001a613dda878285856146d1565b94509450505050613e17565b8251604003613e0f5760208301516040840151613e048683836147b4565b935093505050613e17565b506000905060025b9250929050565b6000816004811115613e3257613e32615e34565b03613e3a5750565b6001816004811115613e4e57613e4e615e34565b03613e965760405162461bcd60e51b815260206004820152601860248201527745434453413a20696e76616c6964207369676e617475726560401b6044820152606401610cf4565b6002816004811115613eaa57613eaa615e34565b03613ef75760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610cf4565b6003816004811115613f0b57613f0b615e34565b03613f635760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c604482015261756560f01b6064820152608401610cf4565b6004816004811115613f7757613f77615e34565b036134fe5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c604482015261756560f01b6064820152608401610cf4565b613fd98282612456565b6115e557600082815260a0602090815260408083206001600160a01b03851684529091529020805460ff191660011790556140113390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b6060816000018054806020026020016040519081016040528092919081815260200182805480156140a557602002820191906000526020600020905b815481526020019060010190808311614091575b50505050509050919050565b6140bb8282612456565b156115e557600082815260a0602090815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b60008261412585846147ed565b14949350505050565b6000614183826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166148599092919063ffffffff16565b80519091501561109657808060200190518101906141a19190615e4a565b6110965760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610cf4565b6000826000018281548110614217576142176159e5565b9060005260206000200154905092915050565b600054610100900460ff166142515760405162461bcd60e51b8152600401610cf490615d7a565b6001606e55565b6000818152600183016020526040812054801561434157600061427c600183615d4f565b855490915060009061429090600190615d4f565b90508181146142f55760008660000182815481106142b0576142b06159e5565b90600052602060002001549050808760000184815481106142d3576142d36159e5565b6000918252602080832090910192909255918252600188019052604090208390555b855486908061430657614306615e67565b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050610ca0565b6000915050610ca0565b60006001600160e01b031982166380ac58cd60e01b148061437c57506001600160e01b03198216635b5e139f60e01b145b80610ca057506301ffc9a760e01b6001600160e01b0319831614610ca0565b6065546001600160a01b0384166143c457604051622e076360e81b815260040160405180910390fd5b826000036143e55760405163b562e8dd60e01b815260040160405180910390fd5b6001600160a01b0384166000818152606a6020908152604080832080546001600160801b031981166001600160401b038083168b018116918217600160401b6001600160401b031990941690921783900481168b01811690920217909155858452606990925290912080546001600160e01b0319168317600160a01b429093169290920291909117905581908185019061447e90613a59565b156144f4575b60405182906001600160a01b03881690600090600080516020615eb5833981519152908290a46144bd6000878480600101955087613a68565b6144da576040516368d2bf6b60e11b815260040160405180910390fd5b8082036144845782606554146144ef57600080fd5b614527565b5b6040516001830192906001600160a01b03881690600090600080516020615eb5833981519152908290a48082036144f5575b50606555611313600085838684565b60606000614545836002615973565b61455090600261593d565b6001600160401b0381111561456757614567614a57565b6040519080825280601f01601f191660200182016040528015614591576020820181803683370190505b509050600360fc1b816000815181106145ac576145ac6159e5565b60200101906001600160f81b031916908160001a905350600f60fb1b816001815181106145db576145db6159e5565b60200101906001600160f81b031916908160001a90535060006145ff846002615973565b61460a90600161593d565b90505b6001811115614682576f181899199a1a9b1b9c1cb0b131b232b360811b85600f166010811061463e5761463e6159e5565b1a60f81b828281518110614654576146546159e5565b60200101906001600160f81b031916908160001a90535060049490941c9361467b81615e7d565b905061460d565b50831561133f5760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e746044820152606401610cf4565b6000806fa2a8918ca85bafe22016d0b997e4df60600160ff1b038311156146fe57506000905060036147ab565b8460ff16601b1415801561471657508460ff16601c14155b1561472757506000905060046147ab565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa15801561477b573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b0381166147a4576000600192509250506147ab565b9150600090505b94509492505050565b6000806001600160ff1b038316816147d160ff86901c601b61593d565b90506147df878288856146d1565b935093505050935093915050565b600081815b8451811015611fa057600085828151811061480f5761480f6159e5565b602002602001015190508083116148355760008381526020829052604090209250614846565b600081815260208490526040902092505b5080614851816159fb565b9150506147f2565b606061393784846000858561486d85613a59565b6148b95760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610cf4565b600080866001600160a01b031685876040516148d5919061590b565b60006040518083038185875af1925050503d8060008114614912576040519150601f19603f3d011682016040523d82523d6000602084013e614917565b606091505b5091509150614927828286614932565b979650505050505050565b6060831561494157508161133f565b8251156149515782518084602001fd5b8160405162461bcd60e51b8152600401610cf49190614ba8565b828054614977906159ab565b90600052602060002090601f01602090048101928261499957600085556149df565b82601f106149b257805160ff19168380011785556149df565b828001600101855582156149df579182015b828111156149df5782518255916020019190600101906149c4565b506149eb929150614a0f565b5090565b604080516060810182526000808252602082018190529181019190915290565b5b808211156149eb5760008155600101614a10565b6001600160e01b0319811681146134fe57600080fd5b600060208284031215614a4c57600080fd5b813561133f81614a24565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715614a9557614a95614a57565b604052919050565b600082601f830112614aae57600080fd5b81356001600160401b03811115614ac757614ac7614a57565b614ada601f8201601f1916602001614a6d565b818152846020838601011115614aef57600080fd5b816020850160208301376000918101602001919091529392505050565b60008060408385031215614b1f57600080fd5b82356001600160401b03811115614b3557600080fd5b614b4185828601614a9d565b95602094909401359450505050565b60005b83811015614b6b578181015183820152602001614b53565b838111156113135750506000910152565b60008151808452614b94816020860160208601614b50565b601f01601f19169290920160200192915050565b60208152600061133f6020830184614b7c565b600060208284031215614bcd57600080fd5b5035919050565b6001600160a01b0391909116815260200190565b6001600160a01b03811681146134fe57600080fd5b60008060408385031215614c1057600080fd5b8235614c1b81614be8565b946020939093013593505050565b600081518084526020808501808196508360051b8101915082860160005b85811015614c71578284038952614c5f848351614b7c565b98850198935090840190600101614c47565b5091979650505050505050565b60208152600061133f6020830184614c29565b60006001600160401b03821115614caa57614caa614a57565b5060051b60200190565b60008060408385031215614cc757600080fd5b82356001600160401b0380821115614cde57600080fd5b614cea86838701614a9d565b9350602091508185013581811115614d0157600080fd5b85019050601f81018613614d1457600080fd5b8035614d27614d2282614c91565b614a6d565b81815260059190911b82018301908381019088831115614d4657600080fd5b928401925b82841015614d6d578335614d5e81614be8565b82529284019290840190614d4b565b80955050505050509250929050565b60008083601f840112614d8e57600080fd5b5081356001600160401b03811115614da557600080fd5b6020830191508360208260051b8501011115613e1757600080fd5b600080600060408486031215614dd557600080fd5b8335925060208401356001600160401b03811115614df257600080fd5b614dfe86828701614d7c565b9497909650939450505050565b60008060408385031215614e1e57600080fd5b8235915060208301356001600160401b03811115614e3b57600080fd5b614e4785828601614a9d565b9150509250929050565b600060208284031215614e6357600080fd5b813561133f81614be8565b6020808252825182820181905260009190848201906040850190845b8181101561243257835183529284019291840191600101614e8a565b600080600060608486031215614ebb57600080fd5b8335614ec681614be8565b92506020840135614ed681614be8565b929592945050506040919091013590565b60008060408385031215614efa57600080fd5b823591506020830135614f0c81614be8565b809150509250929050565b600060208284031215614f2957600080fd5b81356001600160401b03811115614f3f57600080fd5b61393784828501614a9d565b6020808252825182820181905260009190848201906040850190845b818110156124325783516001600160a01b031683529284019291840191600101614f67565b80356001600160801b0381168114613a3057600080fd5b803563ffffffff81168114613a3057600080fd5b803561ffff81168114613a3057600080fd5b80151581146134fe57600080fd5b8035613a3081614fc9565b600080600080600060a08688031215614ffa57600080fd5b85356001600160401b0381111561501057600080fd5b61501c88828901614a9d565b95505061502b60208701614f8c565b935061503960408701614fa3565b925061504760608701614fb7565b9150608086013561505781614fc9565b809150509295509295909350565b600080600080600080600060e0888a03121561508057600080fd5b873561508b81614be8565b96506020880135955060408801359450606088013593506080880135925060a08801356150b781614be8565b915060c08801356001600160401b038111156150d257600080fd5b6150de8a828b01614a9d565b91505092959891949750929550565b600080600080600080600080610100898b03121561510a57600080fd5b88356001600160401b038082111561512157600080fd5b61512d8c838d01614a9d565b995060209150818b013561514081614be8565b985060408b0135975060608b0135965060808b0135955060a08b0135945060c08b013561516c81614be8565b935060e08b01358181111561518057600080fd5b8b019050601f81018c1361519357600080fd5b80356151a1614d2282614c91565b81815260059190911b8201830190838101908e8311156151c057600080fd5b928401925b828410156151de578335825292840192908401906151c5565b80955050505050509295985092959890939650565b600080600080600080600080610100898b03121561521057600080fd5b88356001600160401b0381111561522657600080fd5b6152328b828c01614a9d565b98505061524160208a01614f8c565b965061524f60408a01614fa3565b955061525d60608a01614fb7565b9450608089013561526d81614fc9565b935060a089013561527d81614fc9565b925060c089013561528d81614fc9565b915060e089013561529d81614be8565b809150509295985092959890939650565b600060208083850312156152c157600080fd5b82356001600160401b038111156152d757600080fd5b8301601f810185136152e857600080fd5b80356152f6614d2282614c91565b81815260059190911b8201830190838101908783111561531557600080fd5b928401925b828410156149275783358252928401929084019061531a565b80516001600160a01b031682526020808201516001600160401b0316908301526040908101511515910152565b6020808252825182820181905260009190848201906040850190845b818110156124325761538f838551615333565b928401926060929092019160010161537c565b60008060008060008060c087890312156153bb57600080fd5b86356153c681614fc9565b955060208701356153d681614fc9565b945060408701356153e681614fc9565b935060608701356153f681614fc9565b9250608087013561540681614fc9565b915060a087013561541681614fc9565b809150509295509295509295565b600080600080600080600080610100898b03121561544157600080fd5b883561544c81614be8565b97506020890135965060408901359550606089013594506080890135935060a089013561547881614be8565b925060c089013561548881614be8565b8092505060e089013590509295985092959890939650565b600080604083850312156154b357600080fd5b50508035926020909101359150565b600080600080606085870312156154d857600080fd5b84356001600160401b03808211156154ef57600080fd5b818701915087601f83011261550357600080fd5b81358181111561551257600080fd5b88602082850101111561552457600080fd5b60209283019650945061553a9187019050614f8c565b9150604085013561554a81614be8565b939692955090935050565b81516001600160801b0316815260208083015163ffffffff169082015260408083015161ffff16908201526060808301511515908201526080828101516101008301916155a59084018215159052565b5060a08301516155b960a084018215159052565b5060c08301516155cd60c084018215159052565b5060e083015161229560e08401826001600160a01b03169052565b6000806000606084860312156155fd57600080fd5b833561560881614be8565b95602085013595506040909401359392505050565b60006020828403121561562f57600080fd5b81356001600160401b038116811461133f57600080fd5b6000806040838503121561565957600080fd5b823561566481614be8565b91506020830135614f0c81614fc9565b6040815260006156876040830185614c29565b82810360208481019190915284518083528582019282019060005b818110156156be578451835293830193918301916001016156a2565b5090979650505050505050565b600080600080608085870312156156e157600080fd5b84356156ec81614be8565b935060208501356156fc81614be8565b92506040850135915060608501356001600160401b0381111561571e57600080fd5b61572a87828801614a9d565b91505092959194509250565b6000806040838503121561574957600080fd5b823561575481614be8565b915060208301356001600160401b03811115614e3b57600080fd5b60608101610ca08284615333565b6000806000806040858703121561579357600080fd5b84356001600160401b03808211156157aa57600080fd5b6157b688838901614d7c565b909650945060208701359150808211156157cf57600080fd5b506157dc87828801614d7c565b95989497509550505050565b600080604083850312156157fb57600080fd5b82356001600160401b038082111561581257600080fd5b61581e86838701614a9d565b9350602085013591508082111561583457600080fd5b50614e4785828601614a9d565b60008060006040848603121561585657600080fd5b83356001600160401b0381111561586c57600080fd5b61587886828701614d7c565b909450925050602084013561588c81614fc9565b809150509250925092565b600080604083850312156158aa57600080fd5b82356158b581614be8565b91506020830135614f0c81614be8565b600080604083850312156158d857600080fd5b82356001600160401b038111156158ee57600080fd5b6158fa85828601614a9d565b9250506020830135614f0c81614fc9565b6000825161591d818460208701614b50565b9190910192915050565b634e487b7160e01b600052601160045260246000fd5b6000821982111561595057615950615927565b500190565b6020808252600490820152636e6f706560e01b604082015260600190565b600081600019048311821515161561598d5761598d615927565b500290565b6001600160a01b03929092168252602082015260400190565b600181811c908216806159bf57607f821691505b6020821081036159df57634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052603260045260246000fd5b600060018201615a0d57615a0d615927565b5060010190565b602080825260029082015261617360f01b604082015260600190565b6020808252600290820152616e6160f01b604082015260600190565b6020808252600890820152677069636b206f6e6560c01b604082015260600190565b634e487b7160e01b600052601260045260246000fd5b600082615a9357615a93615a6e565b500490565b600060208284031215615aaa57600080fd5b5051919050565b8035613a3081614be8565b60008060008060008060008060008060006101608c8e031215615ade57600080fd5b6001600160401b038c35811015615af457600080fd5b615b018e8e358f01614a9d565b9b508060208e01351115615b1457600080fd5b615b248e60208f01358f01614a9d565b9a508060408e01351115615b3757600080fd5b50615b488d60408e01358e01614a9d565b9850615b5660608d01615ab1565b9750615b6460808d01614fd7565b9650615b7260a08d01614fd7565b9550615b8060c08d01614fd7565b9450615b8e60e08d01614fd7565b9350615b9d6101008d01614fd7565b9250615bac6101208d01614fd7565b9150615bbb6101408d01614fd7565b90509295989b509295989b9093969950565b60208082526010908201526f64697361626c6564206665617475726560801b604082015260600190565b6020808252600290820152611c1960f21b604082015260600190565b60008351615c25818460208801614b50565b637572692f60e01b9083019081528351615c46816004840160208801614b50565b01600401949350505050565b60008251615c64818460208701614b50565b6b636f6e74726163745f75726960a01b920191825250600c01919050565b600063ffffffff83811690831681811015615c9f57615c9f615927565b039392505050565b6020808252602e908201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160408201526d191e481a5b9a5d1a585b1a5e995960921b606082015260800190565b6001600160a01b0385811682528416602082015260408101839052608060608201819052600090615d2890830184614b7c565b9695505050505050565b600060208284031215615d4457600080fd5b815161133f81614a24565b600082821015615d6157615d61615927565b500390565b600082615d7557615d75615a6e565b500690565b6020808252602b908201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960408201526a6e697469616c697a696e6760a81b606082015260800190565b76020b1b1b2b9b9a1b7b73a3937b61d1030b1b1b7bab73a1604d1b815260008351615df7816017850160208801614b50565b7001034b99036b4b9b9b4b733903937b6329607d1b6017918401918201528351615e28816028840160208801614b50565b01602801949350505050565b634e487b7160e01b600052602160045260246000fd5b600060208284031215615e5c57600080fd5b815161133f81614fc9565b634e487b7160e01b600052603160045260246000fd5b600081615e8c57615e8c615927565b50600019019056fe9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6ddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3efa2646970667358221220ba7a5819153347ac16b12abec993315040aecbf1a3587d6c255beef969d616b864736f6c634300080e0033
Deployed Bytecode Sourcemap
126477:19609:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;145666:417;;;;;;;;;;-1:-1:-1;145666:417:0;;;;;:::i;:::-;;:::i;:::-;;;661:14:1;;654:22;636:41;;624:2;609:18;145666:417:0;;;;;;;;131914:1264;;;;;;:::i;:::-;;:::i;:::-;;94741:100;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;96333:245::-;;;;;;;;;;-1:-1:-1;96333:245:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;95904:363::-;;;;;;;;;;-1:-1:-1;95904:363:0;;;;;:::i;:::-;;:::i;127554:26::-;;;;;;;;;;-1:-1:-1;127554:26:0;;;;;:::i;:::-;;:::i;129890:96::-;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;139166:394::-;;;;;;;;;;-1:-1:-1;139166:394:0;;;;;:::i;:::-;;:::i;90751:303::-;;;;;;;;;;;;;:::i;:::-;;;6172:25:1;;;6160:2;6145:18;90751:303:0;6026:177:1;128563:197:0;;;;;;;;;;-1:-1:-1;128563:197:0;;;;;:::i;:::-;;:::i;136670:223::-;;;;;;;;;;-1:-1:-1;136670:223:0;;;;;:::i;:::-;;:::i;128768:277::-;;;;;;;;;;-1:-1:-1;128768:277:0;;;;;:::i;:::-;;:::i;129719:163::-;;;;;;;;;;-1:-1:-1;129719:163:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;97321:170::-;;;;;;;;;;-1:-1:-1;97321:170:0;;;;;:::i;:::-;;:::i;115711:131::-;;;;;;;;;;-1:-1:-1;115711:131:0;;;;;:::i;:::-;;:::i;82544:1382::-;;;;;;;;;;-1:-1:-1;82544:1382:0;;;;;:::i;:::-;;:::i;116104:147::-;;;;;;;;;;-1:-1:-1;116104:147:0;;;;;:::i;:::-;;:::i;139978:205::-;;;;;;;;;;-1:-1:-1;139978:205:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;117152:218::-;;;;;;;;;;-1:-1:-1;117152:218:0;;;;;:::i;:::-;;:::i;138625:533::-;;;;;;;;;;-1:-1:-1;138625:533:0;;;;;:::i;:::-;;:::i;127988:26::-;;;;;;;;;;-1:-1:-1;127988:26:0;;;;-1:-1:-1;;;;;127988:26:0;;;131417:123;;;;;;;;;;-1:-1:-1;131417:123:0;;;;;:::i;:::-;;:::i;97562:185::-;;;;;;;;;;-1:-1:-1;97562:185:0;;;;;:::i;:::-;;:::i;134548:1003::-;;;;;;:::i;:::-;;:::i;133186:1354::-;;;;;;:::i;:::-;;:::i;143959:777::-;;;;;;;;;;-1:-1:-1;143959:777:0;;;;;:::i;:::-;;:::i;137138:847::-;;;;;;;;;;-1:-1:-1;137138:847:0;;;;;:::i;:::-;;:::i;85156:523::-;;;;;;;;;;-1:-1:-1;85156:523:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;143286:665::-;;;;;;;;;;-1:-1:-1;143286:665:0;;;;;:::i;:::-;;:::i;94549:125::-;;;;;;;;;;-1:-1:-1;94549:125:0;;;;;:::i;:::-;;:::i;91965:206::-;;;;;;;;;;-1:-1:-1;91965:206:0;;;;;:::i;:::-;;:::i;127529:18::-;;;;;;;;;;-1:-1:-1;127529:18:0;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;127529:18:0;;;;;-1:-1:-1;;;127529:18:0;;;;;-1:-1:-1;;;127529:18:0;;;;-1:-1:-1;;;127529:18:0;;-1:-1:-1;;;;;127529:18:0;;;;;;;18747:14:1;;18740:22;18722:41;;18806:14;;18799:22;18794:2;18779:18;;18772:50;18865:14;;18858:22;18838:18;;;18831:50;;;;18924:14;;18917:22;18912:2;18897:18;;18890:50;18984:14;18977:22;18971:3;18956:19;;18949:51;19044:14;19037:22;19031:3;19016:19;;19009:51;19104:14;;19097:22;19091:3;19076:19;;19069:51;-1:-1:-1;;;;;19157:31:1;19151:3;19136:19;;19129:60;18709:3;18694:19;127529:18:0;18423:772:1;140795:392:0;;;;;;;;;;-1:-1:-1;140795:392:0;;;;;:::i;:::-;;:::i;135883:642::-;;;;;;;;;;-1:-1:-1;135883:642:0;;;;;:::i;:::-;;:::i;89082:978::-;;;;;;;;;;-1:-1:-1;89082:978:0;;;;;:::i;:::-;;:::i;121252:153::-;;;;;;;;;;-1:-1:-1;121252:153:0;;;;;:::i;:::-;;:::i;114149:147::-;;;;;;;;;;-1:-1:-1;114149:147:0;;;;;:::i;:::-;;:::i;127773:41::-;;;;;;;;;;-1:-1:-1;127773:41:0;;;;;:::i;:::-;;;;;;;;;;;;;;;;94910:104;;;;;;;;;;;;;:::i;141728:1550::-;;;;;;;;;;-1:-1:-1;141728:1550:0;;;;;:::i;:::-;;:::i;129374:337::-;;;;;;;;;;-1:-1:-1;129374:337:0;;;;;:::i;:::-;;:::i;130530:233::-;;;;;;;;;;-1:-1:-1;130530:233:0;;;;;:::i;:::-;;:::i;129994:186::-;;;;;;;;;;-1:-1:-1;129994:186:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;86069:2564::-;;;;;;;;;;-1:-1:-1;86069:2564:0;;;;;:::i;:::-;;:::i;129095:271::-;;;;;;;;;;-1:-1:-1;129095:271:0;;;;;:::i;:::-;;:::i;113243:49::-;;;;;;;;;;-1:-1:-1;113243:49:0;113288:4;113243:49;;96650:319;;;;;;;;;;-1:-1:-1;96650:319:0;;;;;:::i;:::-;;:::i;128023:329::-;;;;;;;;;;;;;:::i;:::-;;;;;;;;:::i;138316:301::-;;;;;;;;;;-1:-1:-1;138316:301:0;;;;;:::i;:::-;;:::i;97818:406::-;;;;;;;;;;-1:-1:-1;97818:406:0;;;;;:::i;:::-;;:::i;140191:596::-;;;;;;;;;;-1:-1:-1;140191:596:0;;;;;:::i;:::-;;:::i;84556:441::-;;;;;;;;;;-1:-1:-1;84556:441:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;131145:264::-;;;;;;;;;;-1:-1:-1;131145:264:0;;;;;:::i;:::-;;:::i;144933:329::-;;;;;;;;;;-1:-1:-1;144933:329:0;;;;;:::i;:::-;;:::i;130188:334::-;;;;;;;;;;-1:-1:-1;130188:334:0;;;;;:::i;:::-;;:::i;121579:142::-;;;;;;;;;;-1:-1:-1;121579:142:0;;;;;:::i;:::-;;:::i;90068:250::-;;;;;;;;;;-1:-1:-1;90068:250:0;;;;;:::i;:::-;;:::i;126816:62::-;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;126816:62:0;;116496:149;;;;;;;;;;-1:-1:-1;116496:149:0;;;;;:::i;:::-;;:::i;82324:39::-;;;;;;;;;;;;;;;;128360:195;;;;;;;;;;-1:-1:-1;128360:195:0;;;;;:::i;:::-;;:::i;141195:362::-;;;;;;;;;;-1:-1:-1;141195:362:0;;;;;:::i;:::-;;:::i;144744:181::-;;;;;;;;;;;;;:::i;97040:214::-;;;;;;;;;;-1:-1:-1;97040:214:0;;;;;:::i;:::-;-1:-1:-1;;;;;97211:25:0;;;97182:4;97211:25;;;:18;:25;;;;;;;;:35;;;;;;;;;;;;;;;97040:214;139568:402;;;;;;;;;;-1:-1:-1;139568:402:0;;;;;:::i;:::-;;:::i;126885:44::-;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;126885:44:0;;;;;137993:315;;;;;;;;;;-1:-1:-1;137993:315:0;;;;;:::i;:::-;;:::i;145666:417::-;145853:4;-1:-1:-1;;;;;;145895:51:0;;-1:-1:-1;;;145895:51:0;;:127;;-1:-1:-1;;;;;;;145963:59:0;;-1:-1:-1;;;145963:59:0;145895:127;:180;;;;146039:36;146063:11;146039:23;:36::i;:::-;145875:200;145666:417;-1:-1:-1;;145666:417:0:o;131914:1264::-;124421:1;125196:7;;:19;125188:63;;;;-1:-1:-1;;;125188:63:0;;28747:2:1;125188:63:0;;;28729:21:1;28786:2;28766:18;;;28759:30;28825:33;28805:18;;;28798:61;28876:18;;125188:63:0;;;;;;;;;124421:1;125329:7;:18;132064:27:::1;::::0;132040:11:::1;::::0;132064:27:::1;::::0;132081:9;;132064:27:::1;;;:::i;:::-;;::::0;;-1:-1:-1;;132064:27:0;;::::1;::::0;;;;;;132054:38;;132064:27:::1;132054:38:::0;;::::1;::::0;132103:23:::1;132129:14:::0;;;:9:::1;:14:::0;;;;;132054:38;;-1:-1:-1;132156:30:0::1;132129:14:::0;132179:6;132156:11:::1;:30::i;:::-;132503:22:::0;;-1:-1:-1;;;132503:22:0;::::1;;;132502:23;132494:46;;;::::0;-1:-1:-1;;;132494:46:0;;29388:2:1;132494:46:0::1;::::0;::::1;29370:21:1::0;29427:2;29407:18;;;29400:30;-1:-1:-1;;;29446:18:1;;;29439:40;29496:18;;132494:46:0::1;29186:334:1::0;132494:46:0::1;132558:18:::0;;-1:-1:-1;;;132558:18:0;::::1;;;132553:450;;132601:15;::::0;;;:10:::1;:15;::::0;;;;:36:::1;::::0;132626:10:::1;132601:24;:36::i;:::-;132593:45;;;::::0;::::1;;132743:23:::0;;::::1;132679:18:::0;;;:13:::1;:18;::::0;;;;;;;132698:10:::1;132679:30:::0;;;;;;;;-1:-1:-1;;;132743:23:0;;::::1;;;::::0;132679:39:::1;::::0;132712:6;;132679:39:::1;:::i;:::-;:87;;132653:161;;;::::0;-1:-1:-1;;;132653:161:0;;29992:2:1;132653:161:0::1;::::0;::::1;29974:21:1::0;30031:2;30011:18;;;30004:30;-1:-1:-1;;;30050:18:1;;;30043:42;30102:18;;132653:161:0::1;29790:336:1::0;132653:161:0::1;132829:18;::::0;;;:13:::1;:18;::::0;;;;;;;132848:10:::1;132829:30:::0;;;;;;;:40;;132863:6;;132829:18;:40:::1;::::0;132863:6;;132829:40:::1;:::i;:::-;::::0;;;-1:-1:-1;132553:450:0::1;::::0;-1:-1:-1;132553:450:0::1;;132920:23:::0;;-1:-1:-1;;;132920:23:0;::::1;;;132910:33:::0;::::1;;132902:50;;;;-1:-1:-1::0;;;132902:50:0::1;;;;;;;:::i;:::-;133056:22;::::0;::::1;::::0;133093:15;;133015:11:::1;::::0;:26:::1;::::0;-1:-1:-1;;;;;133056:22:0;;::::1;::::0;133093:24:::1;::::0;133111:6;;-1:-1:-1;;;;;133093:15:0::1;:24;:::i;:::-;133015:113;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;133141:29;133151:10;133163:6;133141:9;:29::i;:::-;-1:-1:-1::0;;124377:1:0;125508:7;:22;-1:-1:-1;;131914:1264:0:o;94741:100::-;94795:13;94828:5;94821:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;94741:100;:::o;96333:245::-;96437:7;96467:16;96475:7;96467;:16::i;:::-;96462:64;;96492:34;;-1:-1:-1;;;96492:34:0;;;;;;;;;;;96462:64;-1:-1:-1;96546:24:0;;;;:15;:24;;;;;;-1:-1:-1;;;;;96546:24:0;;96333:245::o;95904:363::-;95977:13;95993:16;96001:7;95993;:16::i;:::-;95977:32;;96030:5;-1:-1:-1;;;;;96024:11:0;:2;-1:-1:-1;;;;;96024:11:0;;96020:48;;96044:24;;-1:-1:-1;;;96044:24:0;;;;;;;;;;;96020:48;78076:10;-1:-1:-1;;;;;96085:21:0;;;;;;:63;;-1:-1:-1;96111:37:0;96128:5;78076:10;97040:214;:::i;96111:37::-;96110:38;96085:63;96081:138;;;96172:35;;-1:-1:-1;;;96172:35:0;;;;;;;;;;;96081:138;96231:28;96240:2;96244:7;96253:5;96231:8;:28::i;:::-;95966:301;95904:363;;:::o;127554:26::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;129890:96::-;129933:15;129968:10;129961:17;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;129890:96;:::o;139166:394::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;139387:11:::1;139428:9;139411:27;;;;;;;;:::i;:::-;;;;;;;;;;;;;139401:38;;;;;;139387:52;;139455:9;139450:103;139474:7;:14;139470:1;:18;139450:103;;;139510:31;139530:7;139538:1;139530:10;;;;;;;;:::i;:::-;;;;;;;139510;:15;139521:3;139510:15;;;;;;;;;;;:19;;:31;;;;:::i;:::-;-1:-1:-1::0;139490:3:0;::::1;::::0;::::1;:::i;:::-;;;;139450:103;;;;139300:260;139166:394:::0;;;:::o;90751:303::-;91005:12;;90989:13;;:28;-1:-1:-1;;90989:46:0;;90751:303::o;128563:197::-;128650:9;128645:108;128665:19;;;128645:108;;;128706:35;128723:4;128729:8;;128738:1;128729:11;;;;;;;:::i;:::-;;;;;;;;;;;;;;:::i;128706:35::-;128686:3;;;;:::i;:::-;;;;128645:108;;;;128563:197;;;:::o;136670:223::-;136776:4;136818:67;-1:-1:-1;;;;;;;;;;;136839:45:0;136853:19;136867:4;136853:13;:19::i;:::-;136874:9;136839:13;:45::i;136818:67::-;136798:87;136670:223;-1:-1:-1;;;136670:223:0:o;128768:277::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;128892:11:::1;::::0;-1:-1:-1;;;;;128892:11:0::1;:25:::0;128884:40:::1;;;;-1:-1:-1::0;;;128884:40:0::1;;;;;;;:::i;:::-;-1:-1:-1::0;129011:11:0::1;:26:::0;;-1:-1:-1;;;;;;129011:26:0::1;-1:-1:-1::0;;;;;129011:26:0;;;::::1;::::0;;;::::1;::::0;;128768:277::o;129719:163::-;129802:26;129853:21;129867:6;129853:13;:21::i;97321:170::-;97455:28;97465:4;97471:2;97475:7;97455:9;:28::i;115711:131::-;115785:7;115812:12;;;:6;:12;;;;;:22;;;;115711:131::o;82544:1382::-;82611:8;82623:1;82611:13;82607:49;;82633:23;;-1:-1:-1;;;82633:23:0;;;;;;;;;;;82607:49;90498:1;82671:13;;:32;82667:64;;82712:19;;-1:-1:-1;;;82712:19:0;;;;;;;;;;;82667:64;82778:24;;82742:33;82817:30;;;82813:106;;-1:-1:-1;90498:1:0;82813:106;82962:13;;82933:25;:42;82929:94;;82997:26;;-1:-1:-1;;;82997:26:0;;;;;;;;;;;82929:94;83325:13;;83188:36;;;-1:-1:-1;;83188:40:0;;;-1:-1:-1;83306:97:0;;;-1:-1:-1;83370:13:0;;-1:-1:-1;;83370:17:0;83306:97;83436:25;83419:433;83468:8;83463:1;:13;83419:433;;83559:1;83528:14;;;:11;:14;;;;;:19;-1:-1:-1;;;;;83528:19:0;:33;:59;;;;-1:-1:-1;83566:14:0;;;;:11;:14;;;;;:21;-1:-1:-1;;;83566:21:0;;;;83565:22;83528:59;83502:335;;;83630:31;83664:15;83677:1;83664:12;:15::i;:::-;83724:14;;;83702;;;:11;:14;;;;;;;;:36;;83793:24;;;;;-1:-1:-1;;;;;83761:56:0;-1:-1:-1;;;83761:56:0;-1:-1:-1;;;;;;83761:56:0;;;-1:-1:-1;;;;;83702:36:0;;;83761:56;;;;;;;-1:-1:-1;83502:335:0;83478:3;;83419:433;;;-1:-1:-1;83906:1:0;83895:12;83868:24;:39;-1:-1:-1;;82544:1382:0:o;116104:147::-;116187:18;116200:4;116187:12;:18::i;:::-;113734:16;113745:4;113734:10;:16::i;:::-;116218:25:::1;116229:4;116235:7;116218:10;:25::i;139978:205::-:0;140075:16;140116:59;:10;:50;140154:9;140137:27;;;;;;;;:::i;:::-;;;;;;;;;;;;;140127:38;;;;;;140116:50;;;;;;;;;;;:57;:59::i;117152:218::-;-1:-1:-1;;;;;117248:23:0;;78076:10;117248:23;117240:83;;;;-1:-1:-1;;;117240:83:0;;32112:2:1;117240:83:0;;;32094:21:1;32151:2;32131:18;;;32124:30;32190:34;32170:18;;;32163:62;-1:-1:-1;;;32241:18:1;;;32234:45;32296:19;;117240:83:0;31910:411:1;117240:83:0;117336:26;117348:4;117354:7;117336:11;:26::i;:::-;117152:218;;:::o;138625:533::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;138916:11:::1;138957:9;138940:27;;;;;;;;:::i;:::-;;::::0;;-1:-1:-1;;138940:27:0;;::::1;::::0;;;;;;138930:38;;138940:27:::1;138930:38:::0;;::::1;::::0;138979:14:::1;::::0;;;:9:::1;:14:::0;;;;;:29;;139115:35;::::1;;-1:-1:-1::0;;;139115:35:0::1;-1:-1:-1::0;;;;139059:45:0::1;::::0;;::::1;-1:-1:-1::0;;;139059:45:0::1;139115:35:::0;;;;-1:-1:-1;;;;139019:29:0::1;::::0;;::::1;-1:-1:-1::0;;;139019:29:0::1;-1:-1:-1::0;;;;;;139019:29:0;;;-1:-1:-1;;;;;138979:29:0;;::::1;139019::::0;;;;;;;::::1;139115:35:::0;;;;;;;;;;;::::1;::::0;;-1:-1:-1;;;138625:533:0:o;131417:123::-;131498:34;;-1:-1:-1;;;131498:34:0;;32528:2:1;131498:34:0;;;32510:21:1;32567:2;32547:18;;;32540:30;-1:-1:-1;;;32586:18:1;;;32579:54;32650:18;;131498:34:0;32326:348:1;97562:185:0;97700:39;97717:4;97723:2;97727:7;97700:39;;;;;;;;;;;;:16;:39::i;134548:1003::-;134794:12;134809:213;134828:6;134849;134870:7;134892:5;134912:12;134939:16;134978:4;134998:13;134809:4;:213::i;:::-;135041:6;:20;134794:228;;-1:-1:-1;;;;135041:20:0;;;;135033:35;;;;-1:-1:-1;;;135033:35:0;;;;;;;:::i;:::-;135087:6;:21;;;;;;135079:36;;;;-1:-1:-1;;;135079:36:0;;;;;;;:::i;:::-;135136:27;135147:4;135153:9;135136:10;:27::i;:::-;135128:36;;;;;;135177:16;135187:5;135177:9;:16::i;:::-;-1:-1:-1;;;;;135208:20:0;;;135204:90;;-1:-1:-1;;;;;135253:20:0;;135263:10;135253:20;135245:37;;;;-1:-1:-1;;;135245:37:0;;;;;;;:::i;:::-;135323:1;135314:6;:10;135306:31;;;;-1:-1:-1;;;135306:31:0;;;;;;;:::i;:::-;135381:12;;135373:29;;;;-1:-1:-1;;;135373:29:0;;;;;;;:::i;:::-;135440:11;:26;135467:16;135485:21;135500:6;135485:12;:21;:::i;:::-;135440:67;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;135518:25;135528:6;135536;135518:9;:25::i;:::-;134783:768;134548:1003;;;;;;;:::o;133186:1354::-;133466:11;133507:9;133490:27;;;;;;;;:::i;:::-;;;;-1:-1:-1;;133490:27:0;;;;;;;;;133480:38;;133490:27;133480:38;;;;133529:23;133555:14;;;:9;:14;;;;;133480:38;;-1:-1:-1;133582:30:0;133555:14;133605:6;133582:11;:30::i;:::-;133801:22;;-1:-1:-1;;;133801:22:0;;;;133793:42;;;;-1:-1:-1;;;133793:42:0;;33547:2:1;133793:42:0;;;33529:21:1;33586:1;33566:18;;;33559:29;-1:-1:-1;;;33604:18:1;;;33597:37;33651:18;;133793:42:0;33345:330:1;133793:42:0;133848:12;133863:213;133882:6;133903;133924:7;133946:5;133966:12;133993:16;134032:4;134052:13;133863:4;:213::i;:::-;134114:15;;;;:10;:15;;;;;;133848:228;;-1:-1:-1;134095:42:0;;133848:228;;134131:5;134095:12;:42::i;:::-;134087:66;;;;-1:-1:-1;;;134087:66:0;;33882:2:1;134087:66:0;;;33864:21:1;33921:2;33901:18;;;33894:30;-1:-1:-1;;;33940:18:1;;;33933:41;33991:18;;134087:66:0;33680:335:1;134087:66:0;134166:16;134176:5;134166:9;:16::i;:::-;-1:-1:-1;;;;;134197:20:0;;;134193:90;;-1:-1:-1;;;;;134242:20:0;;134252:10;134242:20;134234:37;;;;-1:-1:-1;;;134234:37:0;;;;;;;:::i;:::-;134312:1;134303:6;:10;134295:31;;;;-1:-1:-1;;;134295:31:0;;;;;;;:::i;:::-;134370:12;;134362:29;;;;-1:-1:-1;;;134362:29:0;;;;;;;:::i;:::-;134429:11;:26;134456:16;134474:21;134489:6;134474:12;:21;:::i;:::-;134429:67;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;134507:25;134517:6;134525;134507:9;:25::i;:::-;133455:1085;;;133186:1354;;;;;;;;:::o;143959:777::-;144035:11;;-1:-1:-1;;;;;144035:11:0;;144057:155;;144111:39;113288:4;144139:10;144111:7;:39::i;:::-;144103:62;;;;-1:-1:-1;;;144103:62:0;;34222:2:1;144103:62:0;;;34204:21:1;34261:2;34241:18;;;34234:30;-1:-1:-1;;;34280:18:1;;;34273:40;34330:18;;144103:62:0;34020:334:1;144103:62:0;-1:-1:-1;144190:10:0;144057:155;-1:-1:-1;;;;;144226:26:0;;144222:507;;144277:11;;144342:3;;-1:-1:-1;;;;;144277:11:0;;;;144269:100;;144349:5;;144318:27;;:21;:27;:::i;:::-;144317:37;;;;:::i;:::-;144269:100;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;144384:48:0;;-1:-1:-1;;;;;144384:25:0;;;144410:21;144384:48;;;;;;;;;144410:21;144384:25;:48;;;;;;;;;;;;;;;;;;;144222:507;144552:11;;144616:3;;144583:30;;-1:-1:-1;;;144583:30:0;;144487:12;;144515:128;;-1:-1:-1;;;;;144552:11:0;;;;144623:5;;144583:15;;;;;:30;;144607:4;;144583:30;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:36;;;;:::i;:::-;144582:46;;;;:::i;:::-;-1:-1:-1;;;;;144515:18:0;;;:128;:18;:128::i;:::-;144658:59;144677:7;144686:5;-1:-1:-1;;;;;144686:15:0;;144710:4;144686:30;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;137138:847::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;137508:11:::1;137549:9;137532:27;;;;;;;;:::i;:::-;;::::0;;;;::::1;-1:-1:-1::0;;137532:27:0;;;;;;137522:38;;137532:27:::1;137522:38:::0;;::::1;::::0;137582:14:::1;::::0;;;:9:::1;:14:::0;;;;;:20;137522:38;;-1:-1:-1;;;;137582:20:0;::::1;;;137581:21;137573:47;;;::::0;-1:-1:-1;;;137573:47:0;;35007:2:1;137573:47:0::1;::::0;::::1;34989:21:1::0;35046:2;35026:18;;;35019:30;-1:-1:-1;;;35065:18:1;;;35058:43;35118:18;;137573:47:0::1;34805:337:1::0;137573:47:0::1;137631:10;:26:::0;;::::1;::::0;::::1;::::0;;-1:-1:-1;137631:26:0;;;;;;::::1;::::0;;::::1;::::0;::::1;::::0;::::1;::::0;::::1;:::i;:::-;;137685:292;;;;;;;;137713:6;-1:-1:-1::0;;;;;137685:292:0::1;;;;;137741:6;137685:292;;;;;;137777:14;137685:292;;;;;;137816:9;137685:292;;;;;;137850:9;137685:292;;;;;;137888:9;137685:292;;;;;;137961:4;137685:292;;;;;;137926:13;-1:-1:-1::0;;;;;137685:292:0::1;;;::::0;137668:9:::1;:14;137678:3;137668:14;;;;;;;;;;;:309;;;;;;;;;;;;;-1:-1:-1::0;;;;;137668:309:0::1;;;;;-1:-1:-1::0;;;;;137668:309:0::1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1::0;;;;;137668:309:0::1;;;;;-1:-1:-1::0;;;;;137668:309:0::1;;;;;;;;;137421:564;137138:847:::0;;;;;;;;;:::o;85156:523::-;85354:15;;85263:23;;85329:22;85354:15;-1:-1:-1;;;;;85421:68:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;85384:105;;85509:9;85504:125;85525:14;85520:1;:19;85504:125;;85581:32;85601:8;85610:1;85601:11;;;;;;;;:::i;:::-;;;;;;;85581:19;:32::i;:::-;85565:10;85576:1;85565:13;;;;;;;;:::i;:::-;;;;;;;;;;:48;85541:3;;85504:125;;;-1:-1:-1;85650:10:0;85156:523;-1:-1:-1;;;85156:523:0:o;143286:665::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;143552:6:::1;:22:::0;::::1;::::0;::::1;;;143544:31;;;::::0;::::1;;-1:-1:-1::0;143662:6:0::1;:39:::0;;-1:-1:-1;;143712:41:0;143662:39;::::1;;-1:-1:-1::0;;143712:41:0;;;;;143662:39:::1;143712:41:::0;::::1;;::::0;;;::::1;::::0;;;::::1;-1:-1:-1::0;;143812:39:0;143764:37;;::::1;;::::0;;;::::1;-1:-1:-1::0;;143812:39:0;;;;;;;::::1;;::::0;;;::::1;;-1:-1:-1::0;;;;143906:37:0;-1:-1:-1;;;143862:33:0;::::1;;::::0;;;::::1;-1:-1:-1::0;;;;143906:37:0;;-1:-1:-1;;;143906:37:0;::::1;;::::0;;;::::1;;::::0;;143286:665::o;94549:125::-;94613:7;94640:21;94653:7;94640:12;:21::i;:::-;:26;;94549:125;-1:-1:-1;;94549:125:0:o;91965:206::-;92029:7;-1:-1:-1;;;;;92053:19:0;;92049:60;;92081:28;;-1:-1:-1;;;92081:28:0;;;;;;;;;;;92049:60;-1:-1:-1;;;;;;92135:19:0;;;;;:12;:19;;;;;:27;-1:-1:-1;;;;;92135:27:0;;91965:206::o;140795:392::-;140957:10;:17;140887:15;;140920:21;;-1:-1:-1;;;;;140944:31:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;140920:55;;140991:9;140986:171;141010:10;:17;141006:21;;140986:171;;;141053:32;141063:6;141071:10;141082:1;141071:13;;;;;;;;:::i;:::-;;;;;;;;141053:32;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:9;:32::i;:::-;141049:97;;;141117:10;141128:1;141117:13;;;;;;;;:::i;:::-;;;;;;;;141106:24;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:5;141112:1;141106:8;;;;;;;;:::i;:::-;;;;;;:24;;;;141049:97;141029:3;;;;:::i;:::-;;;;140986:171;;;-1:-1:-1;141174:5:0;140795:392;-1:-1:-1;;140795:392:0:o;135883:642::-;136214:288;;-1:-1:-1;;;;;;35494:2:1;35530:15;;;35526:24;;136214:288:0;;;35514:37:1;35567:12;;;35560:28;;;35604:12;;;35597:28;;;35641:12;;;35634:28;;;35678:13;;;35671:29;;;35735:15;;;35731:24;;35716:13;;;35709:47;35791:15;;;35787:24;35772:13;;;35765:47;35828:13;;;35821:29;;;136146:7:0;;35866:13:1;;136214:288:0;;;;;;;;;;;;136186:331;;;;;;136166:351;;135883:642;;;;;;;;;;:::o;89082:978::-;89168:16;89227:19;89261:25;89301:22;89326:16;89336:5;89326:9;:16::i;:::-;89301:41;;89357:25;89399:14;-1:-1:-1;;;;;89385:29:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;89385:29:0;;89357:57;;89429:31;;:::i;:::-;90498:1;89475:537;89559:14;89544:11;:29;89475:537;;89642:14;;;;:11;:14;;;;;;;;;89630:26;;;;;;;;;-1:-1:-1;;;;;89630:26:0;;;;-1:-1:-1;;;89630:26:0;;-1:-1:-1;;;;;89630:26:0;;;;;;;;-1:-1:-1;;;89630:26:0;;;;;;;;;;;;;;-1:-1:-1;89720:8:0;89675:73;89770:14;;-1:-1:-1;;;;;89770:28:0;;89766:111;;89843:14;;;-1:-1:-1;89766:111:0;89920:5;-1:-1:-1;;;;;89899:26:0;:17;-1:-1:-1;;;;;89899:26:0;;89895:102;;89976:1;89950:8;89959:13;;;;;;89950:23;;;;;;;;:::i;:::-;;;;;;:27;;;;;89895:102;89592:3;;89475:537;;;-1:-1:-1;90033:8:0;;89082:978;-1:-1:-1;;;;;;89082:978:0:o;121252:153::-;121342:7;121369:18;;;:12;:18;;;;;:28;;121391:5;121369:21;:28::i;114149:147::-;114235:4;114259:12;;;:6;:12;;;;;;;;-1:-1:-1;;;;;114259:29:0;;;;;;;;;;;;;;;114149:147::o;94910:104::-;94966:13;94999:7;94992:14;;;;;:::i;141728:1550::-;72518:19;72540:25;72563:1;72540:22;:25::i;:::-;72518:47;;72580:14;72576:67;;;72611:13;:20;;-1:-1:-1;;72611:20:0;;;;;72576:67;141886:12:::1;141872:11;;:26;;;;;-1:-1:-1::0;;;;;141872:26:0::1;;;;;-1:-1:-1::0;;;;;141872:26:0::1;;;;;;141915:4;-1:-1:-1::0;;;;;141909:10:0::1;:3;:10;;;;141947:18;141980:20:::0;142015:26:::1;142056:13:::0;142084:20:::1;142119:21:::0;142155:19:::1;142189:20:::0;142224:22:::1;142261:17:::0;142293:19:::1;142355:7;;142326:395;;;;;;;:::i;:::-;141932:789;;;;;;;;;;;;;;;;;;;;;;142734:24;142745:4;142751:6;142734:10;:24::i;:::-;142769:37;113288:4;142800:5:::0;142769:10:::1;:37::i;:::-;142817:30;-1:-1:-1::0;;;;;;;;;;;142841:5:0::1;142817:10;:30::i;:::-;142860:28:::0;;::::1;::::0;:13:::1;::::0;:28:::1;::::0;::::1;::::0;::::1;:::i;:::-;-1:-1:-1::0;142908:362:0::1;::::0;;::::1;::::0;;::::1;::::0;;;::::1;;::::0;;;;::::1;;;::::0;::::1;::::0;;;;::::1;;::::0;;;;;;;::::1;;::::0;;;;;;;::::1;;::::0;;;;;;;::::1;;::::0;;;;;;;::::1;;::::0;;;;;;-1:-1:-1;142908:362:0;;;;;;;;142899:6:::1;:371:::0;;-1:-1:-1;;142899:371:0;-1:-1:-1;;142899:371:0;;;;;;;;;;::::1;::::0;;;::::1;-1:-1:-1::0;;142899:371:0;;;;::::1;-1:-1:-1::0;;142899:371:0;;;;;;;;::::1;;-1:-1:-1::0;;;;142899:371:0;-1:-1:-1;;;142899:371:0;;::::1;-1:-1:-1::0;;;;142899:371:0;;;;;-1:-1:-1;;;142899:371:0;;::::1;;-1:-1:-1::0;;;;;;;;142899:371:0;-1:-1:-1;;;142899:371:0;;::::1;-1:-1:-1::0;;;;;;;;142899:371:0;;;;;;;-1:-1:-1;;72665:102:0;;;-1:-1:-1;72665:102:0;;-1:-1:-1;72665:102:0;72716:5;72700:21;;-1:-1:-1;;72700:21:0;;;72741:14;;-1:-1:-1;37483:36:1;;72741:14:0;;37471:2:1;37456:18;72741:14:0;;;;;;;72507:267;141728:1550;;;;:::o;129374:337::-;129460:28;129506:13;129522:24;129541:4;129522:18;:24::i;:::-;129506:40;;129585:5;-1:-1:-1;;;;;129571:20:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;129571:20:0;;129557:34;;129607:9;129602:102;129626:5;129622:1;:9;129602:102;;;129670:22;129684:4;129690:1;129670:13;:22::i;:::-;129653:11;129665:1;129653:14;;;;;;;;:::i;:::-;-1:-1:-1;;;;;129653:39:0;;;:14;;;;;;;;;;;:39;129633:3;;;;:::i;:::-;;;;129602:102;;;;129495:216;129374:337;;;:::o;130530:233::-;130617:6;:21;;;;;;130609:50;;;;-1:-1:-1;;;130609:50:0;;;;;;;:::i;:::-;130678:32;-1:-1:-1;;;;;;;;;;;130699:10:0;130678:7;:32::i;:::-;130670:47;;;;-1:-1:-1;;;130670:47:0;;;;;;;:::i;:::-;130728:27;130738:8;130748:6;130728:9;:27::i;129994:186::-;-1:-1:-1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;130123:9:0;:49;130160:9;130143:27;;;;;;;;:::i;:::-;;;;-1:-1:-1;;130143:27:0;;;;;;;;;130133:38;;130143:27;130133:38;;;;130123:49;;;;;;;;;;;;-1:-1:-1;130123:49:0;130116:56;;;;;;;;;-1:-1:-1;;;;;130116:56:0;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;-1:-1:-1;;;130116:56:0;;;;;;;;;;;;;;;-1:-1:-1;;;;;130116:56:0;;;;;;129994:186;-1:-1:-1;;129994:186:0:o;86069:2564::-;86195:16;86262:4;86253:5;:13;86249:45;;86275:19;;-1:-1:-1;;;86275:19:0;;;;;;;;;;;86249:45;86363:13;;86309:19;;90498:1;86454:5;:23;86450:87;;;90498:1;86498:23;;86450:87;86617:9;86610:4;:16;86606:73;;;86654:9;86647:16;;86606:73;86693:25;86721:16;86731:5;86721:9;:16::i;:::-;86693:44;;86915:4;86907:5;:12;86903:278;;;86962:12;;;86997:31;;;86993:111;;;87073:11;87053:31;;86993:111;86921:198;86903:278;;;-1:-1:-1;87164:1:0;86903:278;87195:25;87237:17;-1:-1:-1;;;;;87223:32:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;87223:32:0;;87195:60;;87274:17;87295:1;87274:22;87270:78;;87324:8;-1:-1:-1;87317:15:0;;-1:-1:-1;;;87317:15:0;87270:78;87492:31;87526:26;87546:5;87526:19;:26::i;:::-;87492:60;;87567:25;87812:9;:16;;;87807:92;;-1:-1:-1;87869:14:0;;87807:92;87948:5;87913:543;87977:4;87972:1;:9;;:45;;;;;88000:17;87985:11;:32;;87972:45;87913:543;;;88086:14;;;;:11;:14;;;;;;;;;88074:26;;;;;;;;;-1:-1:-1;;;;;88074:26:0;;;;-1:-1:-1;;;88074:26:0;;-1:-1:-1;;;;;88074:26:0;;;;;;;;-1:-1:-1;;;88074:26:0;;;;;;;;;;;;;;-1:-1:-1;88164:8:0;88119:73;88214:14;;-1:-1:-1;;;;;88214:28:0;;88210:111;;88287:14;;;-1:-1:-1;88210:111:0;88364:5;-1:-1:-1;;;;;88343:26:0;:17;-1:-1:-1;;;;;88343:26:0;;88339:102;;88420:1;88394:8;88403:13;;;;;;88394:23;;;;;;;;:::i;:::-;;;;;;:27;;;;;88339:102;88036:3;;87913:543;;;-1:-1:-1;;;88541:29:0;;;-1:-1:-1;88541:29:0;;86069:2564;-1:-1:-1;;;;;86069:2564:0:o;129095:271::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;129214:6:::1;:16:::0;-1:-1:-1;;;129214:16:0;::::1;-1:-1:-1::0;;;;;129214:16:0::1;:21:::0;129206:36:::1;;;;-1:-1:-1::0;;;129206:36:0::1;;;;;;;:::i;:::-;-1:-1:-1::0;129329:6:0::1;:29:::0;;-1:-1:-1;;;;;129329:29:0;;::::1;-1:-1:-1::0;;;129329:29:0::1;-1:-1:-1::0;;;;;;;;129329:29:0;;::::1;::::0;;;::::1;::::0;;129095:271::o;96650:319::-;78076:10;-1:-1:-1;;;;;96781:24:0;;;96777:54;;96814:17;;-1:-1:-1;;;96814:17:0;;;;;;;;;;;96777:54;78076:10;96844:32;;;;:18;:32;;;;;;;;-1:-1:-1;;;;;96844:42:0;;;;;;;;;;;;:53;;-1:-1:-1;;96844:53:0;;;;;;;;;;96913:48;;636:41:1;;;96844:42:0;;78076:10;96913:48;;609:18:1;96913:48:0;;;;;;;96650:319;;:::o;128023:329::-;128161:15;;;128174:1;128161:15;;;128091:21;128161:15;;;;;;128091:21;;128161:15;;;;;;;;;;;;;;;;;;-1:-1:-1;;128194:16:0;;;128208:1;128194:16;;;;;;;;128153:23;;-1:-1:-1;128194:16:0;128208:1;128194:16;;;;;;;;;;-1:-1:-1;128194:16:0;128187:23;;128223:19;;;;;;;;;;;;;-1:-1:-1;;;128223:19:0;;;:5;128229:1;128223:8;;;;;;;;:::i;:::-;;;;;;:19;;;;128253:18;;;;;;;;;;;;;-1:-1:-1;;;128253:18:0;;;:5;128259:1;128253:8;;;;;;;;:::i;:::-;;;;;;:18;;;;-1:-1:-1;;;;;;;;;;;128284:4:0;128289:1;128284:7;;;;;;;;:::i;:::-;;;;;;:21;;;;;113288:4;128326:18;;128316:4;128321:1;128316:7;;;;;;;;:::i;:::-;;;;;;:28;;;;;128023:329;;:::o;138316:301::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;138524:11:::1;138565:9;138548:27;;;;;;;;:::i;:::-;;::::0;;-1:-1:-1;;138548:27:0;;::::1;::::0;;;;;;138538:38;;138548:27:::1;138538:38:::0;;::::1;::::0;138587:15:::1;::::0;;;:10:::1;:15:::0;;;;;:22;;;;-1:-1:-1;;;138316:301:0:o;97818:406::-;97985:28;97995:4;98001:2;98005:7;97985:9;:28::i;:::-;98042:15;:2;-1:-1:-1;;;;;98042:13:0;;:15::i;:::-;:89;;;;;98075:56;98106:4;98112:2;98116:7;98125:5;98075:30;:56::i;:::-;98074:57;98042:89;98024:193;;;98165:40;;-1:-1:-1;;;98165:40:0;;;;;;;;;;;140191:596;140299:4;140321:14;140338:20;140348:9;140338;:20::i;:::-;140321:37;;140374:1;:10;;;140369:56;;140408:5;140401:12;;;;;140369:56;140439:1;:7;;;:12;;140450:1;140439:12;140435:57;;140475:5;140468:12;;;;;140435:57;140502:11;140543:9;140526:27;;;;;;;;:::i;:::-;;;;;;;;;;;;;140516:38;;;;;;140502:52;;140570:1;:10;;;140569:11;:48;;;;-1:-1:-1;140585:15:0;;;;:10;:15;;;;;:32;;140610:6;140585:24;:32::i;:::-;140584:33;140569:48;140565:93;;;140641:5;140634:12;;;;;;140565:93;140702:15;;;;;140672:18;;;;:13;:18;;;;;;;-1:-1:-1;;;;;140672:26:0;;;;;;;;;;;:45;;;;-1:-1:-1;140668:90:0;;140741:5;140734:12;;;;;;140668:90;-1:-1:-1;140775:4:0;;140191:596;-1:-1:-1;;;;140191:596:0:o;84556:441::-;84650:21;;:::i;:::-;84689:31;;:::i;:::-;90498:1;84735:7;:25;:53;;;;84775:13;;84764:7;:24;;84735:53;84731:102;;;84812:9;84556:441;-1:-1:-1;;84556:441:0:o;84731:102::-;-1:-1:-1;84855:20:0;;;;:11;:20;;;;;;;;;84843:32;;;;;;;;;-1:-1:-1;;;;;84843:32:0;;;;-1:-1:-1;;;84843:32:0;;-1:-1:-1;;;;;84843:32:0;;;;;;;;-1:-1:-1;;;84843:32:0;;;;;;;;;;;;;;;;84886:65;;84930:9;84556:441;-1:-1:-1;;84556:441:0:o;84886:65::-;84968:21;84981:7;84968:12;:21::i;131145:264::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;131340:6:::1;:21:::0;::::1;;131332:36;;;;-1:-1:-1::0;;;131332:36:0::1;;;;;;;:::i;:::-;131379:22:::0;;::::1;::::0;:13:::1;::::0;:22:::1;::::0;::::1;::::0;::::1;:::i;144933:329::-:0;145051:13;145090:16;145098:7;145090;:16::i;:::-;145082:46;;;;-1:-1:-1;;;145082:46:0;;38407:2:1;145082:46:0;;;38389:21:1;38446:2;38426:18;;;38419:30;-1:-1:-1;;;38465:18:1;;;38458:47;38522:18;;145082:46:0;38205:341:1;145082:46:0;145141:21;145165:10;:8;:10::i;:::-;145141:34;;145217:7;145234:18;:7;:16;:18::i;:::-;145200:53;;;;;;;;;:::i;:::-;;;;;;;;;;;;;145186:68;;;144933:329;;;:::o;130188:334::-;130301:6;:21;;;;;;130293:50;;;;-1:-1:-1;;;130293:50:0;;;;;;;:::i;:::-;130362:32;-1:-1:-1;;;;;;;;;;;130383:10:0;130362:7;:32::i;:::-;130354:47;;;;-1:-1:-1;;;130354:47:0;;;;;;;:::i;:::-;130417:9;130412:103;130432:18;;;130412:103;;;130472:31;130481:7;;130489:1;130481:10;;;;;;;:::i;:::-;;;;;;;;;;;;;;:::i;:::-;130493:6;;130500:1;130493:9;;;;;;;:::i;:::-;;;;;;;130472:8;:31::i;:::-;130452:3;;;;:::i;:::-;;;;130412:103;;121579:142;121659:7;121686:18;;;:12;:18;;;;;:27;;:25;:27::i;90068:250::-;90154:26;:24;:26::i;:::-;90191:25;:23;:25::i;:::-;90227:13;;;;:5;;:13;;;;;:::i;:::-;-1:-1:-1;90251:17:0;;;;:7;;:17;;;;;:::i;:::-;-1:-1:-1;90498:1:0;90279:13;:31;-1:-1:-1;;90068:250:0:o;116496:149::-;116580:18;116593:4;116580:12;:18::i;:::-;113734:16;113745:4;113734:10;:16::i;:::-;116611:26:::1;116623:4;116629:7;116611:11;:26::i;128360:195::-:0;128446:9;128441:107;128461:19;;;128441:107;;;128502:34;128518:4;128524:8;;128533:1;128524:11;;;;;;;:::i;:::-;;;;;;;;;;;;;;:::i;128502:34::-;128482:3;;;;:::i;:::-;;;;128441:107;;141195:362;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;141409:6:::1;:21:::0;;;::::1;;;141401:36;;;::::0;-1:-1:-1;;;141401:36:0;;39375:2:1;141401:36:0::1;::::0;::::1;39357:21:1::0;39414:1;39394:18;;;39387:29;-1:-1:-1;;;39432:18:1;;;39425:32;39474:18;;141401:36:0::1;39173:325:1::0;141401:36:0::1;141455:9;141450:100;141470:17:::0;;::::1;141450:100;;;141532:6;141509:9;:20;141519:6;;141526:1;141519:9;;;;;;;:::i;:::-;;;;;;;141509:20;;;;;;;;;;;;:29;;;;;;;;;;;;;;;;;;141489:3;;;;;:::i;:::-;;;;141450:100;;144744:181:::0;144790:13;144816:21;144840:10;:8;:10::i;:::-;144816:34;;144892:7;144875:41;;;;;;;;:::i;:::-;;;;;;;;;;;;;144861:56;;;144744:181;:::o;139568:402::-;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;139794:11:::1;139835:9;139818:27;;;;;;;;:::i;:::-;;;;;;;;;;;;;139808:38;;;;;;139794:52;;139862:9;139857:106;139881:7;:14;139877:1;:18;139857:106;;;139917:34;139940:7;139948:1;139940:10;;;;;;;;:::i;:::-;;;;;;;139917;:15;139928:3;139917:15;;;;;;;;;;;:22;;:34;;;;:::i;:::-;-1:-1:-1::0;139897:3:0;::::1;::::0;::::1;:::i;:::-;;;;139857:106;;137993:315:::0;113288:4;113734:16;113288:4;113734:10;:16::i;:::-;138202:11:::1;138243:9;138226:27;;;;;;;;:::i;:::-;;::::0;;-1:-1:-1;;138226:27:0;;::::1;::::0;;;;;;138216:38;;138226:27:::1;138216:38:::0;;::::1;::::0;138265:14:::1;::::0;;;:9:::1;:14:::0;;;;;:35;;;::::1;;-1:-1:-1::0;;;138265:35:0::1;-1:-1:-1::0;;;;138265:35:0;;::::1;::::0;;;::::1;::::0;;;-1:-1:-1;;;137993:315:0:o;120428:225::-;120513:4;-1:-1:-1;;;;;;120537:68:0;;-1:-1:-1;;;120537:68:0;;:108;;;120609:36;120633:11;120609:23;:36::i;131548:332::-;131638:18;;-1:-1:-1;;;131638:18:0;;;;131630:41;;;;-1:-1:-1;;;131630:41:0;;40161:2:1;131630:41:0;;;40143:21:1;40200:2;40180:18;;;40173:30;-1:-1:-1;;;40219:18:1;;;40212:40;40269:18;;131630:41:0;39959:334:1;131630:41:0;131690:15;;-1:-1:-1;;;131690:15:0;;;;-1:-1:-1;;131690:25:0;131682:50;;;;-1:-1:-1;;;131682:50:0;;40500:2:1;131682:50:0;;;40482:21:1;40539:2;40519:18;;;40512:30;-1:-1:-1;;;40558:18:1;;;40551:42;40610:18;;131682:50:0;40298:336:1;131682:50:0;131748:6;:20;;;;;;131743:86;;131793:9;131806:10;131793:23;131785:32;;;;;;131839:33;;131865:6;;131839:33;;:15;;:33;;131865:6;;-1:-1:-1;;;131839:33:0;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;131548:332;;:::o;44356:167::-;44436:4;44460:55;44470:3;-1:-1:-1;;;;;44490:23:0;;44460:9;:55::i;130771:236::-;130848:6;:16;-1:-1:-1;;;130848:16:0;;-1:-1:-1;;;;;130848:16:0;:21;130844:105;;130920:6;:16;-1:-1:-1;;;130920:16:0;;-1:-1:-1;;;;;130920:16:0;130910:6;130894:13;:11;:13::i;:::-;:22;;;;:::i;:::-;:42;;130886:51;;;;;;130959:27;130969:8;130979:6;130959:9;:27::i;98479:213::-;98536:4;98592:7;90498:1;98573:26;;:66;;;;;98626:13;;98616:7;:23;98573:66;:111;;;;-1:-1:-1;;98657:20:0;;;;:11;:20;;;;;:27;-1:-1:-1;;;98657:27:0;;;;98656:28;;98479:213::o;107934:196::-;108049:24;;;;:15;:24;;;;;;:29;;-1:-1:-1;;;;;;108049:29:0;-1:-1:-1;;;;;108049:29:0;;;;;;;;;108094:28;;108049:24;;108094:28;;;;;;;107934:196;;;:::o;114600:105::-;114667:30;114678:4;78076:10;114667;:30::i;:::-;114600:105;:::o;43784:152::-;43854:4;43878:50;43883:3;-1:-1:-1;;;;;43903:23:0;;43878:4;:50::i;136533:129::-;136593:7;136620:34;136649:4;33074:58;;-1:-1:-1;;;33074:58:0;;;44319:80:1;44415:12;;;44408:28;;;32941:7:0;;44452:12:1;;33074:58:0;;;;;;;;;;;;33064:69;;;;;;33057:76;;32872:269;;;;29070:231;29148:7;29169:17;29188:18;29210:27;29221:4;29227:9;29210:10;:27::i;:::-;29168:69;;;;29248:18;29260:5;29248:11;:18::i;102882:2130::-;102997:35;103035:21;103048:7;103035:12;:21::i;:::-;102997:59;;103095:4;-1:-1:-1;;;;;103073:26:0;:13;:18;;;-1:-1:-1;;;;;103073:26:0;;103069:67;;103108:28;;-1:-1:-1;;;103108:28:0;;;;;;;;;;;103069:67;103149:22;78076:10;-1:-1:-1;;;;;103175:20:0;;;;:73;;-1:-1:-1;103212:36:0;103229:4;78076:10;97040:214;:::i;103212:36::-;103175:126;;;-1:-1:-1;78076:10:0;103265:20;103277:7;103265:11;:20::i;:::-;-1:-1:-1;;;;;103265:36:0;;103175:126;103149:153;;103320:17;103315:66;;103346:35;;-1:-1:-1;;;103346:35:0;;;;;;;;;;;103315:66;-1:-1:-1;;;;;103396:16:0;;103392:52;;103421:23;;-1:-1:-1;;;103421:23:0;;;;;;;;;;;103392:52;103565:35;103582:1;103586:7;103595:4;103565:8;:35::i;:::-;-1:-1:-1;;;;;103896:18:0;;;;;;;:12;:18;;;;;;;;:31;;-1:-1:-1;;;;;;103896:31:0;;;-1:-1:-1;;;;;103896:31:0;;;-1:-1:-1;;103896:31:0;;;;;;;103942:16;;;;;;;;;:29;;;;;;;;-1:-1:-1;103942:29:0;;;;;;;;;;;104022:20;;;:11;:20;;;;;;104057:18;;-1:-1:-1;;;;;;104090:49:0;;;;-1:-1:-1;;;104123:15:0;104090:49;;;;;;;;;;104413:11;;104473:24;;;;;104516:13;;104022:20;;104473:24;;104516:13;104512:384;;104726:13;;104711:11;:28;104707:174;;104764:20;;104833:28;;;;-1:-1:-1;;;;;104807:54:0;-1:-1:-1;;;104807:54:0;-1:-1:-1;;;;;;104807:54:0;;;-1:-1:-1;;;;;104764:20:0;;104807:54;;;;104707:174;103871:1036;;;104943:7;104939:2;-1:-1:-1;;;;;104924:27:0;104933:4;-1:-1:-1;;;;;104924:27:0;-1:-1:-1;;;;;;;;;;;104924:27:0;;;;;;;;;104962:42;128563:197;93346:1141;93435:21;;:::i;:::-;93489:7;;90498:1;93538:23;;:47;;;;;93572:13;;93565:4;:20;93538:47;93534:886;;;93606:31;93640:17;;;:11;:17;;;;;;;;;93606:51;;;;;;;;;-1:-1:-1;;;;;93606:51:0;;;;-1:-1:-1;;;93606:51:0;;-1:-1:-1;;;;;93606:51:0;;;;;;;;-1:-1:-1;;;93606:51:0;;;;;;;;;;;;;;93676:729;;93726:14;;-1:-1:-1;;;;;93726:28:0;;93722:101;;93790:9;93346:1141;-1:-1:-1;;;93346:1141:0:o;93722:101::-;-1:-1:-1;;;94165:6:0;94210:17;;;;:11;:17;;;;;;;;;94198:29;;;;;;;;;-1:-1:-1;;;;;94198:29:0;;;;;-1:-1:-1;;;94198:29:0;;-1:-1:-1;;;;;94198:29:0;;;;;;;;-1:-1:-1;;;94198:29:0;;;;;;;;;;;;;94258:28;94254:109;;94326:9;93346:1141;-1:-1:-1;;;93346:1141:0:o;94254:109::-;94125:261;;;93587:833;93534:886;94448:31;;-1:-1:-1;;;94448:31:0;;;;;;;;;;;121814:169;121902:31;121919:4;121925:7;121902:16;:31::i;:::-;121944:18;;;;:12;:18;;;;;:31;;121967:7;121944:22;:31::i;45788:266::-;45851:16;45880:22;45905:19;45913:3;45905:7;:19::i;122077:174::-;122166:32;122184:4;122190:7;122166:17;:32::i;:::-;122209:18;;;;:12;:18;;;;;:34;;122235:7;122209:25;:34::i;141565:130::-;141628:16;;;;:9;:16;;;;;;;;141627:17;141619:34;;;;-1:-1:-1;;;141619:34:0;;;;;;41067:2:1;41049:21;;;41106:1;41086:18;;;41079:29;-1:-1:-1;;;41139:2:1;41124:18;;41117:34;41183:2;41168:18;;40865:327;141619:34:0;141664:16;;;;:9;:16;;;;;:23;;-1:-1:-1;;141664:23:0;141683:4;141664:23;;;141565:130::o;136901:212::-;137038:4;137062:43;137081:11;137094:4;137100;137062:18;:43::i;:::-;137055:50;136901:212;-1:-1:-1;;;;136901:212:0:o;18371:211::-;18488:86;18508:5;18538:23;;;18563:2;18567:5;18515:58;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;18515:58:0;;;;;;;;;;;;;;-1:-1:-1;;;;;18515:58:0;-1:-1:-1;;;;;;18515:58:0;;;;;;;;;;18488:19;:86::i;45080:158::-;45154:7;45205:22;45209:3;45221:5;45205:3;:22::i;74748:823::-;74812:4;75149:13;;;;;;;75145:419;;;75205:7;:12;;75216:1;75205:12;:61;;;;;75222:44;75260:4;75222:29;:44::i;:::-;75221:45;75205:61;75179:169;;;;-1:-1:-1;;;75179:169:0;;;;;;;:::i;:::-;-1:-1:-1;75370:5:0;;74748:823;-1:-1:-1;74748:823:0:o;75145:419::-;75416:12;;:22;;;;:12;;:22;75408:81;;;;-1:-1:-1;;;75408:81:0;;;;;;;:::i;:::-;-1:-1:-1;75504:12:0;:22;;-1:-1:-1;;75504:22:0;;;;;;;;;;;;-1:-1:-1;;74748:823:0:o;75145:419::-;74748:823;;;:::o;145320:216::-;145402:34;:32;:34::i;:::-;145447:28;145462:4;145468:6;145447:14;:28::i;:::-;145486:42;:40;:42::i;118029:112::-;118108:25;118119:4;118125:7;118108:10;:25::i;10404:326::-;-1:-1:-1;;;;;10699:19:0;;:23;;;10404:326::o;108622:772::-;108819:155;;-1:-1:-1;;;108819:155:0;;108785:4;;-1:-1:-1;;;;;108819:36:0;;;;;:155;;78076:10;;108905:4;;108928:7;;108954:5;;108819:155;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;-1:-1:-1;108819:155:0;;;;;;;;-1:-1:-1;;108819:155:0;;;;;;;;;;;;:::i;:::-;;;108802:585;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;109145:6;:13;109162:1;109145:18;109141:235;;109191:40;;-1:-1:-1;;;109191:40:0;;;;;;;;;;;109141:235;109334:6;109328:13;109319:6;109315:2;109311:15;109304:38;108802:585;-1:-1:-1;;;;;;109030:55:0;-1:-1:-1;;;109030:55:0;;-1:-1:-1;108622:772:0;;;;;;:::o;145544:114::-;145604:13;145637;145630:20;;;;;:::i;55619:723::-;55675:13;55896:5;55905:1;55896:10;55892:53;;-1:-1:-1;;55923:10:0;;;;;;;;;;;;-1:-1:-1;;;55923:10:0;;;;;55619:723::o;55892:53::-;55970:5;55955:12;56011:78;56018:9;;56011:78;;56044:8;;;;:::i;:::-;;-1:-1:-1;56067:10:0;;-1:-1:-1;56075:2:0;56067:10;;:::i;:::-;;;56011:78;;;56099:19;56131:6;-1:-1:-1;;;;;56121:17:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;56121:17:0;;56099:39;;56149:154;56156:10;;56149:154;;56183:11;56193:1;56183:11;;:::i;:::-;;-1:-1:-1;56252:10:0;56260:2;56252:5;:10;:::i;:::-;56239:24;;:2;:24;:::i;:::-;56226:39;;56209:6;56216;56209:14;;;;;;;;:::i;:::-;;;;:56;-1:-1:-1;;;;;56209:56:0;;;;;;;;-1:-1:-1;56280:11:0;56289:2;56280:11;;:::i;:::-;;;56149:154;;44609:117;44672:7;44699:19;44707:3;40093:18;;40010:109;77920:70;74145:13;;;;;;;74137:69;;;;-1:-1:-1;;;74137:69:0;;;;;;;:::i;:::-;77920:70::o;44112:158::-;44185:4;44209:53;44217:3;-1:-1:-1;;;;;44237:23:0;;44209:7;:53::i;113842:215::-;113927:4;-1:-1:-1;;;;;;113951:58:0;;-1:-1:-1;;;113951:58:0;;:98;;;114013:36;114037:11;114013:23;:36::i;39795:129::-;39868:4;39892:19;;;:12;;;;;:19;;;;;;:24;;;39795:129::o;98776:104::-;98845:27;98855:2;98859:8;98845:27;;;;;;;;;;;;:9;:27::i;114995:527::-;115084:22;115092:4;115098:7;115084;:22::i;:::-;115079:436;;115272:52;115311:7;-1:-1:-1;;;;;115272:52:0;115321:2;115272:30;:52::i;:::-;115397:49;115436:4;115443:2;115397:30;:49::i;:::-;115177:292;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;115177:292:0;;;;;;;;;;-1:-1:-1;;;115123:380:0;;;;;;;:::i;37699:414::-;37762:4;37784:21;37794:3;37799:5;37784:9;:21::i;:::-;37779:327;;-1:-1:-1;37822:23:0;;;;;;;;:11;:23;;;;;;;;;;;;;38005:18;;37983:19;;;:12;;;:19;;;;;;:40;;;;38038:11;;37779:327;-1:-1:-1;38089:5:0;38082:12;;26960:1308;27041:7;27050:12;27275:9;:16;27295:2;27275:22;27271:990;;27571:4;27556:20;;27550:27;27621:4;27606:20;;27600:27;27679:4;27664:20;;27658:27;27314:9;27650:36;27722:25;27733:4;27650:36;27550:27;27600;27722:10;:25::i;:::-;27715:32;;;;;;;;;27271:990;27769:9;:16;27789:2;27769:22;27765:496;;28044:4;28029:20;;28023:27;28095:4;28080:20;;28074:27;28137:23;28148:4;28023:27;28074;28137:10;:23::i;:::-;28130:30;;;;;;;;27765:496;-1:-1:-1;28209:1:0;;-1:-1:-1;28213:35:0;27765:496;26960:1308;;;;;:::o;25231:643::-;25309:20;25300:5;:29;;;;;;;;:::i;:::-;;25296:571;;25231:643;:::o;25296:571::-;25407:29;25398:5;:38;;;;;;;;:::i;:::-;;25394:473;;25453:34;;-1:-1:-1;;;25453:34:0;;44809:2:1;25453:34:0;;;44791:21:1;44848:2;44828:18;;;44821:30;-1:-1:-1;;;44867:18:1;;;44860:54;44931:18;;25453:34:0;44607:348:1;25394:473:0;25518:35;25509:5;:44;;;;;;;;:::i;:::-;;25505:362;;25570:41;;-1:-1:-1;;;25570:41:0;;45162:2:1;25570:41:0;;;45144:21:1;45201:2;45181:18;;;45174:30;45240:33;45220:18;;;45213:61;45291:18;;25570:41:0;44960:355:1;25505:362:0;25642:30;25633:5;:39;;;;;;;;:::i;:::-;;25629:238;;25689:44;;-1:-1:-1;;;25689:44:0;;45522:2:1;25689:44:0;;;45504:21:1;45561:2;45541:18;;;45534:30;45600:34;45580:18;;;45573:62;-1:-1:-1;;;45651:18:1;;;45644:32;45693:19;;25689:44:0;45320:398:1;25629:238:0;25764:30;25755:5;:39;;;;;;;;:::i;:::-;;25751:116;;25811:44;;-1:-1:-1;;;25811:44:0;;45925:2:1;25811:44:0;;;45907:21:1;45964:2;45944:18;;;45937:30;46003:34;45983:18;;;45976:62;-1:-1:-1;;;46054:18:1;;;46047:32;46096:19;;25811:44:0;45723:398:1;118653:238:0;118737:22;118745:4;118751:7;118737;:22::i;:::-;118732:152;;118776:12;;;;:6;:12;;;;;;;;-1:-1:-1;;;;;118776:29:0;;;;;;;;;:36;;-1:-1:-1;;118776:36:0;118808:4;118776:36;;;118859:12;78076:10;;77996:98;118859:12;-1:-1:-1;;;;;118832:40:0;118850:7;-1:-1:-1;;;;;118832:40:0;118844:4;118832:40;;;;;;;;;;118653:238;;:::o;41143:111::-;41199:16;41235:3;:11;;41228:18;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;41143:111;;;:::o;119023:239::-;119107:22;119115:4;119121:7;119107;:22::i;:::-;119103:152;;;119178:5;119146:12;;;:6;:12;;;;;;;;-1:-1:-1;;;;;119146:29:0;;;;;;;;;;:37;;-1:-1:-1;;119146:37:0;;;119203:40;78076:10;;119146:12;;119203:40;;119178:5;119203:40;119023:239;;:::o;6990:190::-;7115:4;7168;7139:25;7152:5;7159:4;7139:12;:25::i;:::-;:33;;6990:190;-1:-1:-1;;;;6990:190:0:o;20944:716::-;21368:23;21394:69;21422:4;21394:69;;;;;;;;;;;;;;;;;21402:5;-1:-1:-1;;;;;21394:27:0;;;:69;;;;;:::i;:::-;21478:17;;21368:95;;-1:-1:-1;21478:21:0;21474:179;;21575:10;21564:30;;;;;;;;;;;;:::i;:::-;21556:85;;;;-1:-1:-1;;;21556:85:0;;46578:2:1;21556:85:0;;;46560:21:1;46617:2;46597:18;;;46590:30;46656:34;46636:18;;;46629:62;-1:-1:-1;;;46707:18:1;;;46700:40;46757:19;;21556:85:0;46376:406:1;40473:120:0;40540:7;40567:3;:11;;40579:5;40567:18;;;;;;;;:::i;:::-;;;;;;;;;40560:25;;40473:120;;;;:::o;124584:111::-;74145:13;;;;;;;74137:69;;;;-1:-1:-1;;;74137:69:0;;;;;;;:::i;:::-;124377:1:::1;124665:7;:22:::0;124584:111::o;38289:1420::-;38355:4;38494:19;;;:12;;;:19;;;;;;38530:15;;38526:1176;;38905:21;38929:14;38942:1;38929:10;:14;:::i;:::-;38978:18;;38905:38;;-1:-1:-1;38958:17:0;;38978:22;;38999:1;;38978:22;:::i;:::-;38958:42;;39034:13;39021:9;:26;39017:405;;39068:17;39088:3;:11;;39100:9;39088:22;;;;;;;;:::i;:::-;;;;;;;;;39068:42;;39242:9;39213:3;:11;;39225:13;39213:26;;;;;;;;:::i;:::-;;;;;;;;;;;;:38;;;;39327:23;;;:12;;;:23;;;;;:36;;;39017:405;39503:17;;:3;;:17;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;39598:3;:12;;:19;39611:5;39598:19;;;;;;;;;;;39591:26;;;39641:4;39634:11;;;;;;;38526:1176;39685:5;39678:12;;;;;91502:399;91671:4;-1:-1:-1;;;;;;91713:51:0;;-1:-1:-1;;;91713:51:0;;:127;;-1:-1:-1;;;;;;;91781:59:0;;-1:-1:-1;;;91781:59:0;91713:127;:180;;;-1:-1:-1;;;;;;;;;;76756:51:0;;;91857:36;76647:168;99253:1942;99399:13;;-1:-1:-1;;;;;99427:16:0;;99423:48;;99452:19;;-1:-1:-1;;;99452:19:0;;;;;;;;;;;99423:48;99486:8;99498:1;99486:13;99482:44;;99508:18;;-1:-1:-1;;;99508:18:0;;;;;;;;;;;99482:44;-1:-1:-1;;;;;99877:16:0;;;;;;:12;:16;;;;;;;;:44;;-1:-1:-1;;;;;;99936:49:0;;-1:-1:-1;;;;;99877:44:0;;;;;;;99936:49;;;-1:-1:-1;;;;;;;;;99877:44:0;;;;;;99936:49;;;;;;;;;;;;;;;;100002:25;;;:11;:25;;;;;;:35;;-1:-1:-1;;;;;;100052:66:0;;;-1:-1:-1;;;100102:15:0;100052:66;;;;;;;;;;;;;100002:25;;100199:23;;;;100243:15;;:13;:15::i;:::-;100239:824;;;100279:505;100310:38;;100335:12;;-1:-1:-1;;;;;100310:38:0;;;100327:1;;-1:-1:-1;;;;;;;;;;;100310:38:0;100327:1;;100310:38;100402:212;100471:1;100504:2;100537:14;;;;;;100582:5;100402:30;:212::i;:::-;100371:365;;100672:40;;-1:-1:-1;;;100672:40:0;;;;;;;;;;;100371:365;100779:3;100763:12;:19;100279:505;;100865:12;100848:13;;:29;100844:43;;100879:8;;;100844:43;100239:824;;;100928:120;100959:40;;100984:14;;;;;-1:-1:-1;;;;;100959:40:0;;;100976:1;;-1:-1:-1;;;;;;;;;;;100959:40:0;100976:1;;100959:40;101043:3;101027:12;:19;100928:120;;100239:824;-1:-1:-1;101077:13:0;:28;101127:60;101156:1;101160:2;101164:12;101178:8;101127:60;:::i;56920:451::-;56995:13;57021:19;57053:10;57057:6;57053:1;:10;:::i;:::-;:14;;57066:1;57053:14;:::i;:::-;-1:-1:-1;;;;;57043:25:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;57043:25:0;;57021:47;;-1:-1:-1;;;57079:6:0;57086:1;57079:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;57079:15:0;;;;;;;;;-1:-1:-1;;;57105:6:0;57112:1;57105:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;57105:15:0;;;;;;;;-1:-1:-1;57136:9:0;57148:10;57152:6;57148:1;:10;:::i;:::-;:14;;57161:1;57148:14;:::i;:::-;57136:26;;57131:135;57168:1;57164;:5;57131:135;;;-1:-1:-1;;;57216:5:0;57224:3;57216:11;57203:25;;;;;;;:::i;:::-;;;;57191:6;57198:1;57191:9;;;;;;;;:::i;:::-;;;;:37;-1:-1:-1;;;;;57191:37:0;;;;;;;;-1:-1:-1;57253:1:0;57243:11;;;;;57171:3;;;:::i;:::-;;;57131:135;;;-1:-1:-1;57284:10:0;;57276:55;;;;-1:-1:-1;;;57276:55:0;;47262:2:1;57276:55:0;;;47244:21:1;;;47281:18;;;47274:30;47340:34;47320:18;;;47313:62;47392:18;;57276:55:0;47060:356:1;30522:1632:0;30653:7;;-1:-1:-1;;;;;31574:79:0;;31570:163;;;-1:-1:-1;31686:1:0;;-1:-1:-1;31690:30:0;31670:51;;31570:163;31747:1;:7;;31752:2;31747:7;;:18;;;;;31758:1;:7;;31763:2;31758:7;;31747:18;31743:102;;;-1:-1:-1;31798:1:0;;-1:-1:-1;31802:30:0;31782:51;;31743:102;31959:24;;;31942:14;31959:24;;;;;;;;;47648:25:1;;;47721:4;47709:17;;47689:18;;;47682:45;;;;47743:18;;;47736:34;;;47786:18;;;47779:34;;;31959:24:0;;47620:19:1;;31959:24:0;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;31959:24:0;;-1:-1:-1;;31959:24:0;;;-1:-1:-1;;;;;;;31998:20:0;;31994:103;;32051:1;32055:29;32035:50;;;;;;;31994:103;32117:6;-1:-1:-1;32125:20:0;;-1:-1:-1;30522:1632:0;;;;;;;;:::o;29564:344::-;29678:7;;-1:-1:-1;;;;;29724:80:0;;29678:7;29831:25;29847:3;29832:18;;;29854:2;29831:25;:::i;:::-;29815:42;;29875:25;29886:4;29892:1;29895;29898;29875:10;:25::i;:::-;29868:32;;;;;;29564:344;;;;;;:::o;7541:675::-;7624:7;7667:4;7624:7;7682:497;7706:5;:12;7702:1;:16;7682:497;;;7740:20;7763:5;7769:1;7763:8;;;;;;;;:::i;:::-;;;;;;;7740:31;;7806:12;7790;:28;7786:382;;8292:13;8342:15;;;8378:4;8371:15;;;8425:4;8409:21;;7918:57;;7786:382;;;8292:13;8342:15;;;8378:4;8371:15;;;8425:4;8409:21;;8095:57;;7786:382;-1:-1:-1;7720:3:0;;;;:::i;:::-;;;;7682:497;;13149:229;13286:12;13318:52;13340:6;13348:4;13354:1;13357:12;13286;14564:18;14575:6;14564:10;:18::i;:::-;14556:60;;;;-1:-1:-1;;;14556:60:0;;48433:2:1;14556:60:0;;;48415:21:1;48472:2;48452:18;;;48445:30;48511:31;48491:18;;;48484:59;48560:18;;14556:60:0;48231:353:1;14556:60:0;14630:12;14644:23;14671:6;-1:-1:-1;;;;;14671:11:0;14690:5;14697:4;14671:31;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;14629:73;;;;14720:51;14737:7;14746:10;14758:12;14720:16;:51::i;:::-;14713:58;14269:510;-1:-1:-1;;;;;;;14269:510:0:o;16955:712::-;17105:12;17134:7;17130:530;;;-1:-1:-1;17165:10:0;17158:17;;17130:530;17279:17;;:21;17275:374;;17477:10;17471:17;17538:15;17525:10;17521:2;17517:19;17510:44;17275:374;17620:12;17613:20;;-1:-1:-1;;;17613:20:0;;;;;;;;:::i;-1:-1:-1:-;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;:::-;;;;;;;;;;;;;;;14:131:1;-1:-1:-1;;;;;;88:32:1;;78:43;;68:71;;135:1;132;125:12;150:245;208:6;261:2;249:9;240:7;236:23;232:32;229:52;;;277:1;274;267:12;229:52;316:9;303:23;335:30;359:5;335:30;:::i;688:127::-;749:10;744:3;740:20;737:1;730:31;780:4;777:1;770:15;804:4;801:1;794:15;820:275;891:2;885:9;956:2;937:13;;-1:-1:-1;;933:27:1;921:40;;-1:-1:-1;;;;;976:34:1;;1012:22;;;973:62;970:88;;;1038:18;;:::i;:::-;1074:2;1067:22;820:275;;-1:-1:-1;820:275:1:o;1100:531::-;1143:5;1196:3;1189:4;1181:6;1177:17;1173:27;1163:55;;1214:1;1211;1204:12;1163:55;1237:20;;-1:-1:-1;;;;;1269:26:1;;1266:52;;;1298:18;;:::i;:::-;1342:55;1385:2;1366:13;;-1:-1:-1;;1362:27:1;1391:4;1358:38;1342:55;:::i;:::-;1422:2;1413:7;1406:19;1468:3;1461:4;1456:2;1448:6;1444:15;1440:26;1437:35;1434:55;;;1485:1;1482;1475:12;1434:55;1550:2;1543:4;1535:6;1531:17;1524:4;1515:7;1511:18;1498:55;1598:1;1573:16;;;1591:4;1569:27;1562:38;;;;1577:7;1100:531;-1:-1:-1;;;1100:531:1:o;1636:390::-;1714:6;1722;1775:2;1763:9;1754:7;1750:23;1746:32;1743:52;;;1791:1;1788;1781:12;1743:52;1818:23;;-1:-1:-1;;;;;1853:30:1;;1850:50;;;1896:1;1893;1886:12;1850:50;1919;1961:7;1952:6;1941:9;1937:22;1919:50;:::i;:::-;1909:60;2016:2;2001:18;;;;1988:32;;-1:-1:-1;;;;1636:390:1:o;2031:258::-;2103:1;2113:113;2127:6;2124:1;2121:13;2113:113;;;2203:11;;;2197:18;2184:11;;;2177:39;2149:2;2142:10;2113:113;;;2244:6;2241:1;2238:13;2235:48;;;-1:-1:-1;;2279:1:1;2261:16;;2254:27;2031:258::o;2294:::-;2336:3;2374:5;2368:12;2401:6;2396:3;2389:19;2417:63;2473:6;2466:4;2461:3;2457:14;2450:4;2443:5;2439:16;2417:63;:::i;:::-;2534:2;2513:15;-1:-1:-1;;2509:29:1;2500:39;;;;2541:4;2496:50;;2294:258;-1:-1:-1;;2294:258:1:o;2557:220::-;2706:2;2695:9;2688:21;2669:4;2726:45;2767:2;2756:9;2752:18;2744:6;2726:45;:::i;2782:180::-;2841:6;2894:2;2882:9;2873:7;2869:23;2865:32;2862:52;;;2910:1;2907;2900:12;2862:52;-1:-1:-1;2933:23:1;;2782:180;-1:-1:-1;2782:180:1:o;3076:203::-;-1:-1:-1;;;;;3240:32:1;;;;3222:51;;3210:2;3195:18;;3076:203::o;3284:131::-;-1:-1:-1;;;;;3359:31:1;;3349:42;;3339:70;;3405:1;3402;3395:12;3420:315;3488:6;3496;3549:2;3537:9;3528:7;3524:23;3520:32;3517:52;;;3565:1;3562;3555:12;3517:52;3604:9;3591:23;3623:31;3648:5;3623:31;:::i;:::-;3673:5;3725:2;3710:18;;;;3697:32;;-1:-1:-1;;;3420:315:1:o;3740:616::-;3792:3;3830:5;3824:12;3857:6;3852:3;3845:19;3883:4;3924:2;3919:3;3915:12;3949:11;3976;3969:18;;4026:6;4023:1;4019:14;4012:5;4008:26;3996:38;;4068:2;4061:5;4057:14;4089:1;4099:231;4113:6;4110:1;4107:13;4099:231;;;4184:5;4178:4;4174:16;4169:3;4162:29;4212:38;4245:4;4236:6;4230:13;4212:38;:::i;:::-;4308:12;;;;4204:46;-1:-1:-1;4273:15:1;;;;4135:1;4128:9;4099:231;;;-1:-1:-1;4346:4:1;;3740:616;-1:-1:-1;;;;;;;3740:616:1:o;4361:280::-;4560:2;4549:9;4542:21;4523:4;4580:55;4631:2;4620:9;4616:18;4608:6;4580:55;:::i;4646:183::-;4706:4;-1:-1:-1;;;;;4728:30:1;;4725:56;;;4761:18;;:::i;:::-;-1:-1:-1;4806:1:1;4802:14;4818:4;4798:25;;4646:183::o;4834:1187::-;4937:6;4945;4998:2;4986:9;4977:7;4973:23;4969:32;4966:52;;;5014:1;5011;5004:12;4966:52;5041:23;;-1:-1:-1;;;;;5113:14:1;;;5110:34;;;5140:1;5137;5130:12;5110:34;5163:50;5205:7;5196:6;5185:9;5181:22;5163:50;:::i;:::-;5153:60;;5232:2;5222:12;;5287:2;5276:9;5272:18;5259:32;5316:2;5306:8;5303:16;5300:36;;;5332:1;5329;5322:12;5300:36;5355:24;;;-1:-1:-1;5410:4:1;5402:13;;5398:27;-1:-1:-1;5388:55:1;;5439:1;5436;5429:12;5388:55;5475:2;5462:16;5498:60;5514:43;5554:2;5514:43;:::i;:::-;5498:60;:::i;:::-;5592:15;;;5674:1;5670:10;;;;5662:19;;5658:28;;;5623:12;;;;5698:19;;;5695:39;;;5730:1;5727;5720:12;5695:39;5754:11;;;;5774:217;5790:6;5785:3;5782:15;5774:217;;;5870:3;5857:17;5887:31;5912:5;5887:31;:::i;:::-;5931:18;;5807:12;;;;5969;;;;5774:217;;;6010:5;6000:15;;;;;;;4834:1187;;;;;:::o;6208:367::-;6271:8;6281:6;6335:3;6328:4;6320:6;6316:17;6312:27;6302:55;;6353:1;6350;6343:12;6302:55;-1:-1:-1;6376:20:1;;-1:-1:-1;;;;;6408:30:1;;6405:50;;;6451:1;6448;6441:12;6405:50;6488:4;6480:6;6476:17;6464:29;;6548:3;6541:4;6531:6;6528:1;6524:14;6516:6;6512:27;6508:38;6505:47;6502:67;;;6565:1;6562;6555:12;6580:505;6675:6;6683;6691;6744:2;6732:9;6723:7;6719:23;6715:32;6712:52;;;6760:1;6757;6750:12;6712:52;6783:23;;;-1:-1:-1;6857:2:1;6842:18;;6829:32;-1:-1:-1;;;;;6873:30:1;;6870:50;;;6916:1;6913;6906:12;6870:50;6955:70;7017:7;7008:6;6997:9;6993:22;6955:70;:::i;:::-;6580:505;;7044:8;;-1:-1:-1;6929:96:1;;-1:-1:-1;;;;6580:505:1:o;7090:389::-;7167:6;7175;7228:2;7216:9;7207:7;7203:23;7199:32;7196:52;;;7244:1;7241;7234:12;7196:52;7267:23;;;-1:-1:-1;7341:2:1;7326:18;;7313:32;-1:-1:-1;;;;;7357:30:1;;7354:50;;;7400:1;7397;7390:12;7354:50;7423;7465:7;7456:6;7445:9;7441:22;7423:50;:::i;:::-;7413:60;;;7090:389;;;;;:::o;7484:247::-;7543:6;7596:2;7584:9;7575:7;7571:23;7567:32;7564:52;;;7612:1;7609;7602:12;7564:52;7651:9;7638:23;7670:31;7695:5;7670:31;:::i;7736:632::-;7907:2;7959:21;;;8029:13;;7932:18;;;8051:22;;;7878:4;;7907:2;8130:15;;;;8104:2;8089:18;;;7878:4;8173:169;8187:6;8184:1;8181:13;8173:169;;;8248:13;;8236:26;;8317:15;;;;8282:12;;;;8209:1;8202:9;8173:169;;8373:456;8450:6;8458;8466;8519:2;8507:9;8498:7;8494:23;8490:32;8487:52;;;8535:1;8532;8525:12;8487:52;8574:9;8561:23;8593:31;8618:5;8593:31;:::i;:::-;8643:5;-1:-1:-1;8700:2:1;8685:18;;8672:32;8713:33;8672:32;8713:33;:::i;:::-;8373:456;;8765:7;;-1:-1:-1;;;8819:2:1;8804:18;;;;8791:32;;8373:456::o;9201:315::-;9269:6;9277;9330:2;9318:9;9309:7;9305:23;9301:32;9298:52;;;9346:1;9343;9336:12;9298:52;9382:9;9369:23;9359:33;;9442:2;9431:9;9427:18;9414:32;9455:31;9480:5;9455:31;:::i;:::-;9505:5;9495:15;;;9201:315;;;;;:::o;9521:322::-;9590:6;9643:2;9631:9;9622:7;9618:23;9614:32;9611:52;;;9659:1;9656;9649:12;9611:52;9686:23;;-1:-1:-1;;;;;9721:30:1;;9718:50;;;9764:1;9761;9754:12;9718:50;9787;9829:7;9820:6;9809:9;9805:22;9787:50;:::i;9848:658::-;10019:2;10071:21;;;10141:13;;10044:18;;;10163:22;;;9990:4;;10019:2;10242:15;;;;10216:2;10201:18;;;9990:4;10285:195;10299:6;10296:1;10293:13;10285:195;;;10364:13;;-1:-1:-1;;;;;10360:39:1;10348:52;;10455:15;;;;10420:12;;;;10396:1;10314:9;10285:195;;10511:173;10579:20;;-1:-1:-1;;;;;10628:31:1;;10618:42;;10608:70;;10674:1;10671;10664:12;10689:163;10756:20;;10816:10;10805:22;;10795:33;;10785:61;;10842:1;10839;10832:12;10857:159;10924:20;;10984:6;10973:18;;10963:29;;10953:57;;11006:1;11003;10996:12;11021:118;11107:5;11100:13;11093:21;11086:5;11083:32;11073:60;;11129:1;11126;11119:12;11144:128;11209:20;;11238:28;11209:20;11238:28;:::i;11277:671::-;11377:6;11385;11393;11401;11409;11462:3;11450:9;11441:7;11437:23;11433:33;11430:53;;;11479:1;11476;11469:12;11430:53;11506:23;;-1:-1:-1;;;;;11541:30:1;;11538:50;;;11584:1;11581;11574:12;11538:50;11607;11649:7;11640:6;11629:9;11625:22;11607:50;:::i;:::-;11597:60;;;11676:38;11710:2;11699:9;11695:18;11676:38;:::i;:::-;11666:48;;11733:37;11766:2;11755:9;11751:18;11733:37;:::i;:::-;11723:47;;11789:37;11822:2;11811:9;11807:18;11789:37;:::i;:::-;11779:47;;11876:3;11865:9;11861:19;11848:33;11890:28;11912:5;11890:28;:::i;:::-;11937:5;11927:15;;;11277:671;;;;;;;;:::o;11953:873::-;12075:6;12083;12091;12099;12107;12115;12123;12176:3;12164:9;12155:7;12151:23;12147:33;12144:53;;;12193:1;12190;12183:12;12144:53;12232:9;12219:23;12251:31;12276:5;12251:31;:::i;:::-;12301:5;-1:-1:-1;12353:2:1;12338:18;;12325:32;;-1:-1:-1;12404:2:1;12389:18;;12376:32;;-1:-1:-1;12455:2:1;12440:18;;12427:32;;-1:-1:-1;12506:3:1;12491:19;;12478:33;;-1:-1:-1;12563:3:1;12548:19;;12535:33;12577;12535;12577;:::i;:::-;12629:7;-1:-1:-1;12687:3:1;12672:19;;12659:33;-1:-1:-1;;;;;12704:30:1;;12701:50;;;12747:1;12744;12737:12;12701:50;12770;12812:7;12803:6;12792:9;12788:22;12770:50;:::i;:::-;12760:60;;;11953:873;;;;;;;;;;:::o;12831:1665::-;12988:6;12996;13004;13012;13020;13028;13036;13044;13097:3;13085:9;13076:7;13072:23;13068:33;13065:53;;;13114:1;13111;13104:12;13065:53;13141:23;;-1:-1:-1;;;;;13213:14:1;;;13210:34;;;13240:1;13237;13230:12;13210:34;13263:50;13305:7;13296:6;13285:9;13281:22;13263:50;:::i;:::-;13253:60;;13332:2;13322:12;;13384:2;13373:9;13369:18;13356:32;13397:31;13422:5;13397:31;:::i;:::-;13447:5;-1:-1:-1;13499:2:1;13484:18;;13471:32;;-1:-1:-1;13550:2:1;13535:18;;13522:32;;-1:-1:-1;13601:3:1;13586:19;;13573:33;;-1:-1:-1;13653:3:1;13638:19;;13625:33;;-1:-1:-1;13710:3:1;13695:19;;13682:33;13724;13682;13724;:::i;:::-;13776:7;-1:-1:-1;13836:3:1;13821:19;;13808:33;13853:16;;;13850:36;;;13882:1;13879;13872:12;13850:36;13905:24;;;-1:-1:-1;13960:4:1;13952:13;;13948:27;-1:-1:-1;13938:55:1;;13989:1;13986;13979:12;13938:55;14025:2;14012:16;14048:60;14064:43;14104:2;14064:43;:::i;14048:60::-;14142:15;;;14224:1;14220:10;;;;14212:19;;14208:28;;;14173:12;;;;14248:19;;;14245:39;;;14280:1;14277;14270:12;14245:39;14304:11;;;;14324:142;14340:6;14335:3;14332:15;14324:142;;;14406:17;;14394:30;;14357:12;;;;14444;;;;14324:142;;;14485:5;14475:15;;;;;;;12831:1665;;;;;;;;;;;:::o;14501:1085::-;14622:6;14630;14638;14646;14654;14662;14670;14678;14731:3;14719:9;14710:7;14706:23;14702:33;14699:53;;;14748:1;14745;14738:12;14699:53;14775:23;;-1:-1:-1;;;;;14810:30:1;;14807:50;;;14853:1;14850;14843:12;14807:50;14876;14918:7;14909:6;14898:9;14894:22;14876:50;:::i;:::-;14866:60;;;14945:38;14979:2;14968:9;14964:18;14945:38;:::i;:::-;14935:48;;15002:37;15035:2;15024:9;15020:18;15002:37;:::i;:::-;14992:47;;15058:37;15091:2;15080:9;15076:18;15058:37;:::i;:::-;15048:47;;15145:3;15134:9;15130:19;15117:33;15159:28;15181:5;15159:28;:::i;:::-;15206:5;-1:-1:-1;15263:3:1;15248:19;;15235:33;15277:30;15235:33;15277:30;:::i;:::-;15326:7;-1:-1:-1;15385:3:1;15370:19;;15357:33;15399:30;15357:33;15399:30;:::i;:::-;15448:7;-1:-1:-1;15507:3:1;15492:19;;15479:33;15521;15479;15521;:::i;:::-;15573:7;15563:17;;;14501:1085;;;;;;;;;;;:::o;15591:891::-;15675:6;15706:2;15749;15737:9;15728:7;15724:23;15720:32;15717:52;;;15765:1;15762;15755:12;15717:52;15792:23;;-1:-1:-1;;;;;15827:30:1;;15824:50;;;15870:1;15867;15860:12;15824:50;15893:22;;15946:4;15938:13;;15934:27;-1:-1:-1;15924:55:1;;15975:1;15972;15965:12;15924:55;16011:2;15998:16;16034:60;16050:43;16090:2;16050:43;:::i;16034:60::-;16128:15;;;16210:1;16206:10;;;;16198:19;;16194:28;;;16159:12;;;;16234:19;;;16231:39;;;16266:1;16263;16256:12;16231:39;16290:11;;;;16310:142;16326:6;16321:3;16318:15;16310:142;;;16392:17;;16380:30;;16343:12;;;;16430;;;;16310:142;;16487:278;16571:12;;-1:-1:-1;;;;;16567:38:1;16555:51;;16659:4;16648:16;;;16642:23;-1:-1:-1;;;;;16638:48:1;16622:14;;;16615:72;16675:2;16739:16;;;16733:23;16726:31;16719:39;16703:14;;16696:63;16487:278::o;16770:724::-;17005:2;17057:21;;;17127:13;;17030:18;;;17149:22;;;16976:4;;17005:2;17228:15;;;;17202:2;17187:18;;;16976:4;17271:197;17285:6;17282:1;17279:13;17271:197;;;17334:52;17382:3;17373:6;17367:13;17334:52;:::i;:::-;17443:15;;;;17415:4;17406:14;;;;;17307:1;17300:9;17271:197;;17499:919;17585:6;17593;17601;17609;17617;17625;17678:3;17666:9;17657:7;17653:23;17649:33;17646:53;;;17695:1;17692;17685:12;17646:53;17734:9;17721:23;17753:28;17775:5;17753:28;:::i;:::-;17800:5;-1:-1:-1;17857:2:1;17842:18;;17829:32;17870:30;17829:32;17870:30;:::i;:::-;17919:7;-1:-1:-1;17978:2:1;17963:18;;17950:32;17991:30;17950:32;17991:30;:::i;:::-;18040:7;-1:-1:-1;18099:2:1;18084:18;;18071:32;18112:30;18071:32;18112:30;:::i;:::-;18161:7;-1:-1:-1;18220:3:1;18205:19;;18192:33;18234:30;18192:33;18234:30;:::i;:::-;18283:7;-1:-1:-1;18342:3:1;18327:19;;18314:33;18356:30;18314:33;18356:30;:::i;:::-;18405:7;18395:17;;;17499:919;;;;;;;;:::o;19200:874::-;19322:6;19330;19338;19346;19354;19362;19370;19378;19431:3;19419:9;19410:7;19406:23;19402:33;19399:53;;;19448:1;19445;19438:12;19399:53;19487:9;19474:23;19506:31;19531:5;19506:31;:::i;:::-;19556:5;-1:-1:-1;19608:2:1;19593:18;;19580:32;;-1:-1:-1;19659:2:1;19644:18;;19631:32;;-1:-1:-1;19710:2:1;19695:18;;19682:32;;-1:-1:-1;19761:3:1;19746:19;;19733:33;;-1:-1:-1;19818:3:1;19803:19;;19790:33;19832;19790;19832;:::i;:::-;19884:7;-1:-1:-1;19943:3:1;19928:19;;19915:33;19957;19915;19957;:::i;:::-;20009:7;19999:17;;;20063:3;20052:9;20048:19;20035:33;20025:43;;19200:874;;;;;;;;;;;:::o;20079:248::-;20147:6;20155;20208:2;20196:9;20187:7;20183:23;20179:32;20176:52;;;20224:1;20221;20214:12;20176:52;-1:-1:-1;;20247:23:1;;;20317:2;20302:18;;;20289:32;;-1:-1:-1;20079:248:1:o;20332:806::-;20420:6;20428;20436;20444;20497:2;20485:9;20476:7;20472:23;20468:32;20465:52;;;20513:1;20510;20503:12;20465:52;20540:23;;-1:-1:-1;;;;;20612:14:1;;;20609:34;;;20639:1;20636;20629:12;20609:34;20677:6;20666:9;20662:22;20652:32;;20722:7;20715:4;20711:2;20707:13;20703:27;20693:55;;20744:1;20741;20734:12;20693:55;20784:2;20771:16;20810:2;20802:6;20799:14;20796:34;;;20826:1;20823;20816:12;20796:34;20873:7;20866:4;20857:6;20853:2;20849:15;20845:26;20842:39;20839:59;;;20894:1;20891;20884:12;20839:59;20925:4;20917:13;;;;-1:-1:-1;20949:6:1;-1:-1:-1;20974:40:1;;20993:20;;;-1:-1:-1;20974:40:1;:::i;:::-;20964:50;;21064:2;21053:9;21049:18;21036:32;21077:31;21102:5;21077:31;:::i;:::-;20332:806;;;;-1:-1:-1;20332:806:1;;-1:-1:-1;;20332:806:1:o;21143:959::-;21358:13;;-1:-1:-1;;;;;21354:39:1;21336:58;;21454:4;21442:17;;;21436:24;21462:10;21432:41;21410:20;;;21403:71;21534:4;21522:17;;;21516:24;21542:6;21512:37;21490:20;;;21483:67;21620:4;21608:17;;;21602:24;21595:32;21588:40;21566:20;;;21559:70;21381:3;21664:17;;;21658:24;21323:3;21308:19;;;21691:51;;21721:20;;21658:24;470:13;463:21;451:34;;400:91;21691:51;;21791:4;21783:6;21779:17;21773:24;21806:53;21853:4;21842:9;21838:20;21822:14;470:13;463:21;451:34;;400:91;21806:53;;21908:4;21900:6;21896:17;21890:24;21923:53;21970:4;21959:9;21955:20;21939:14;470:13;463:21;451:34;;400:91;21923:53;;22025:4;22017:6;22013:17;22007:24;22040:56;22090:4;22079:9;22075:20;22059:14;-1:-1:-1;;;;;3033:31:1;3021:44;;2967:104;22107:383;22184:6;22192;22200;22253:2;22241:9;22232:7;22228:23;22224:32;22221:52;;;22269:1;22266;22259:12;22221:52;22308:9;22295:23;22327:31;22352:5;22327:31;:::i;:::-;22377:5;22429:2;22414:18;;22401:32;;-1:-1:-1;22480:2:1;22465:18;;;22452:32;;22107:383;-1:-1:-1;;;22107:383:1:o;22495:284::-;22553:6;22606:2;22594:9;22585:7;22581:23;22577:32;22574:52;;;22622:1;22619;22612:12;22574:52;22648:23;;-1:-1:-1;;;;;22700:30:1;;22690:41;;22680:69;;22745:1;22742;22735:12;22784:382;22849:6;22857;22910:2;22898:9;22889:7;22885:23;22881:32;22878:52;;;22926:1;22923;22916:12;22878:52;22965:9;22952:23;22984:31;23009:5;22984:31;:::i;:::-;23034:5;-1:-1:-1;23091:2:1;23076:18;;23063:32;23104:30;23063:32;23104:30;:::i;23171:823::-;23448:2;23437:9;23430:21;23411:4;23474:55;23525:2;23514:9;23510:18;23502:6;23474:55;:::i;:::-;23586:22;;;23548:2;23566:18;;;23559:50;;;;23658:13;;23680:22;;;23756:15;;;;23718;;;23789:1;23799:169;23813:6;23810:1;23807:13;23799:169;;;23874:13;;23862:26;;23943:15;;;;23908:12;;;;23835:1;23828:9;23799:169;;;-1:-1:-1;23985:3:1;;23171:823;-1:-1:-1;;;;;;;23171:823:1:o;24394:666::-;24489:6;24497;24505;24513;24566:3;24554:9;24545:7;24541:23;24537:33;24534:53;;;24583:1;24580;24573:12;24534:53;24622:9;24609:23;24641:31;24666:5;24641:31;:::i;:::-;24691:5;-1:-1:-1;24748:2:1;24733:18;;24720:32;24761:33;24720:32;24761:33;:::i;:::-;24813:7;-1:-1:-1;24867:2:1;24852:18;;24839:32;;-1:-1:-1;24922:2:1;24907:18;;24894:32;-1:-1:-1;;;;;24938:30:1;;24935:50;;;24981:1;24978;24971:12;24935:50;25004;25046:7;25037:6;25026:9;25022:22;25004:50;:::i;:::-;24994:60;;;24394:666;;;;;;;:::o;25065:457::-;25143:6;25151;25204:2;25192:9;25183:7;25179:23;25175:32;25172:52;;;25220:1;25217;25210:12;25172:52;25259:9;25246:23;25278:31;25303:5;25278:31;:::i;:::-;25328:5;-1:-1:-1;25384:2:1;25369:18;;25356:32;-1:-1:-1;;;;;25400:30:1;;25397:50;;;25443:1;25440;25433:12;25527:267;25725:2;25710:18;;25737:51;25714:9;25770:6;25737:51;:::i;25799:773::-;25921:6;25929;25937;25945;25998:2;25986:9;25977:7;25973:23;25969:32;25966:52;;;26014:1;26011;26004:12;25966:52;26041:23;;-1:-1:-1;;;;;26113:14:1;;;26110:34;;;26140:1;26137;26130:12;26110:34;26179:70;26241:7;26232:6;26221:9;26217:22;26179:70;:::i;:::-;26268:8;;-1:-1:-1;26153:96:1;-1:-1:-1;26356:2:1;26341:18;;26328:32;;-1:-1:-1;26372:16:1;;;26369:36;;;26401:1;26398;26391:12;26369:36;;26440:72;26504:7;26493:8;26482:9;26478:24;26440:72;:::i;:::-;25799:773;;;;-1:-1:-1;26531:8:1;-1:-1:-1;;;;25799:773:1:o;26577:543::-;26665:6;26673;26726:2;26714:9;26705:7;26701:23;26697:32;26694:52;;;26742:1;26739;26732:12;26694:52;26769:23;;-1:-1:-1;;;;;26841:14:1;;;26838:34;;;26868:1;26865;26858:12;26838:34;26891:50;26933:7;26924:6;26913:9;26909:22;26891:50;:::i;:::-;26881:60;;26994:2;26983:9;26979:18;26966:32;26950:48;;27023:2;27013:8;27010:16;27007:36;;;27039:1;27036;27029:12;27007:36;;27062:52;27106:7;27095:8;27084:9;27080:24;27062:52;:::i;27125:566::-;27217:6;27225;27233;27286:2;27274:9;27265:7;27261:23;27257:32;27254:52;;;27302:1;27299;27292:12;27254:52;27329:23;;-1:-1:-1;;;;;27364:30:1;;27361:50;;;27407:1;27404;27397:12;27361:50;27446:70;27508:7;27499:6;27488:9;27484:22;27446:70;:::i;:::-;27535:8;;-1:-1:-1;27420:96:1;-1:-1:-1;;27620:2:1;27605:18;;27592:32;27633:28;27592:32;27633:28;:::i;:::-;27680:5;27670:15;;;27125:566;;;;;:::o;27696:388::-;27764:6;27772;27825:2;27813:9;27804:7;27800:23;27796:32;27793:52;;;27841:1;27838;27831:12;27793:52;27880:9;27867:23;27899:31;27924:5;27899:31;:::i;:::-;27949:5;-1:-1:-1;28006:2:1;27991:18;;27978:32;28019:33;27978:32;28019:33;:::i;28089:451::-;28164:6;28172;28225:2;28213:9;28204:7;28200:23;28196:32;28193:52;;;28241:1;28238;28231:12;28193:52;28268:23;;-1:-1:-1;;;;;28303:30:1;;28300:50;;;28346:1;28343;28336:12;28300:50;28369;28411:7;28402:6;28391:9;28387:22;28369:50;:::i;:::-;28359:60;;;28469:2;28458:9;28454:18;28441:32;28482:28;28504:5;28482:28;:::i;28905:276::-;29036:3;29074:6;29068:13;29090:53;29136:6;29131:3;29124:4;29116:6;29112:17;29090:53;:::i;:::-;29159:16;;;;;28905:276;-1:-1:-1;;28905:276:1:o;29525:127::-;29586:10;29581:3;29577:20;29574:1;29567:31;29617:4;29614:1;29607:15;29641:4;29638:1;29631:15;29657:128;29697:3;29728:1;29724:6;29721:1;29718:13;29715:39;;;29734:18;;:::i;:::-;-1:-1:-1;29770:9:1;;29657:128::o;30131:327::-;30333:2;30315:21;;;30372:1;30352:18;;;30345:29;-1:-1:-1;;;30405:2:1;30390:18;;30383:34;30449:2;30434:18;;30131:327::o;30463:168::-;30503:7;30569:1;30565;30561:6;30557:14;30554:1;30551:21;30546:1;30539:9;30532:17;30528:45;30525:71;;;30576:18;;:::i;:::-;-1:-1:-1;30616:9:1;;30463:168::o;30636:282::-;-1:-1:-1;;;;;30836:32:1;;;;30818:51;;30900:2;30885:18;;30878:34;30806:2;30791:18;;30636:282::o;30923:380::-;31002:1;30998:12;;;;31045;;;31066:61;;31120:4;31112:6;31108:17;31098:27;;31066:61;31173:2;31165:6;31162:14;31142:18;31139:38;31136:161;;31219:10;31214:3;31210:20;31207:1;31200:31;31254:4;31251:1;31244:15;31282:4;31279:1;31272:15;31136:161;;30923:380;;;:::o;31308:127::-;31369:10;31364:3;31360:20;31357:1;31350:31;31400:4;31397:1;31390:15;31424:4;31421:1;31414:15;31440:135;31479:3;31500:17;;;31497:43;;31520:18;;:::i;:::-;-1:-1:-1;31567:1:1;31556:13;;31440:135::o;31580:325::-;31782:2;31764:21;;;31821:1;31801:18;;;31794:29;-1:-1:-1;;;31854:2:1;31839:18;;31832:32;31896:2;31881:18;;31580:325::o;32679:::-;32881:2;32863:21;;;32920:1;32900:18;;;32893:29;-1:-1:-1;;;32953:2:1;32938:18;;32931:32;32995:2;32980:18;;32679:325::o;33009:331::-;33211:2;33193:21;;;33250:1;33230:18;;;33223:29;-1:-1:-1;;;33283:2:1;33268:18;;33261:38;33331:2;33316:18;;33009:331::o;34359:127::-;34420:10;34415:3;34411:20;34408:1;34401:31;34451:4;34448:1;34441:15;34475:4;34472:1;34465:15;34491:120;34531:1;34557;34547:35;;34562:18;;:::i;:::-;-1:-1:-1;34596:9:1;;34491:120::o;34616:184::-;34686:6;34739:2;34727:9;34718:7;34714:23;34710:32;34707:52;;;34755:1;34752;34745:12;34707:52;-1:-1:-1;34778:16:1;;34616:184;-1:-1:-1;34616:184:1:o;35890:142::-;35966:20;;35995:31;35966:20;35995:31;:::i;36037:1289::-;36203:6;36211;36219;36227;36235;36243;36251;36259;36267;36275;36283:7;36337:3;36325:9;36316:7;36312:23;36308:33;36305:53;;;36354:1;36351;36344:12;36305:53;-1:-1:-1;;;;;36410:23:1;;36407:31;-1:-1:-1;36404:51:1;;;36451:1;36448;36441:12;36404:51;36474:67;36533:7;36520:9;36507:23;36496:9;36492:39;36474:67;:::i;:::-;36464:77;;36590:2;36584;36573:9;36569:18;36556:32;36553:40;36550:60;;;36606:1;36603;36596:12;36550:60;36629:76;36697:7;36690:2;36679:9;36675:18;36662:32;36651:9;36647:48;36629:76;:::i;:::-;36619:86;;36754:2;36748;36737:9;36733:18;36720:32;36717:40;36714:60;;;36770:1;36767;36760:12;36714:60;;36793:76;36861:7;36854:2;36843:9;36839:18;36826:32;36815:9;36811:48;36793:76;:::i;:::-;36783:86;;36888:46;36930:2;36919:9;36915:18;36888:46;:::i;:::-;36878:56;;36953:36;36984:3;36973:9;36969:19;36953:36;:::i;:::-;36943:46;;37008:36;37039:3;37028:9;37024:19;37008:36;:::i;:::-;36998:46;;37063:36;37094:3;37083:9;37079:19;37063:36;:::i;:::-;37053:46;;37118:36;37149:3;37138:9;37134:19;37118:36;:::i;:::-;37108:46;;37173:36;37204:3;37193:9;37189:19;37173:36;:::i;:::-;37163:46;;37228:36;37259:3;37248:9;37244:19;37228:36;:::i;:::-;37218:46;;37284:36;37315:3;37304:9;37300:19;37284:36;:::i;:::-;37273:47;;36037:1289;;;;;;;;;;;;;;:::o;37530:340::-;37732:2;37714:21;;;37771:2;37751:18;;;37744:30;-1:-1:-1;;;37805:2:1;37790:18;;37783:46;37861:2;37846:18;;37530:340::o;37875:325::-;38077:2;38059:21;;;38116:1;38096:18;;;38089:29;-1:-1:-1;;;38149:2:1;38134:18;;38127:32;38191:2;38176:18;;37875:325::o;38551:617::-;38831:3;38869:6;38863:13;38885:53;38931:6;38926:3;38919:4;38911:6;38907:17;38885:53;:::i;:::-;-1:-1:-1;;;38960:16:1;;;38985:21;;;39031:13;;39053:65;39031:13;39105:1;39094:13;;39087:4;39075:17;;39053:65;:::i;:::-;39138:20;39160:1;39134:28;;38551:617;-1:-1:-1;;;;38551:617:1:o;39503:451::-;39735:3;39773:6;39767:13;39789:53;39835:6;39830:3;39823:4;39815:6;39811:17;39789:53;:::i;:::-;-1:-1:-1;;;39864:16:1;;39889:29;;;-1:-1:-1;39945:2:1;39934:14;;39503:451;-1:-1:-1;39503:451:1:o;40639:221::-;40678:4;40707:10;40767;;;;40737;;40789:12;;;40786:38;;;40804:18;;:::i;:::-;40841:13;;40639:221;-1:-1:-1;;;40639:221:1:o;41476:410::-;41678:2;41660:21;;;41717:2;41697:18;;;41690:30;41756:34;41751:2;41736:18;;41729:62;-1:-1:-1;;;41822:2:1;41807:18;;41800:44;41876:3;41861:19;;41476:410::o;41891:489::-;-1:-1:-1;;;;;42160:15:1;;;42142:34;;42212:15;;42207:2;42192:18;;42185:43;42259:2;42244:18;;42237:34;;;42307:3;42302:2;42287:18;;42280:31;;;42085:4;;42328:46;;42354:19;;42346:6;42328:46;:::i;:::-;42320:54;41891:489;-1:-1:-1;;;;;;41891:489:1:o;42385:249::-;42454:6;42507:2;42495:9;42486:7;42482:23;42478:32;42475:52;;;42523:1;42520;42513:12;42475:52;42555:9;42549:16;42574:30;42598:5;42574:30;:::i;42639:125::-;42679:4;42707:1;42704;42701:8;42698:34;;;42712:18;;:::i;:::-;-1:-1:-1;42749:9:1;;42639:125::o;42769:112::-;42801:1;42827;42817:35;;42832:18;;:::i;:::-;-1:-1:-1;42866:9:1;;42769:112::o;42886:407::-;43088:2;43070:21;;;43127:2;43107:18;;;43100:30;43166:34;43161:2;43146:18;;43139:62;-1:-1:-1;;;43232:2:1;43217:18;;43210:41;43283:3;43268:19;;42886:407::o;43298:786::-;-1:-1:-1;;;43704:3:1;43697:38;43679:3;43764:6;43758:13;43780:62;43835:6;43830:2;43825:3;43821:12;43814:4;43806:6;43802:17;43780:62;:::i;:::-;-1:-1:-1;;;43901:2:1;43861:16;;;43893:11;;;43886:40;43951:13;;43973:63;43951:13;44022:2;44014:11;;44007:4;43995:17;;43973:63;:::i;:::-;44056:17;44075:2;44052:26;;43298:786;-1:-1:-1;;;;43298:786:1:o;44475:127::-;44536:10;44531:3;44527:20;44524:1;44517:31;44567:4;44564:1;44557:15;44591:4;44588:1;44581:15;46126:245;46193:6;46246:2;46234:9;46225:7;46221:23;46217:32;46214:52;;;46262:1;46259;46252:12;46214:52;46294:9;46288:16;46313:28;46335:5;46313:28;:::i;46787:127::-;46848:10;46843:3;46839:20;46836:1;46829:31;46879:4;46876:1;46869:15;46903:4;46900:1;46893:15;46919:136;46958:3;46986:5;46976:39;;46995:18;;:::i;:::-;-1:-1:-1;;;47031:18:1;;46919:136::o
Swarm Source
ipfs://ba7a5819153347ac16b12abec993315040aecbf1a3587d6c255beef969d616b8
Loading...
Loading
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.