ETH Price: $3,247.64 (+2.29%)
Gas: 3 Gwei

Token

Finn Cotton (FC)
 

Overview

Max Total Supply

603 FC

Holders

161

Total Transfers

-

Market

Volume (24H)

N/A

Min Price (24H)

N/A

Max Price (24H)

N/A

Other Info

Loading...
Loading
Loading...
Loading
Loading...
Loading

Click here to update the token information / general information
# Exchange Pair Price  24H Volume % Volume

Contract Source Code Verified (Exact Match)

Contract Name:
FinnCotton

Compiler Version
v0.8.16+commit.07a7930e

Optimization Enabled:
Yes with 200 runs

Other Settings:
default evmVersion, MIT license

Contract Source Code (Solidity)

/**
 *Submitted for verification at Etherscan.io on 2022-10-06
*/

// File: @openzeppelin/contracts/access/IAccessControl.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 IAccessControl {
    /**
     * @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/security/ReentrancyGuard.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 ReentrancyGuard {
    // 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;

    constructor() {
        _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;
    }
}

// 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/Context.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 Context {
    function _msgSender() internal view virtual returns (address) {
        return msg.sender;
    }

    function _msgData() internal view virtual returns (bytes calldata) {
        return msg.data;
    }
}

// File: @openzeppelin/contracts/access/Ownable.sol


// OpenZeppelin Contracts v4.4.1 (access/Ownable.sol)

pragma solidity ^0.8.0;


/**
 * @dev Contract module which provides a basic access control mechanism, where
 * there is an account (an owner) that can be granted exclusive access to
 * specific functions.
 *
 * By default, the owner account will be the one that deploys the contract. This
 * can later be changed with {transferOwnership}.
 *
 * This module is used through inheritance. It will make available the modifier
 * `onlyOwner`, which can be applied to your functions to restrict their use to
 * the owner.
 */
abstract contract Ownable is Context {
    address private _owner;

    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);

    /**
     * @dev Initializes the contract setting the deployer as the initial owner.
     */
    constructor() {
        _transferOwnership(_msgSender());
    }

    /**
     * @dev Returns the address of the current owner.
     */
    function owner() public view virtual returns (address) {
        return _owner;
    }

    /**
     * @dev Throws if called by any account other than the owner.
     */
    modifier onlyOwner() {
        require(owner() == _msgSender(), "Ownable: caller is not the owner");
        _;
    }

    /**
     * @dev Leaves the contract without owner. It will not be possible to call
     * `onlyOwner` functions anymore. Can only be called by the current owner.
     *
     * NOTE: Renouncing ownership will leave the contract without an owner,
     * thereby removing any functionality that is only available to the owner.
     */
    function renounceOwnership() public virtual onlyOwner {
        _transferOwnership(address(0));
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`).
     * Can only be called by the current owner.
     */
    function transferOwnership(address newOwner) public virtual onlyOwner {
        require(newOwner != address(0), "Ownable: new owner is the zero address");
        _transferOwnership(newOwner);
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`).
     * Internal function without access restriction.
     */
    function _transferOwnership(address newOwner) internal virtual {
        address oldOwner = _owner;
        _owner = newOwner;
        emit OwnershipTransferred(oldOwner, newOwner);
    }
}

// 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/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: @openzeppelin/contracts/utils/introspection/IERC165.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 IERC165 {
    /**
     * @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/utils/introspection/ERC165.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 ERC165 is IERC165 {
    /**
     * @dev See {IERC165-supportsInterface}.
     */
    function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
        return interfaceId == type(IERC165).interfaceId;
    }
}

// File: @openzeppelin/contracts/access/AccessControl.sol


// OpenZeppelin Contracts (last updated v4.7.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 AccessControl is Context, IAccessControl, ERC165 {
    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(IAccessControl).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 ",
                        Strings.toHexString(uint160(account), 20),
                        " is missing role ",
                        Strings.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.
     *
     * May emit a {RoleGranted} event.
     */
    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.
     *
     * May emit a {RoleRevoked} event.
     */
    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`.
     *
     * May emit a {RoleRevoked} event.
     */
    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.
     *
     * May emit a {RoleGranted} event.
     *
     * [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.
     *
     * May emit a {RoleGranted} event.
     */
    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.
     *
     * May emit a {RoleRevoked} event.
     */
    function _revokeRole(bytes32 role, address account) internal virtual {
        if (hasRole(role, account)) {
            _roles[role].members[account] = false;
            emit RoleRevoked(role, account, _msgSender());
        }
    }
}

// File: @openzeppelin/contracts/token/ERC721/IERC721.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 IERC721 is IERC165 {
    /**
     * @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/token/ERC721/extensions/IERC721Enumerable.sol


// OpenZeppelin Contracts (last updated v4.5.0) (token/ERC721/extensions/IERC721Enumerable.sol)

pragma solidity ^0.8.0;


/**
 * @title ERC-721 Non-Fungible Token Standard, optional enumeration extension
 * @dev See https://eips.ethereum.org/EIPS/eip-721
 */
interface IERC721Enumerable is IERC721 {
    /**
     * @dev Returns the total amount of tokens stored by the contract.
     */
    function totalSupply() external view returns (uint256);

    /**
     * @dev Returns a token ID owned by `owner` at a given `index` of its token list.
     * Use along with {balanceOf} to enumerate all of ``owner``'s tokens.
     */
    function tokenOfOwnerByIndex(address owner, uint256 index) external view returns (uint256);

    /**
     * @dev Returns a token ID at a given `index` of all the tokens stored by the contract.
     * Use along with {totalSupply} to enumerate all tokens.
     */
    function tokenByIndex(uint256 index) external view returns (uint256);
}

// File: @openzeppelin/contracts/token/ERC721/extensions/IERC721Metadata.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 IERC721Metadata is IERC721 {
    /**
     * @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/token/ERC721/ERC721.sol


// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC721/ERC721.sol)

pragma solidity ^0.8.0;








/**
 * @dev Implementation of https://eips.ethereum.org/EIPS/eip-721[ERC721] Non-Fungible Token Standard, including
 * the Metadata extension, but not including the Enumerable extension, which is available separately as
 * {ERC721Enumerable}.
 */
contract ERC721 is Context, ERC165, IERC721, IERC721Metadata {
    using Address for address;
    using Strings for uint256;

    // Token name
    string private _name;

    // Token symbol
    string private _symbol;

    // Mapping from token ID to owner address
    mapping(uint256 => address) private _owners;

    // Mapping owner address to token count
    mapping(address => uint256) private _balances;

    // 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;

    /**
     * @dev Initializes the contract by setting a `name` and a `symbol` to the token collection.
     */
    constructor(string memory name_, string memory symbol_) {
        _name = name_;
        _symbol = symbol_;
    }

    /**
     * @dev See {IERC165-supportsInterface}.
     */
    function supportsInterface(bytes4 interfaceId) public view virtual override(ERC165, IERC165) returns (bool) {
        return
            interfaceId == type(IERC721).interfaceId ||
            interfaceId == type(IERC721Metadata).interfaceId ||
            super.supportsInterface(interfaceId);
    }

    /**
     * @dev See {IERC721-balanceOf}.
     */
    function balanceOf(address owner) public view virtual override returns (uint256) {
        require(owner != address(0), "ERC721: balance query for the zero address");
        return _balances[owner];
    }

    /**
     * @dev See {IERC721-ownerOf}.
     */
    function ownerOf(uint256 tokenId) public view virtual override returns (address) {
        address owner = _owners[tokenId];
        require(owner != address(0), "ERC721: owner query for nonexistent token");
        return owner;
    }

    /**
     * @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) {
        require(_exists(tokenId), "ERC721Metadata: URI query for nonexistent token");

        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 overridden in child contracts.
     */
    function _baseURI() internal view virtual returns (string memory) {
        return "";
    }

    /**
     * @dev See {IERC721-approve}.
     */
    function approve(address to, uint256 tokenId) public virtual override {
        address owner = ERC721.ownerOf(tokenId);
        require(to != owner, "ERC721: approval to current owner");

        require(
            _msgSender() == owner || isApprovedForAll(owner, _msgSender()),
            "ERC721: approve caller is not owner nor approved for all"
        );

        _approve(to, tokenId);
    }

    /**
     * @dev See {IERC721-getApproved}.
     */
    function getApproved(uint256 tokenId) public view virtual override returns (address) {
        require(_exists(tokenId), "ERC721: approved query for nonexistent token");

        return _tokenApprovals[tokenId];
    }

    /**
     * @dev See {IERC721-setApprovalForAll}.
     */
    function setApprovalForAll(address operator, bool approved) public virtual override {
        _setApprovalForAll(_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 {
        //solhint-disable-next-line max-line-length
        require(_isApprovedOrOwner(_msgSender(), tokenId), "ERC721: transfer caller is not owner nor approved");

        _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 {
        require(_isApprovedOrOwner(_msgSender(), tokenId), "ERC721: transfer caller is not owner nor approved");
        _safeTransfer(from, to, tokenId, _data);
    }

    /**
     * @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.
     *
     * `_data` is additional data, it has no specified format and it is sent in call to `to`.
     *
     * This internal function is equivalent to {safeTransferFrom}, and can be used to e.g.
     * implement alternative mechanisms to perform token transfer, such as signature-based.
     *
     * Requirements:
     *
     * - `from` cannot be the zero address.
     * - `to` cannot be the zero address.
     * - `tokenId` token must exist and be owned by `from`.
     * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer.
     *
     * Emits a {Transfer} event.
     */
    function _safeTransfer(
        address from,
        address to,
        uint256 tokenId,
        bytes memory _data
    ) internal virtual {
        _transfer(from, to, tokenId);
        require(_checkOnERC721Received(from, to, tokenId, _data), "ERC721: transfer to non ERC721Receiver implementer");
    }

    /**
     * @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`),
     * and stop existing when they are burned (`_burn`).
     */
    function _exists(uint256 tokenId) internal view virtual returns (bool) {
        return _owners[tokenId] != address(0);
    }

    /**
     * @dev Returns whether `spender` is allowed to manage `tokenId`.
     *
     * Requirements:
     *
     * - `tokenId` must exist.
     */
    function _isApprovedOrOwner(address spender, uint256 tokenId) internal view virtual returns (bool) {
        require(_exists(tokenId), "ERC721: operator query for nonexistent token");
        address owner = ERC721.ownerOf(tokenId);
        return (spender == owner || isApprovedForAll(owner, spender) || getApproved(tokenId) == spender);
    }

    /**
     * @dev Safely mints `tokenId` and transfers it to `to`.
     *
     * Requirements:
     *
     * - `tokenId` must not exist.
     * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer.
     *
     * Emits a {Transfer} event.
     */
    function _safeMint(address to, uint256 tokenId) internal virtual {
        _safeMint(to, tokenId, "");
    }

    /**
     * @dev Same as {xref-ERC721-_safeMint-address-uint256-}[`_safeMint`], with an additional `data` parameter which is
     * forwarded in {IERC721Receiver-onERC721Received} to contract recipients.
     */
    function _safeMint(
        address to,
        uint256 tokenId,
        bytes memory _data
    ) internal virtual {
        _mint(to, tokenId);
        require(
            _checkOnERC721Received(address(0), to, tokenId, _data),
            "ERC721: transfer to non ERC721Receiver implementer"
        );
    }

    /**
     * @dev Mints `tokenId` and transfers it to `to`.
     *
     * WARNING: Usage of this method is discouraged, use {_safeMint} whenever possible
     *
     * Requirements:
     *
     * - `tokenId` must not exist.
     * - `to` cannot be the zero address.
     *
     * Emits a {Transfer} event.
     */
    function _mint(address to, uint256 tokenId) internal virtual {
        require(to != address(0), "ERC721: mint to the zero address");
        require(!_exists(tokenId), "ERC721: token already minted");

        _beforeTokenTransfer(address(0), to, tokenId);

        _balances[to] += 1;
        _owners[tokenId] = to;

        emit Transfer(address(0), to, tokenId);

        _afterTokenTransfer(address(0), to, tokenId);
    }

    /**
     * @dev Destroys `tokenId`.
     * The approval is cleared when the token is burned.
     *
     * Requirements:
     *
     * - `tokenId` must exist.
     *
     * Emits a {Transfer} event.
     */
    function _burn(uint256 tokenId) internal virtual {
        address owner = ERC721.ownerOf(tokenId);

        _beforeTokenTransfer(owner, address(0), tokenId);

        // Clear approvals
        _approve(address(0), tokenId);

        _balances[owner] -= 1;
        delete _owners[tokenId];

        emit Transfer(owner, address(0), tokenId);

        _afterTokenTransfer(owner, address(0), tokenId);
    }

    /**
     * @dev Transfers `tokenId` from `from` to `to`.
     *  As opposed to {transferFrom}, this imposes no restrictions on msg.sender.
     *
     * 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
    ) internal virtual {
        require(ERC721.ownerOf(tokenId) == from, "ERC721: transfer from incorrect owner");
        require(to != address(0), "ERC721: transfer to the zero address");

        _beforeTokenTransfer(from, to, tokenId);

        // Clear approvals from the previous owner
        _approve(address(0), tokenId);

        _balances[from] -= 1;
        _balances[to] += 1;
        _owners[tokenId] = to;

        emit Transfer(from, to, tokenId);

        _afterTokenTransfer(from, to, tokenId);
    }

    /**
     * @dev Approve `to` to operate on `tokenId`
     *
     * Emits a {Approval} event.
     */
    function _approve(address to, uint256 tokenId) internal virtual {
        _tokenApprovals[tokenId] = to;
        emit Approval(ERC721.ownerOf(tokenId), to, tokenId);
    }

    /**
     * @dev Approve `operator` to operate on all of `owner` tokens
     *
     * Emits a {ApprovalForAll} event.
     */
    function _setApprovalForAll(
        address owner,
        address operator,
        bool approved
    ) internal virtual {
        require(owner != operator, "ERC721: approve to caller");
        _operatorApprovals[owner][operator] = approved;
        emit ApprovalForAll(owner, operator, approved);
    }

    /**
     * @dev Internal function to invoke {IERC721Receiver-onERC721Received} on a target address.
     * The call is not executed if the target address is not a 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 _checkOnERC721Received(
        address from,
        address to,
        uint256 tokenId,
        bytes memory _data
    ) private returns (bool) {
        if (to.isContract()) {
            try IERC721Receiver(to).onERC721Received(_msgSender(), from, tokenId, _data) returns (bytes4 retval) {
                return retval == IERC721Receiver.onERC721Received.selector;
            } catch (bytes memory reason) {
                if (reason.length == 0) {
                    revert("ERC721: transfer to non ERC721Receiver implementer");
                } else {
                    assembly {
                        revert(add(32, reason), mload(reason))
                    }
                }
            }
        } else {
            return true;
        }
    }

    /**
     * @dev Hook that is called before any token transfer. This includes minting
     * and burning.
     *
     * 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, ``from``'s `tokenId` will be burned.
     * - `from` and `to` are never both zero.
     *
     * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
     */
    function _beforeTokenTransfer(
        address from,
        address to,
        uint256 tokenId
    ) internal virtual {}

    /**
     * @dev Hook that is called after any transfer of tokens. This includes
     * minting and burning.
     *
     * Calling conditions:
     *
     * - when `from` and `to` are both non-zero.
     * - `from` and `to` are never both zero.
     *
     * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
     */
    function _afterTokenTransfer(
        address from,
        address to,
        uint256 tokenId
    ) internal virtual {}
}

// File: @openzeppelin/contracts/token/ERC721/extensions/ERC721Enumerable.sol


// OpenZeppelin Contracts v4.4.1 (token/ERC721/extensions/ERC721Enumerable.sol)

pragma solidity ^0.8.0;



/**
 * @dev This implements an optional extension of {ERC721} defined in the EIP that adds
 * enumerability of all the token ids in the contract as well as all token ids owned by each
 * account.
 */
abstract contract ERC721Enumerable is ERC721, IERC721Enumerable {
    // Mapping from owner to list of owned token IDs
    mapping(address => mapping(uint256 => uint256)) private _ownedTokens;

    // Mapping from token ID to index of the owner tokens list
    mapping(uint256 => uint256) private _ownedTokensIndex;

    // Array with all token ids, used for enumeration
    uint256[] private _allTokens;

    // Mapping from token id to position in the allTokens array
    mapping(uint256 => uint256) private _allTokensIndex;

    /**
     * @dev See {IERC165-supportsInterface}.
     */
    function supportsInterface(bytes4 interfaceId) public view virtual override(IERC165, ERC721) returns (bool) {
        return interfaceId == type(IERC721Enumerable).interfaceId || super.supportsInterface(interfaceId);
    }

    /**
     * @dev See {IERC721Enumerable-tokenOfOwnerByIndex}.
     */
    function tokenOfOwnerByIndex(address owner, uint256 index) public view virtual override returns (uint256) {
        require(index < ERC721.balanceOf(owner), "ERC721Enumerable: owner index out of bounds");
        return _ownedTokens[owner][index];
    }

    /**
     * @dev See {IERC721Enumerable-totalSupply}.
     */
    function totalSupply() public view virtual override returns (uint256) {
        return _allTokens.length;
    }

    /**
     * @dev See {IERC721Enumerable-tokenByIndex}.
     */
    function tokenByIndex(uint256 index) public view virtual override returns (uint256) {
        require(index < ERC721Enumerable.totalSupply(), "ERC721Enumerable: global index out of bounds");
        return _allTokens[index];
    }

    /**
     * @dev Hook that is called before any token transfer. This includes minting
     * and burning.
     *
     * 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, ``from``'s `tokenId` will be burned.
     * - `from` cannot be the zero address.
     * - `to` cannot be the zero address.
     *
     * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
     */
    function _beforeTokenTransfer(
        address from,
        address to,
        uint256 tokenId
    ) internal virtual override {
        super._beforeTokenTransfer(from, to, tokenId);

        if (from == address(0)) {
            _addTokenToAllTokensEnumeration(tokenId);
        } else if (from != to) {
            _removeTokenFromOwnerEnumeration(from, tokenId);
        }
        if (to == address(0)) {
            _removeTokenFromAllTokensEnumeration(tokenId);
        } else if (to != from) {
            _addTokenToOwnerEnumeration(to, tokenId);
        }
    }

    /**
     * @dev Private function to add a token to this extension's ownership-tracking data structures.
     * @param to address representing the new owner of the given token ID
     * @param tokenId uint256 ID of the token to be added to the tokens list of the given address
     */
    function _addTokenToOwnerEnumeration(address to, uint256 tokenId) private {
        uint256 length = ERC721.balanceOf(to);
        _ownedTokens[to][length] = tokenId;
        _ownedTokensIndex[tokenId] = length;
    }

    /**
     * @dev Private function to add a token to this extension's token tracking data structures.
     * @param tokenId uint256 ID of the token to be added to the tokens list
     */
    function _addTokenToAllTokensEnumeration(uint256 tokenId) private {
        _allTokensIndex[tokenId] = _allTokens.length;
        _allTokens.push(tokenId);
    }

    /**
     * @dev Private function to remove a token from this extension's ownership-tracking data structures. Note that
     * while the token is not assigned a new owner, the `_ownedTokensIndex` mapping is _not_ updated: this allows for
     * gas optimizations e.g. when performing a transfer operation (avoiding double writes).
     * This has O(1) time complexity, but alters the order of the _ownedTokens array.
     * @param from address representing the previous owner of the given token ID
     * @param tokenId uint256 ID of the token to be removed from the tokens list of the given address
     */
    function _removeTokenFromOwnerEnumeration(address from, uint256 tokenId) private {
        // To prevent a gap in from's tokens array, we store the last token in the index of the token to delete, and
        // then delete the last slot (swap and pop).

        uint256 lastTokenIndex = ERC721.balanceOf(from) - 1;
        uint256 tokenIndex = _ownedTokensIndex[tokenId];

        // When the token to delete is the last token, the swap operation is unnecessary
        if (tokenIndex != lastTokenIndex) {
            uint256 lastTokenId = _ownedTokens[from][lastTokenIndex];

            _ownedTokens[from][tokenIndex] = lastTokenId; // Move the last token to the slot of the to-delete token
            _ownedTokensIndex[lastTokenId] = tokenIndex; // Update the moved token's index
        }

        // This also deletes the contents at the last position of the array
        delete _ownedTokensIndex[tokenId];
        delete _ownedTokens[from][lastTokenIndex];
    }

    /**
     * @dev Private function to remove a token from this extension's token tracking data structures.
     * This has O(1) time complexity, but alters the order of the _allTokens array.
     * @param tokenId uint256 ID of the token to be removed from the tokens list
     */
    function _removeTokenFromAllTokensEnumeration(uint256 tokenId) private {
        // To prevent a gap in the tokens array, we store the last token in the index of the token to delete, and
        // then delete the last slot (swap and pop).

        uint256 lastTokenIndex = _allTokens.length - 1;
        uint256 tokenIndex = _allTokensIndex[tokenId];

        // When the token to delete is the last token, the swap operation is unnecessary. However, since this occurs so
        // rarely (when the last minted token is burnt) that we still do the swap here to avoid the gas cost of adding
        // an 'if' statement (like in _removeTokenFromOwnerEnumeration)
        uint256 lastTokenId = _allTokens[lastTokenIndex];

        _allTokens[tokenIndex] = lastTokenId; // Move the last token to the slot of the to-delete token
        _allTokensIndex[lastTokenId] = tokenIndex; // Update the moved token's index

        // This also deletes the contents at the last position of the array
        delete _allTokensIndex[tokenId];
        _allTokens.pop();
    }
}

// File: finncotton.sol


pragma solidity ^0.8.0;  







error InvalidCall();

contract FinnCotton is ERC721Enumerable,ReentrancyGuard,AccessControl, Ownable{
    using Strings for uint256;
    
    struct GroupNFT{
        uint256 startTokenId;
        uint256 endTokenId;
        uint256 nextTokenId;
        bool isReveal;
        bool isPause;
        string baseURI;
    }

    bytes32 private constant _APPROVED_ROLE = keccak256("APPROVED_ROLE");
    
    uint256 public collectionSupplies = 10000; 
    uint256 public tokenIdPartner; 
    
    uint256 public cost = 0.06 ether; 
    uint256 public whiteListCost = 0.04 ether;  

    address public signer = 0x00A5bAc26C0BE6A598d0E524725C85ad8F188BaF;
    address public walletAddress = 0x0b33692475FeE247Aea054c4AB4FCE9BB6E70303;
     
    mapping(uint256 => string) public partnerNftURIs;   
 
    uint256 public maxMintPerWallet = 10;
    mapping(address => uint256) public walletMints;  
    mapping(address => uint256) public freeMints;  
    mapping(address => uint256) public whiteListMints;  
    bool public freeMintPause  = true;
    bool public whiteListPause  = true;
    bool public publicPause  = true;  
    string private _CONTRACT_URI = "ipfs://bafkreifuckldcrzl7ybek5adwnebufz4y2pn5z5y73v4faymmznyotmely";   

     // ----- Group Ethan -----
    // Group ID  : #1
    GroupNFT public groupEthan = GroupNFT(1,750,1,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/1.json");  
    // ----- Group Ethan -----

    // ----- Group Glide -----
    // Group ID  : #2
    GroupNFT public groupGlide = GroupNFT(751,2250,751,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/2.json");  
    // ----- Group Glide -----
    
    // ----- Group Raptor -----
    // Group ID  : #3
    GroupNFT public groupRaptor = GroupNFT(2251,4250,2251,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/3.json");  
    // ----- Group Raptor -----

    // ----- Group Strike -----
    // Group ID  : #4
    GroupNFT public groupStrike = GroupNFT(4251,5750,4251,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/4.json");  
    // ----- Group Strike ----- 
    
    // ----- Group PulseElite -----
    // Group ID  : #5
    GroupNFT public groupPulseElite = GroupNFT(5751,7750,5751,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/5.json");  
    // ----- Group PulseElite -----

    // ----- Group Ignite -----
    // Group ID  : #6
    GroupNFT public groupIgnite = GroupNFT(7751,9250,7751,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/6.json");  
    // ----- Group Ignite -----
    
    // ----- Group Noah -----
    // Group ID  : #7
    GroupNFT public groupNoah = GroupNFT(9251,10000,9251,false,true,"ipfs://bafybeibp4er6lk6cvm4jyvla4xicy6sabgthtmvsedtvpn234wobq3w6pa/7.json");  
    // ----- Group Noah -----
    

    constructor( )  ERC721("Finn Cotton", "FC")   {   
        _setupRole(DEFAULT_ADMIN_ROLE, msg.sender);
        unchecked { tokenIdPartner = collectionSupplies + 1; }    
    }
    
    function contractURI() external view returns(string memory) {
        return _CONTRACT_URI;
    }

    function isApprovedForAll(
        address owner,
        address operator
    ) public view override(IERC721,ERC721) returns(bool) {
        return hasRole(_APPROVED_ROLE, operator) 
        || super.isApprovedForAll(owner, operator);
    } 
    
    function mint(uint256 quantity_,uint256 groupId_)public payable nonReentrant{   
        require(!publicPause,"PUBLIC_MINT_PAUSED"); 
        require(quantity_ > 0,"INVALID_QUANTITY");  
        require(msg.value >= cost * quantity_, "INVALID_VALUE");
        require(walletMints[msg.sender] + quantity_ <= maxMintPerWallet, "EXCEED_MINT_PER_WALLET");

        _finalMint(quantity_,groupId_,msg.sender); 
        unchecked { walletMints[msg.sender] += quantity_; }
    }

  
    function specialMint(uint256 quantity_,uint256 groupId_,uint256 maxMint,uint256 mintStatus, bytes memory sig_)public payable nonReentrant {  
        
        bytes32 digest = keccak256(abi.encodePacked(mintStatus, msg.sender, maxMint));
        bytes32 message = ECDSA.toEthSignedMessageHash(digest); 
        require(ECDSA.recover(message, sig_) == signer, "CONTRACT_MINT_NOT_ALLOWED");     
 
        // mintStatus : freemint = 1; whitelist = 2  
        if(!whiteListPause && mintStatus == 2){
            // Whitelist mint
            require(msg.value >= whiteListCost * quantity_, "INVALID_VALUE");
            require(whiteListMints[msg.sender] + quantity_ <= maxMint, "EXCEED_WHITELIST_MINT"); 
        }else if (!freeMintPause && mintStatus == 1){
            // Freemint
            require(freeMints[msg.sender] + quantity_ <= maxMint, "EXCEED_FREE_MINT"); 
        }else{
            revert("INVALID_SPECIAL_MINT_1");
        }    
 
        require(quantity_ > 0,"INVALID_QUANTITY");   

        _finalMint(quantity_,groupId_,msg.sender); 
        unchecked { walletMints[msg.sender] += quantity_; }
        
        if(!whiteListPause && mintStatus == 2){
            // Whitelist mint
            unchecked { whiteListMints[msg.sender] += quantity_; }
        }else if (!freeMintPause && mintStatus == 1){
            // Freemint
            unchecked { freeMints[msg.sender] += quantity_; }
        }
    }  

    function isOwnsAll(
        address owner, 
        uint256[] memory tokenIds
    ) external view returns(bool) {
        for (uint256 i = 0; i < tokenIds.length; i++) {
            if (owner != ownerOf(tokenIds[i])) {
                return false;
            }
        } 
        return true;
    }
// =============================== START PRIVATE ===============================  

    function _mintGroup(uint256 quantity_,GroupNFT storage group_,address to_)private  { 
        GroupNFT storage group = group_;
        require(!group.isPause,"GROUP_PAUSE");
        
        unchecked{
            uint256 groupSupplies  = ((group.endTokenId - group.startTokenId) + 1) + (group.startTokenId-1); 
            require((group.nextTokenId - 1) + quantity_ <= groupSupplies,"NOT_ENOUGH_SUPPLIES");
 
            for (uint256 i = 0; i < quantity_; i++) {
                _safeMint(to_, group.nextTokenId);
                group.nextTokenId++;
            }  
        }
    }  
     
    function _finalMint(uint256 quantity_,uint256 groupId_,address to_)private { 
        if(groupId_ == 1){
            // Ethan Mint   
            _mintGroup(quantity_,groupEthan,to_);  
        }else if(groupId_ == 2){
            // Glide Mint
            _mintGroup(quantity_,groupGlide,to_);
        }else if(groupId_ == 3){
            // Raptor Mint
            _mintGroup(quantity_,groupRaptor,to_);
        }else if(groupId_ == 4){
            // Strike Mint
            _mintGroup(quantity_,groupStrike,to_);
        }else if(groupId_ == 5){
            // PulseElite Mint
            _mintGroup(quantity_,groupPulseElite,to_);
        }else if(groupId_ == 6){
            // Ignite Mint
            _mintGroup(quantity_,groupIgnite,to_);
        }else if(groupId_ == 7){
            // Noah Mint
            _mintGroup(quantity_,groupNoah,to_);
        }else{
            revert("INVALID_GROUP");
        }   
    }
    
// =============================== END PRIVATE ===============================
 

// =============================== START ONLY OWNER ===============================

    function modifyPartnerNftTokenUri(uint256 tokenId_,string calldata uri_ ) public onlyOwner{
        require(bytes(partnerNftURIs[tokenId_]).length > 0,"INVALID_PARTNER_TOKEN_ID"); 
        partnerNftURIs[tokenId_] = uri_;
    } 

    function partnerNftBatchMint(string[] memory partnerNFTs_) public onlyOwner  { 
        require(0 < partnerNFTs_.length, "INVALID_LENGTH");
        
        unchecked { 
            for(uint256 i = 0 ; i < partnerNFTs_.length ;i ++){    
                require(bytes(partnerNFTs_[i]).length > 0,"REQUIRED_URI");   

                partnerNftURIs[tokenIdPartner] = partnerNFTs_[i];

                _safeMint(owner(),tokenIdPartner); 
                tokenIdPartner++;  
            }
        } 
    }
    
    function setPauses(bool publicPause_, bool whiteListPause_,bool freeMintPause_) public onlyOwner{
        publicPause = publicPause_;
        whiteListPause = whiteListPause_;
        freeMintPause = freeMintPause_;
    }  

    function modifyGroupPause(uint256 groupId_ ,bool isPause_)public onlyOwner{ 
        if(groupId_ == 1){
            // Ethan 
            groupEthan.isPause = isPause_;
        }else if(groupId_ == 2 ){
            // Glide  
            groupGlide.isPause = isPause_;
        }else if(groupId_ == 3 ){
            // Raptor  
            groupRaptor.isPause = isPause_;
        }else if(groupId_ == 4 ){
            // Strike  
            groupStrike.isPause = isPause_;
        }else if(groupId_ == 5 ){
            // PulseElite  
            groupPulseElite.isPause = isPause_;
        }else if(groupId_ == 6 ){
            // Ignite  
            groupIgnite.isPause = isPause_;
        }else if(groupId_ == 7){
            // Noah  
            groupNoah.isPause = isPause_;
        } 
    } 

    function modifyGroupRevealBaseURI(uint256 groupId_ ,bool isReveal_,string calldata baseURI_)public onlyOwner{ 
        if(groupId_ == 1){
            // Ethan 
            groupEthan.isReveal = isReveal_;
            groupEthan.baseURI = baseURI_;
        }else if(groupId_ == 2 ){
            // Glide  
            groupGlide.isReveal = isReveal_;
            groupGlide.baseURI = baseURI_; 
        }else if(groupId_ == 3 ){
            // Raptor  
            groupRaptor.isReveal = isReveal_;
            groupRaptor.baseURI = baseURI_;
        }else if(groupId_ == 4 ){
            // Strike  
            groupStrike.isReveal = isReveal_;
            groupStrike.baseURI = baseURI_;
        }else if(groupId_ == 5 ){
            // PulseElite  
            groupPulseElite.isReveal = isReveal_;
            groupPulseElite.baseURI = baseURI_;
        }else if(groupId_ == 6 ){
            // Ignite  
            groupIgnite.isReveal = isReveal_;
            groupIgnite.baseURI = baseURI_;
        }else if(groupId_ == 7){
            // Noah  
            groupNoah.isReveal = isReveal_;
            groupNoah.baseURI = baseURI_;
        } 
    } 

    function modifyGroup(uint256 groupId_ ,uint256 startTokenId_,uint256 endTokenId_,uint256 nextTokenId_)public onlyOwner{ 
        if(groupId_ == 1){
            // Ethan 
            groupEthan.startTokenId = startTokenId_;
            groupEthan.endTokenId = endTokenId_;
            groupEthan.nextTokenId = nextTokenId_;
        }else if(groupId_ == 2 ){
            // Glide   
            groupGlide.startTokenId = startTokenId_;
            groupGlide.endTokenId = endTokenId_;
            groupGlide.nextTokenId = nextTokenId_;
        }else if(groupId_ == 3 ){
            // Raptor   
            groupRaptor.startTokenId = startTokenId_;
            groupRaptor.endTokenId = endTokenId_;
            groupRaptor.nextTokenId = nextTokenId_;
        }else if(groupId_ == 4 ){
            // Strike   
            groupStrike.startTokenId = startTokenId_;
            groupStrike.endTokenId = endTokenId_;
            groupStrike.nextTokenId = nextTokenId_;
        }else if(groupId_ == 5 ){
            // PulseElite   
            groupPulseElite.startTokenId = startTokenId_;
            groupPulseElite.endTokenId = endTokenId_;
            groupPulseElite.nextTokenId = nextTokenId_;
        }else if(groupId_ == 6 ){
            // Ignite   
            groupIgnite.startTokenId = startTokenId_;
            groupIgnite.endTokenId = endTokenId_;
            groupIgnite.nextTokenId = nextTokenId_;
        }else if(groupId_ == 7){
            // Noah   
            groupNoah.startTokenId = startTokenId_;
            groupNoah.endTokenId = endTokenId_;
            groupNoah.nextTokenId = nextTokenId_;
        } 
    }  
    
    function setMaxMintPerWallet(uint256 maxMintPerWallet_)public onlyOwner{
        maxMintPerWallet = maxMintPerWallet_;
    }

    function setWhiteListCost(uint256 whiteListCost_)public onlyOwner{
        whiteListCost = whiteListCost_;
    }

    function setCost(uint256 cost_)public onlyOwner{
        cost = cost_;
    }

    function setSigner(address signer_) public onlyOwner{
        signer = signer_;
    } 

    function mintOwner(address to_ ,uint256 quantity_,uint256 groupId_)public onlyOwner  nonReentrant{  
        require(quantity_ > 0,"INVALID_QUANTITY");    
        _finalMint(quantity_,groupId_,to_);
    }

    function setWalletAddress(address _walletAddress) external onlyOwner nonReentrant { 
        walletAddress = _walletAddress;
    }

    function withdraw() external onlyOwner nonReentrant { 
        payable(walletAddress).transfer(address(this).balance);
    } 
    
// =============================== END ONLY OWNER ===============================
 
    function tokenURI(uint256 tokenId_)  public view override returns(string memory){  
        require(_exists(tokenId_), "TOKEN_IS_NOT_EXIST");

        if (bytes(partnerNftURIs[tokenId_]).length > 0) { 
            return partnerNftURIs[tokenId_];
        }

        bool isReveal = false; 
        string memory baseURI;

        if(groupEthan.startTokenId <= tokenId_  && groupEthan.endTokenId>= tokenId_ ){
            isReveal = groupEthan.isReveal;
            baseURI = groupEthan.baseURI;
        }else if(groupGlide.startTokenId <= tokenId_  && groupGlide.endTokenId>= tokenId_ ){
            isReveal = groupGlide.isReveal;
            baseURI = groupGlide.baseURI;
        }else if(groupRaptor.startTokenId <= tokenId_  && groupRaptor.endTokenId>= tokenId_ ){
            isReveal = groupRaptor.isReveal;
            baseURI = groupRaptor.baseURI;
        }else if(groupStrike.startTokenId <= tokenId_  && groupStrike.endTokenId>= tokenId_ ){
            isReveal = groupStrike.isReveal;
            baseURI = groupStrike.baseURI;
        }else if(groupPulseElite.startTokenId <= tokenId_  && groupPulseElite.endTokenId>= tokenId_){
            isReveal = groupPulseElite.isReveal;
            baseURI = groupPulseElite.baseURI;
        }else if(groupIgnite.startTokenId <= tokenId_  && groupIgnite.endTokenId>= tokenId_){
            isReveal = groupIgnite.isReveal;
            baseURI = groupIgnite.baseURI;
        }else if(groupNoah.startTokenId <= tokenId_  && groupNoah.endTokenId>= tokenId_){
            isReveal = groupNoah.isReveal;
            baseURI = groupNoah.baseURI;
        }
 
        if(isReveal){
            return string(
                abi.encodePacked(baseURI, tokenId_.toString(), ".json")
            ); 
        }else{
            return string(
                abi.encodePacked(baseURI)
            ); 
        } 
    }  

    function tokensOfOwner(address _owner) public view returns (uint256[] memory) {
        uint256 ownerTokenCount = balanceOf(_owner);
        uint256[] memory tokenIds = new uint256[](ownerTokenCount);
        for (uint256 i; i < ownerTokenCount; i++) {
            tokenIds[i] = tokenOfOwnerByIndex(_owner, i);
        }
        return tokenIds;
    }   
    
    function setContractURI(string memory _uri) external onlyOwner {
        _CONTRACT_URI = _uri;
    }
    
    function supportsInterface(bytes4 interfaceId) public view virtual override(AccessControl,ERC721Enumerable) returns (bool) { 
        return interfaceId == type(IERC721Metadata).interfaceId  
        || super.supportsInterface(interfaceId);
    }
}

Contract Security Audit

Contract ABI

[{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"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":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","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":[{"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":"collectionSupplies","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"contractURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"cost","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"freeMintPause","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"freeMints","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"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":"address","name":"account","type":"address"}],"name":"grantRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"groupEthan","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupGlide","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupIgnite","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupNoah","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupPulseElite","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupRaptor","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"groupStrike","outputs":[{"internalType":"uint256","name":"startTokenId","type":"uint256"},{"internalType":"uint256","name":"endTokenId","type":"uint256"},{"internalType":"uint256","name":"nextTokenId","type":"uint256"},{"internalType":"bool","name":"isReveal","type":"bool"},{"internalType":"bool","name":"isPause","type":"bool"},{"internalType":"string","name":"baseURI","type":"string"}],"stateMutability":"view","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":"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":"owner","type":"address"},{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"}],"name":"isOwnsAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maxMintPerWallet","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"quantity_","type":"uint256"},{"internalType":"uint256","name":"groupId_","type":"uint256"}],"name":"mint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"to_","type":"address"},{"internalType":"uint256","name":"quantity_","type":"uint256"},{"internalType":"uint256","name":"groupId_","type":"uint256"}],"name":"mintOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"groupId_","type":"uint256"},{"internalType":"uint256","name":"startTokenId_","type":"uint256"},{"internalType":"uint256","name":"endTokenId_","type":"uint256"},{"internalType":"uint256","name":"nextTokenId_","type":"uint256"}],"name":"modifyGroup","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"groupId_","type":"uint256"},{"internalType":"bool","name":"isPause_","type":"bool"}],"name":"modifyGroupPause","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"groupId_","type":"uint256"},{"internalType":"bool","name":"isReveal_","type":"bool"},{"internalType":"string","name":"baseURI_","type":"string"}],"name":"modifyGroupRevealBaseURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId_","type":"uint256"},{"internalType":"string","name":"uri_","type":"string"}],"name":"modifyPartnerNftTokenUri","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"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":"partnerNFTs_","type":"string[]"}],"name":"partnerNftBatchMint","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"partnerNftURIs","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"publicPause","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","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":"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":"string","name":"_uri","type":"string"}],"name":"setContractURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"cost_","type":"uint256"}],"name":"setCost","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"maxMintPerWallet_","type":"uint256"}],"name":"setMaxMintPerWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bool","name":"publicPause_","type":"bool"},{"internalType":"bool","name":"whiteListPause_","type":"bool"},{"internalType":"bool","name":"freeMintPause_","type":"bool"}],"name":"setPauses","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"signer_","type":"address"}],"name":"setSigner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_walletAddress","type":"address"}],"name":"setWalletAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"whiteListCost_","type":"uint256"}],"name":"setWhiteListCost","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"signer","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"quantity_","type":"uint256"},{"internalType":"uint256","name":"groupId_","type":"uint256"},{"internalType":"uint256","name":"maxMint","type":"uint256"},{"internalType":"uint256","name":"mintStatus","type":"uint256"},{"internalType":"bytes","name":"sig_","type":"bytes"}],"name":"specialMint","outputs":[],"stateMutability":"payable","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":"index","type":"uint256"}],"name":"tokenByIndex","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"tokenIdPartner","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"uint256","name":"index","type":"uint256"}],"name":"tokenOfOwnerByIndex","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"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":[],"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":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"walletAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"walletMints","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"whiteListCost","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"whiteListMints","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"whiteListPause","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"withdraw","outputs":[],"stateMutability":"nonpayable","type":"function"}]

612710600d5566d529ae9e860000600f55668e1bc9bf040000601055601180546001600160a01b031990811672a5bac26c0be6a598d0e524725c85ad8f188baf1790915560128054909116730b33692475fee247aea054c4ab4fce9bb6e70303179055600a601455601880546201010162ffffff19909116179055610100604052604260808181529062004f3d60a0396019906200009e908262000798565b506040518060c00160405280600181526020016102ee81526020016001815260200160001515815260200160011515815260200160405180608001604052806049815260200162004fc86049913990528051601a9081556020820151601b556040820151601c556060820151601d8054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151601e9062000146908262000798565b5050506040518060c001604052806102ef81526020016108ca81526020016102ef81526020016000151581526020016001151581526020016040518060800160405280604981526020016200505a6049913990528051601f90815560208083015190556040820151602155606082015160228054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151602390620001f2908262000798565b5050506040518060c001604052806108cb815260200161109a81526020016108cb8152602001600015158152602001600115158152602001604051806080016040528060498152602001620051356049913990528051602490815560208201516025556040820151602655606082015160278054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a08201516028906200029e908262000798565b5050506040518060c0016040528061109b8152602001611676815260200161109b8152602001600015158152602001600115158152602001604051806080016040528060498152602001620050ec604991399052805160299081556020820151602a556040820151602b556060820151602c8054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151602d906200034a908262000798565b5050506040518060c001604052806116778152602001611e4681526020016116778152602001600015158152602001600115158152602001604051806080016040528060498152602001620050116049913990528051602e9081556020820151602f556040820151603055606082015160318054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151603290620003f6908262000798565b5050506040518060c00160405280611e4781526020016124228152602001611e47815260200160001515815260200160011515815260200160405180608001604052806049815260200162004f7f6049913990528051603390815560208201516034556040820151603555606082015160368054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151603790620004a2908262000798565b5050506040518060c00160405280612423815260200161271081526020016124238152602001600015158152602001600115158152602001604051806080016040528060498152602001620050a36049913990528051603890815560208201516039556040820151603a556060820151603b8054608085015115156101000261ff00199315159390931661ffff199091161791909117905560a0820151603c906200054e908262000798565b5050503480156200055e57600080fd5b506040518060400160405280600b81526020016a2334b7371021b7ba3a37b760a91b81525060405180604001604052806002815260200161464360f01b8152508160009081620005af919062000798565b506001620005be828262000798565b50506001600a5550620005d133620005ed565b620005de6000336200063f565b600d54600101600e5562000864565b600c80546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b6200064b82826200064f565b5050565b6000828152600b602090815260408083206001600160a01b038516845290915290205460ff166200064b576000828152600b602090815260408083206001600160a01b03851684529091529020805460ff19166001179055620006af3390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b634e487b7160e01b600052604160045260246000fd5b600181811c908216806200071e57607f821691505b6020821081036200073f57634e487b7160e01b600052602260045260246000fd5b50919050565b601f8211156200079357600081815260208120601f850160051c810160208610156200076e5750805b601f850160051c820191505b818110156200078f578281556001016200077a565b5050505b505050565b81516001600160401b03811115620007b457620007b4620006f3565b620007cc81620007c5845462000709565b8462000745565b602080601f831160018114620008045760008415620007eb5750858301515b600019600386901b1c1916600185901b1785556200078f565b600085815260208120601f198616915b82811015620008355788860151825594840194600190910190840162000814565b5085821015620008545787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b6146c980620008746000396000f3fe6080604052600436106103ce5760003560e01c80638462151c116101fd578063b88d4fde11610118578063d547741f116100ab578063e985e9c51161007a578063e985e9c514610b03578063eceaf40014610b23578063edf5354c14610b42578063f0293fd314610b57578063f2fde38b14610b8457600080fd5b8063d547741f14610a8e578063d6de205e14610aae578063daaa09a414610ace578063e8a3d48514610aee57600080fd5b8063c87b56dd116100e7578063c87b56dd14610a19578063c919578114610a39578063cc2abd6414610a4e578063d27bbe7914610a6e57600080fd5b8063b88d4fde146109ae578063bd370b3e146109ce578063c19fb568146109e3578063c7e9d141146109f957600080fd5b80639ff5a24b11610190578063a67b4bbb1161015f578063a67b4bbb14610938578063ac1a386a14610958578063afdf613414610978578063b228d9251461099857600080fd5b80639ff5a24b146108d9578063a217fddf146108ee578063a22cb46514610903578063a597106f1461092357600080fd5b80639257e044116101cc5780639257e0441461087b5780639382699214610891578063938e3d7b146108a457806395d89b41146108c457600080fd5b80638462151c146107fb5780638da5cb5b1461082857806391d14854146108465780639255d5681461086657600080fd5b80633ccfd60b116102ed5780636352211e116102805780636d41d4fb1161024f5780636d41d4fb1461077957806370a08231146107a6578063715018a6146107c6578063819d7c63146107db57600080fd5b80636352211e146106f957806369ec2f09146107195780636ad5b3ea146107395780636c19e7831461075957600080fd5b806349071a2b116102bc57806349071a2b146106765780634f6ccce71461068c5780635d655285146106ac5780635e58a509146106d957600080fd5b80633ccfd60b146105fa57806342842e0e1461060f57806343bfbe7c1461062f57806344a0d68a1461065657600080fd5b8063197db9c811610365578063248a9ca311610334578063248a9ca31461056a5780632f2ff15d1461059a5780632f745c59146105ba57806336568abe146105da57600080fd5b8063197db9c8146104f75780631b2ef1ca14610517578063238ac9331461052a57806323b872dd1461054a57600080fd5b8063095ea7b3116103a1578063095ea7b31461047c57806312653a341461049e57806313faede6146104be57806318160ddd146104e257600080fd5b806301ffc9a7146103d357806303a3c2221461040857806306fdde0314610422578063081812fc14610444575b600080fd5b3480156103df57600080fd5b506103f36103ee3660046139dc565b610ba4565b60405190151581526020015b60405180910390f35b34801561041457600080fd5b506018546103f39060ff1681565b34801561042e57600080fd5b50610437610bcf565b6040516103ff9190613a49565b34801561045057600080fd5b5061046461045f366004613a5c565b610c61565b6040516001600160a01b0390911681526020016103ff565b34801561048857600080fd5b5061049c610497366004613a91565b610cfb565b005b3480156104aa57600080fd5b5061049c6104b9366004613acb565b610e10565b3480156104ca57600080fd5b506104d4600f5481565b6040519081526020016103ff565b3480156104ee57600080fd5b506008546104d4565b34801561050357600080fd5b5061049c610512366004613b38565b610f14565b61049c610525366004613b91565b611041565b34801561053657600080fd5b50601154610464906001600160a01b031681565b34801561055657600080fd5b5061049c610565366004613bb3565b6111b1565b34801561057657600080fd5b506104d4610585366004613a5c565b6000908152600b602052604090206001015490565b3480156105a657600080fd5b5061049c6105b5366004613bef565b6111e2565b3480156105c657600080fd5b506104d46105d5366004613a91565b611207565b3480156105e657600080fd5b5061049c6105f5366004613bef565b61129d565b34801561060657600080fd5b5061049c611317565b34801561061b57600080fd5b5061049c61062a366004613bb3565b6113a9565b34801561063b57600080fd5b506106446113c4565b6040516103ff96959493929190613c12565b34801561066257600080fd5b5061049c610671366004613a5c565b611478565b34801561068257600080fd5b506104d4600d5481565b34801561069857600080fd5b506104d46106a7366004613a5c565b6114a7565b3480156106b857600080fd5b506104d46106c7366004613c53565b60176020526000908152604090205481565b3480156106e557600080fd5b5061049c6106f4366004613c6e565b61153a565b34801561070557600080fd5b50610464610714366004613a5c565b6115e5565b34801561072557600080fd5b5061049c610734366004613cb9565b61165c565b34801561074557600080fd5b50601254610464906001600160a01b031681565b34801561076557600080fd5b5061049c610774366004613c53565b6116df565b34801561078557600080fd5b506104d4610794366004613c53565b60166020526000908152604090205481565b3480156107b257600080fd5b506104d46107c1366004613c53565b61172b565b3480156107d257600080fd5b5061049c6117b2565b3480156107e757600080fd5b5061049c6107f6366004613dc4565b6117e8565b34801561080757600080fd5b5061081b610816366004613c53565b611924565b6040516103ff9190613e79565b34801561083457600080fd5b50600c546001600160a01b0316610464565b34801561085257600080fd5b506103f3610861366004613bef565b6119c5565b34801561087257600080fd5b506106446119f0565b34801561088757600080fd5b506104d460105481565b61049c61089f366004613ebd565b611a21565b3480156108b057600080fd5b5061049c6108bf366004613f20565b611d76565b3480156108d057600080fd5b50610437611dac565b3480156108e557600080fd5b50610644611dbb565b3480156108fa57600080fd5b506104d4600081565b34801561090f57600080fd5b5061049c61091e366004613f54565b611dec565b34801561092f57600080fd5b50610644611df7565b34801561094457600080fd5b506103f3610953366004613f7e565b611e28565b34801561096457600080fd5b5061049c610973366004613c53565b611e95565b34801561098457600080fd5b5061049c610993366004613a5c565b611f08565b3480156109a457600080fd5b506104d460145481565b3480156109ba57600080fd5b5061049c6109c9366004614021565b611f37565b3480156109da57600080fd5b50610644611f69565b3480156109ef57600080fd5b506104d4600e5481565b348015610a0557600080fd5b5061049c610a14366004613a5c565b611f9a565b348015610a2557600080fd5b50610437610a34366004613a5c565b611fc9565b348015610a4557600080fd5b50610644612392565b348015610a5a57600080fd5b5061049c610a69366004614088565b6123c3565b348015610a7a57600080fd5b5061049c610a893660046140cb565b612425565b348015610a9a57600080fd5b5061049c610aa9366004613bef565b61250e565b348015610aba57600080fd5b50610437610ac9366004613a5c565b612533565b348015610ada57600080fd5b506018546103f39062010000900460ff1681565b348015610afa57600080fd5b506104376125cd565b348015610b0f57600080fd5b506103f3610b1e3660046140fd565b6125dc565b348015610b2f57600080fd5b506018546103f390610100900460ff1681565b348015610b4e57600080fd5b5061064461263f565b348015610b6357600080fd5b506104d4610b72366004613c53565b60156020526000908152604090205481565b348015610b9057600080fd5b5061049c610b9f366004613c53565b612670565b60006001600160e01b03198216635b5e139f60e01b1480610bc95750610bc98261270b565b92915050565b606060008054610bde90614127565b80601f0160208091040260200160405190810160405280929190818152602001828054610c0a90614127565b8015610c575780601f10610c2c57610100808354040283529160200191610c57565b820191906000526020600020905b815481529060010190602001808311610c3a57829003601f168201915b5050505050905090565b6000818152600260205260408120546001600160a01b0316610cdf5760405162461bcd60e51b815260206004820152602c60248201527f4552433732313a20617070726f76656420717565727920666f72206e6f6e657860448201526b34b9ba32b73a103a37b5b2b760a11b60648201526084015b60405180910390fd5b506000908152600460205260409020546001600160a01b031690565b6000610d06826115e5565b9050806001600160a01b0316836001600160a01b031603610d735760405162461bcd60e51b815260206004820152602160248201527f4552433732313a20617070726f76616c20746f2063757272656e74206f776e656044820152603960f91b6064820152608401610cd6565b336001600160a01b0382161480610d8f5750610d8f81336125dc565b610e015760405162461bcd60e51b815260206004820152603860248201527f4552433732313a20617070726f76652063616c6c6572206973206e6f74206f7760448201527f6e6572206e6f7220617070726f76656420666f7220616c6c00000000000000006064820152608401610cd6565b610e0b8383612730565b505050565b600c546001600160a01b03163314610e3a5760405162461bcd60e51b8152600401610cd690614161565b81600103610e5957601d805461ff001916610100831515021790555050565b81600203610e78576022805461ff001916610100831515021790555050565b81600303610e97576027805461ff001916610100831515021790555050565b81600403610eb657602c805461ff001916610100831515021790555050565b81600503610ed5576031805461ff001916610100831515021790555050565b81600603610ef4576036805461ff001916610100831515021790555050565b81600703610f1057603b805461ff001916610100831515021790555b5050565b600c546001600160a01b03163314610f3e5760405162461bcd60e51b8152600401610cd690614161565b83600103610f6757601d805460ff1916841515179055601e610f618284836141dc565b5061103b565b83600203610f8a576022805460ff19168415151790556023610f618284836141dc565b83600303610fad576027805460ff19168415151790556028610f618284836141dc565b83600403610fd057602c805460ff1916841515179055602d610f618284836141dc565b83600503610ff3576031805460ff19168415151790556032610f618284836141dc565b83600603611016576036805460ff19168415151790556037610f618284836141dc565b8360070361103b57603b805460ff1916841515179055603c6110398284836141dc565b505b50505050565b6002600a54036110635760405162461bcd60e51b8152600401610cd69061429b565b6002600a5560185462010000900460ff16156110b65760405162461bcd60e51b8152602060048201526012602482015271141550931250d7d352539517d4105554d15160721b6044820152606401610cd6565b600082116110d65760405162461bcd60e51b8152600401610cd6906142d2565b81600f546110e49190614312565b3410156111235760405162461bcd60e51b815260206004820152600d60248201526c494e56414c49445f56414c554560981b6044820152606401610cd6565b60145433600090815260156020526040902054611141908490614331565b11156111885760405162461bcd60e51b8152602060048201526016602482015275115610d1515117d352539517d4115497d5d05313115560521b6044820152606401610cd6565b61119382823361279e565b50336000908152601560205260409020805490910190556001600a55565b6111bb3382612862565b6111d75760405162461bcd60e51b8152600401610cd690614344565b610e0b838383612939565b6000828152600b60205260409020600101546111fd81612ae0565b610e0b8383612aea565b60006112128361172b565b82106112745760405162461bcd60e51b815260206004820152602b60248201527f455243373231456e756d657261626c653a206f776e657220696e646578206f7560448201526a74206f6620626f756e647360a81b6064820152608401610cd6565b506001600160a01b03919091166000908152600660209081526040808320938352929052205490565b6001600160a01b038116331461130d5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b6064820152608401610cd6565b610f108282612b70565b600c546001600160a01b031633146113415760405162461bcd60e51b8152600401610cd690614161565b6002600a54036113635760405162461bcd60e51b8152600401610cd69061429b565b6002600a556012546040516001600160a01b03909116904780156108fc02916000818181858888f193505050501580156113a1573d6000803e3d6000fd5b506001600a55565b610e0b83838360405180602001604052806000815250611f37565b602e8054602f546030546031546032805494959394929360ff8084169461010090940416929091906113f590614127565b80601f016020809104026020016040519081016040528092919081815260200182805461142190614127565b801561146e5780601f106114435761010080835404028352916020019161146e565b820191906000526020600020905b81548152906001019060200180831161145157829003601f168201915b5050505050905086565b600c546001600160a01b031633146114a25760405162461bcd60e51b8152600401610cd690614161565b600f55565b60006114b260085490565b82106115155760405162461bcd60e51b815260206004820152602c60248201527f455243373231456e756d657261626c653a20676c6f62616c20696e646578206f60448201526b7574206f6620626f756e647360a01b6064820152608401610cd6565b6008828154811061152857611528614395565b90600052602060002001549050919050565b600c546001600160a01b031633146115645760405162461bcd60e51b8152600401610cd690614161565b6000838152601360205260408120805461157d90614127565b9050116115cc5760405162461bcd60e51b815260206004820152601860248201527f494e56414c49445f504152544e45525f544f4b454e5f494400000000000000006044820152606401610cd6565b600083815260136020526040902061103b8284836141dc565b6000818152600260205260408120546001600160a01b031680610bc95760405162461bcd60e51b815260206004820152602960248201527f4552433732313a206f776e657220717565727920666f72206e6f6e657869737460448201526832b73a103a37b5b2b760b91b6064820152608401610cd6565b600c546001600160a01b031633146116865760405162461bcd60e51b8152600401610cd690614161565b6002600a54036116a85760405162461bcd60e51b8152600401610cd69061429b565b6002600a55816116ca5760405162461bcd60e51b8152600401610cd6906142d2565b6116d582828561279e565b50506001600a5550565b600c546001600160a01b031633146117095760405162461bcd60e51b8152600401610cd690614161565b601180546001600160a01b0319166001600160a01b0392909216919091179055565b60006001600160a01b0382166117965760405162461bcd60e51b815260206004820152602a60248201527f4552433732313a2062616c616e636520717565727920666f7220746865207a65604482015269726f206164647265737360b01b6064820152608401610cd6565b506001600160a01b031660009081526003602052604090205490565b600c546001600160a01b031633146117dc5760405162461bcd60e51b8152600401610cd690614161565b6117e66000612bd7565b565b600c546001600160a01b031633146118125760405162461bcd60e51b8152600401610cd690614161565b80516000106118545760405162461bcd60e51b815260206004820152600e60248201526d0929cac82989288be988a9c8ea8960931b6044820152606401610cd6565b60005b8151811015610f1057600082828151811061187457611874614395565b602002602001015151116118b95760405162461bcd60e51b815260206004820152600c60248201526b52455155495245445f55524960a01b6044820152606401610cd6565b8181815181106118cb576118cb614395565b602002602001015160136000600e54815260200190815260200160002090816118f491906143ab565b5061191261190a600c546001600160a01b031690565b600e54612c29565b600e8054600190810190915501611857565b606060006119318361172b565b90506000816001600160401b0381111561194d5761194d613cec565b604051908082528060200260200182016040528015611976578160200160208202803683370190505b50905060005b828110156119bd5761198e8582611207565b8282815181106119a0576119a0614395565b6020908102919091010152806119b58161446a565b91505061197c565b509392505050565b6000918252600b602090815260408084206001600160a01b0393909316845291905290205460ff1690565b601f80546020546021546022546023805494959394929360ff8084169461010090940416929091906113f590614127565b6002600a5403611a435760405162461bcd60e51b8152600401610cd69061429b565b6002600a556040805160208082018590523360601b6bffffffffffffffffffffffff1916828401526054808301879052835180840390910181526074830184528051908201207f19457468657265756d205369676e6564204d6573736167653a0a333200000000609484015260b08084018290528451808503909101815260d090930190935281519101206011546001600160a01b0316611ae48285612c43565b6001600160a01b031614611b3a5760405162461bcd60e51b815260206004820152601960248201527f434f4e54524143545f4d494e545f4e4f545f414c4c4f574544000000000000006044820152606401610cd6565b601854610100900460ff16158015611b525750836002145b15611c0c5786601054611b659190614312565b341015611ba45760405162461bcd60e51b815260206004820152600d60248201526c494e56414c49445f56414c554560981b6044820152606401610cd6565b336000908152601760205260409020548590611bc1908990614331565b1115611c075760405162461bcd60e51b8152602060048201526015602482015274115610d1515117d5d2125511531254d517d3525395605a1b6044820152606401610cd6565b611cc3565b60185460ff16158015611c1f5750836001145b15611c8257336000908152601660205260409020548590611c41908990614331565b1115611c075760405162461bcd60e51b815260206004820152601060248201526f115610d1515117d194915157d352539560821b6044820152606401610cd6565b60405162461bcd60e51b8152602060048201526016602482015275494e56414c49445f5350454349414c5f4d494e545f3160501b6044820152606401610cd6565b60008711611ce35760405162461bcd60e51b8152600401610cd6906142d2565b611cee87873361279e565b336000908152601560205260409020805488019055601854610100900460ff16158015611d1b5750836002145b15611d3a57336000908152601760205260409020805488019055611d68565b60185460ff16158015611d4d5750836001145b15611d68573360009081526016602052604090208054880190555b50506001600a555050505050565b600c546001600160a01b03163314611da05760405162461bcd60e51b8152600401610cd690614161565b6019610f1082826143ab565b606060018054610bde90614127565b601a8054601b54601c54601d54601e805494959394929360ff8084169461010090940416929091906113f590614127565b610f10338383612c5f565b603380546034546035546036546037805494959394929360ff8084169461010090940416929091906113f590614127565b6000805b8251811015611e8b57611e57838281518110611e4a57611e4a614395565b60200260200101516115e5565b6001600160a01b0316846001600160a01b031614611e79576000915050610bc9565b80611e838161446a565b915050611e2c565b5060019392505050565b600c546001600160a01b03163314611ebf5760405162461bcd60e51b8152600401610cd690614161565b6002600a5403611ee15760405162461bcd60e51b8152600401610cd69061429b565b601280546001600160a01b0319166001600160a01b03929092169190911790556001600a55565b600c546001600160a01b03163314611f325760405162461bcd60e51b8152600401610cd690614161565b601455565b611f413383612862565b611f5d5760405162461bcd60e51b8152600401610cd690614344565b61103b84848484612d2d565b60298054602a54602b54602c54602d805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b03163314611fc45760405162461bcd60e51b8152600401610cd690614161565b601055565b6000818152600260205260409020546060906001600160a01b03166120255760405162461bcd60e51b81526020600482015260126024820152711513d2d15397d254d7d393d517d1561254d560721b6044820152606401610cd6565b6000828152601360205260408120805461203e90614127565b905011156120e4576000828152601360205260409020805461205f90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461208b90614127565b80156120d85780601f106120ad576101008083540402835291602001916120d8565b820191906000526020600020905b8154815290600101906020018083116120bb57829003601f168201915b50505050509050919050565b6000606083601a60000154111580156120ff5750601b548411155b156121a157601d54601e805460ff90921693509061211c90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461214890614127565b80156121955780601f1061216a57610100808354040283529160200191612195565b820191906000526020600020905b81548152906001019060200180831161217857829003601f168201915b50505050509050612348565b601f5484108015906121b557506020548411155b156121d2576022546023805460ff90921693509061211c90614127565b60245484108015906121e657506025548411155b15612203576027546028805460ff90921693509061211c90614127565b60295484108015906122175750602a548411155b1561223457602c54602d805460ff90921693509061211c90614127565b602e5484108015906122485750602f548411155b15612265576031546032805460ff90921693509061211c90614127565b603354841080159061227957506034548411155b15612296576036546037805460ff90921693509061211c90614127565b60385484108015906122aa57506039548411155b1561234857603b54603c805460ff9092169350906122c790614127565b80601f01602080910402602001604051908101604052809291908181526020018280546122f390614127565b80156123405780601f1061231557610100808354040283529160200191612340565b820191906000526020600020905b81548152906001019060200180831161232357829003601f168201915b505050505090505b8115612381578061235885612d60565b604051602001612369929190614483565b60405160208183030381529060405292505050919050565b8060405160200161236991906144c2565b602480546025546026546027546028805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b031633146123ed5760405162461bcd60e51b8152600401610cd690614161565b6018805462ffff001916620100009415159490940261ff00191693909317610100921515929092029190911760ff1916901515179055565b600c546001600160a01b0316331461244f5760405162461bcd60e51b8152600401610cd690614161565b8360010361246b57601a839055601b829055601c81905561103b565b8360020361248757601f8390556020829055602181905561103b565b836003036124a35760248390556025829055602681905561103b565b836004036124bf576029839055602a829055602b81905561103b565b836005036124db57602e839055602f829055603081905561103b565b836006036124f75760338390556034829055603581905561103b565b8360070361103b57603892909255603955603a5550565b6000828152600b602052604090206001015461252981612ae0565b610e0b8383612b70565b6013602052600090815260409020805461254c90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461257890614127565b80156125c55780601f1061259a576101008083540402835291602001916125c5565b820191906000526020600020905b8154815290600101906020018083116125a857829003601f168201915b505050505081565b606060198054610bde90614127565b60006126087f4a0c3698e72495f6d49f6ef074f2b34cac5b153c817a7cc37789cccbb873cf5d836119c5565b8061263857506001600160a01b0380841660009081526005602090815260408083209386168352929052205460ff165b9392505050565b60388054603954603a54603b54603c805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b0316331461269a5760405162461bcd60e51b8152600401610cd690614161565b6001600160a01b0381166126ff5760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610cd6565b61270881612bd7565b50565b60006001600160e01b03198216637965db0b60e01b1480610bc95750610bc982612e60565b600081815260046020526040902080546001600160a01b0319166001600160a01b0384169081179091558190612765826115e5565b6001600160a01b03167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a45050565b816001036127b257610e0b83601a83612e85565b816002036127c657610e0b83601f83612e85565b816003036127da57610e0b83602483612e85565b816004036127ee57610e0b83602983612e85565b8160050361280257610e0b83602e83612e85565b8160060361281657610e0b83603383612e85565b8160070361282a57610e0b83603883612e85565b60405162461bcd60e51b815260206004820152600d60248201526c0494e56414c49445f47524f555609c1b6044820152606401610cd6565b6000818152600260205260408120546001600160a01b03166128db5760405162461bcd60e51b815260206004820152602c60248201527f4552433732313a206f70657261746f7220717565727920666f72206e6f6e657860448201526b34b9ba32b73a103a37b5b2b760a11b6064820152608401610cd6565b60006128e6836115e5565b9050806001600160a01b0316846001600160a01b0316148061290d575061290d81856125dc565b806129315750836001600160a01b031661292684610c61565b6001600160a01b0316145b949350505050565b826001600160a01b031661294c826115e5565b6001600160a01b0316146129b05760405162461bcd60e51b815260206004820152602560248201527f4552433732313a207472616e736665722066726f6d20696e636f72726563742060448201526437bbb732b960d91b6064820152608401610cd6565b6001600160a01b038216612a125760405162461bcd60e51b8152602060048201526024808201527f4552433732313a207472616e7366657220746f20746865207a65726f206164646044820152637265737360e01b6064820152608401610cd6565b612a1d838383612f63565b612a28600082612730565b6001600160a01b0383166000908152600360205260408120805460019290612a519084906144de565b90915550506001600160a01b0382166000908152600360205260408120805460019290612a7f908490614331565b909155505060008181526002602052604080822080546001600160a01b0319166001600160a01b0386811691821790925591518493918716917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef91a4505050565b612708813361301b565b612af482826119c5565b610f10576000828152600b602090815260408083206001600160a01b03851684529091529020805460ff19166001179055612b2c3390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b612b7a82826119c5565b15610f10576000828152600b602090815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b600c80546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b610f1082826040518060200160405280600081525061307f565b6000806000612c5285856130b2565b915091506119bd81613120565b816001600160a01b0316836001600160a01b031603612cc05760405162461bcd60e51b815260206004820152601960248201527f4552433732313a20617070726f766520746f2063616c6c6572000000000000006044820152606401610cd6565b6001600160a01b03838116600081815260056020908152604080832094871680845294825291829020805460ff191686151590811790915591519182527f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a3505050565b612d38848484612939565b612d44848484846132d6565b61103b5760405162461bcd60e51b8152600401610cd6906144f1565b606081600003612d875750506040805180820190915260018152600360fc1b602082015290565b8160005b8115612db15780612d9b8161446a565b9150612daa9050600a83614559565b9150612d8b565b6000816001600160401b03811115612dcb57612dcb613cec565b6040519080825280601f01601f191660200182016040528015612df5576020820181803683370190505b5090505b841561293157612e0a6001836144de565b9150612e17600a8661456d565b612e22906030614331565b60f81b818381518110612e3757612e37614395565b60200101906001600160f81b031916908160001a905350612e59600a86614559565b9450612df9565b60006001600160e01b0319821663780e9d6360e01b1480610bc95750610bc9826133d7565b60038201548290610100900460ff1615612ecf5760405162461bcd60e51b815260206004820152600b60248201526a47524f55505f504155534560a81b6044820152606401610cd6565b8054600182015460028301549082900390910190850160001901811015612f2e5760405162461bcd60e51b81526020600482015260136024820152724e4f545f454e4f5547485f535550504c49455360681b6044820152606401610cd6565b60005b85811015612f5b57612f47848460020154612c29565b600283018054600190810190915501612f31565b505050505050565b6001600160a01b038316612fbe57612fb981600880546000838152600960205260408120829055600182018355919091527ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee30155565b612fe1565b816001600160a01b0316836001600160a01b031614612fe157612fe18382613427565b6001600160a01b038216612ff857610e0b816134c4565b826001600160a01b0316826001600160a01b031614610e0b57610e0b8282613573565b61302582826119c5565b610f105761303d816001600160a01b031660146135b7565b6130488360206135b7565b604051602001613059929190614581565b60408051601f198184030181529082905262461bcd60e51b8252610cd691600401613a49565b6130898383613752565b61309660008484846132d6565b610e0b5760405162461bcd60e51b8152600401610cd6906144f1565b60008082516041036130e85760208301516040840151606085015160001a6130dc878285856138a0565b94509450505050613119565b8251604003613111576020830151604084015161310686838361398d565b935093505050613119565b506000905060025b9250929050565b6000816004811115613134576131346145f6565b0361313c5750565b6001816004811115613150576131506145f6565b0361319d5760405162461bcd60e51b815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610cd6565b60028160048111156131b1576131b16145f6565b036131fe5760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610cd6565b6003816004811115613212576132126145f6565b0361326a5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c604482015261756560f01b6064820152608401610cd6565b600481600481111561327e5761327e6145f6565b036127085760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c604482015261756560f01b6064820152608401610cd6565b60006001600160a01b0384163b156133cc57604051630a85bd0160e11b81526001600160a01b0385169063150b7a029061331a90339089908890889060040161460c565b6020604051808303816000875af1925050508015613355575060408051601f3d908101601f1916820190925261335291810190614649565b60015b6133b2573d808015613383576040519150601f19603f3d011682016040523d82523d6000602084013e613388565b606091505b5080516000036133aa5760405162461bcd60e51b8152600401610cd6906144f1565b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050612931565b506001949350505050565b60006001600160e01b031982166380ac58cd60e01b148061340857506001600160e01b03198216635b5e139f60e01b145b80610bc957506301ffc9a760e01b6001600160e01b0319831614610bc9565b600060016134348461172b565b61343e91906144de565b600083815260076020526040902054909150808214613491576001600160a01b03841660009081526006602090815260408083208584528252808320548484528184208190558352600790915290208190555b5060009182526007602090815260408084208490556001600160a01b039094168352600681528383209183525290812055565b6008546000906134d6906001906144de565b600083815260096020526040812054600880549394509092849081106134fe576134fe614395565b90600052602060002001549050806008838154811061351f5761351f614395565b600091825260208083209091019290925582815260099091526040808220849055858252812055600880548061355757613557614666565b6001900381819060005260206000200160009055905550505050565b600061357e8361172b565b6001600160a01b039093166000908152600660209081526040808320868452825280832085905593825260079052919091209190915550565b606060006135c6836002614312565b6135d1906002614331565b6001600160401b038111156135e8576135e8613cec565b6040519080825280601f01601f191660200182016040528015613612576020820181803683370190505b509050600360fc1b8160008151811061362d5761362d614395565b60200101906001600160f81b031916908160001a905350600f60fb1b8160018151811061365c5761365c614395565b60200101906001600160f81b031916908160001a9053506000613680846002614312565b61368b906001614331565b90505b6001811115613703576f181899199a1a9b1b9c1cb0b131b232b360811b85600f16601081106136bf576136bf614395565b1a60f81b8282815181106136d5576136d5614395565b60200101906001600160f81b031916908160001a90535060049490941c936136fc8161467c565b905061368e565b5083156126385760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e746044820152606401610cd6565b6001600160a01b0382166137a85760405162461bcd60e51b815260206004820181905260248201527f4552433732313a206d696e7420746f20746865207a65726f20616464726573736044820152606401610cd6565b6000818152600260205260409020546001600160a01b03161561380d5760405162461bcd60e51b815260206004820152601c60248201527f4552433732313a20746f6b656e20616c7265616479206d696e746564000000006044820152606401610cd6565b61381960008383612f63565b6001600160a01b0382166000908152600360205260408120805460019290613842908490614331565b909155505060008181526002602052604080822080546001600160a01b0319166001600160a01b03861690811790915590518392907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a45050565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a08311156138d75750600090506003613984565b8460ff16601b141580156138ef57508460ff16601c14155b156139005750600090506004613984565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015613954573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b03811661397d57600060019250925050613984565b9150600090505b94509492505050565b6000806001600160ff1b038316816139aa60ff86901c601b614331565b90506139b8878288856138a0565b935093505050935093915050565b6001600160e01b03198116811461270857600080fd5b6000602082840312156139ee57600080fd5b8135612638816139c6565b60005b83811015613a145781810151838201526020016139fc565b50506000910152565b60008151808452613a358160208601602086016139f9565b601f01601f19169290920160200192915050565b6020815260006126386020830184613a1d565b600060208284031215613a6e57600080fd5b5035919050565b80356001600160a01b0381168114613a8c57600080fd5b919050565b60008060408385031215613aa457600080fd5b613aad83613a75565b946020939093013593505050565b80358015158114613a8c57600080fd5b60008060408385031215613ade57600080fd5b82359150613aee60208401613abb565b90509250929050565b60008083601f840112613b0957600080fd5b5081356001600160401b03811115613b2057600080fd5b60208301915083602082850101111561311957600080fd5b60008060008060608587031215613b4e57600080fd5b84359350613b5e60208601613abb565b925060408501356001600160401b03811115613b7957600080fd5b613b8587828801613af7565b95989497509550505050565b60008060408385031215613ba457600080fd5b50508035926020909101359150565b600080600060608486031215613bc857600080fd5b613bd184613a75565b9250613bdf60208501613a75565b9150604084013590509250925092565b60008060408385031215613c0257600080fd5b82359150613aee60208401613a75565b8681528560208201528460408201528315156060820152821515608082015260c060a08201526000613c4760c0830184613a1d565b98975050505050505050565b600060208284031215613c6557600080fd5b61263882613a75565b600080600060408486031215613c8357600080fd5b8335925060208401356001600160401b03811115613ca057600080fd5b613cac86828701613af7565b9497909650939450505050565b600080600060608486031215613cce57600080fd5b613cd784613a75565b95602085013595506040909401359392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715613d2a57613d2a613cec565b604052919050565b60006001600160401b03821115613d4b57613d4b613cec565b5060051b60200190565b600082601f830112613d6657600080fd5b81356001600160401b03811115613d7f57613d7f613cec565b613d92601f8201601f1916602001613d02565b818152846020838601011115613da757600080fd5b816020850160208301376000918101602001919091529392505050565b60006020808385031215613dd757600080fd5b82356001600160401b0380821115613dee57600080fd5b818501915085601f830112613e0257600080fd5b8135613e15613e1082613d32565b613d02565b81815260059190911b83018401908481019088831115613e3457600080fd5b8585015b83811015613e6c57803585811115613e505760008081fd5b613e5e8b89838a0101613d55565b845250918601918601613e38565b5098975050505050505050565b6020808252825182820181905260009190848201906040850190845b81811015613eb157835183529284019291840191600101613e95565b50909695505050505050565b600080600080600060a08688031215613ed557600080fd5b8535945060208601359350604086013592506060860135915060808601356001600160401b03811115613f0757600080fd5b613f1388828901613d55565b9150509295509295909350565b600060208284031215613f3257600080fd5b81356001600160401b03811115613f4857600080fd5b61293184828501613d55565b60008060408385031215613f6757600080fd5b613f7083613a75565b9150613aee60208401613abb565b60008060408385031215613f9157600080fd5b613f9a83613a75565b91506020808401356001600160401b03811115613fb657600080fd5b8401601f81018613613fc757600080fd5b8035613fd5613e1082613d32565b81815260059190911b82018301908381019088831115613ff457600080fd5b928401925b8284101561401257833582529284019290840190613ff9565b80955050505050509250929050565b6000806000806080858703121561403757600080fd5b61404085613a75565b935061404e60208601613a75565b92506040850135915060608501356001600160401b0381111561407057600080fd5b61407c87828801613d55565b91505092959194509250565b60008060006060848603121561409d57600080fd5b6140a684613abb565b92506140b460208501613abb565b91506140c260408501613abb565b90509250925092565b600080600080608085870312156140e157600080fd5b5050823594602084013594506040840135936060013592509050565b6000806040838503121561411057600080fd5b61411983613a75565b9150613aee60208401613a75565b600181811c9082168061413b57607f821691505b60208210810361415b57634e487b7160e01b600052602260045260246000fd5b50919050565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b601f821115610e0b57600081815260208120601f850160051c810160208610156141bd5750805b601f850160051c820191505b81811015612f5b578281556001016141c9565b6001600160401b038311156141f3576141f3613cec565b614207836142018354614127565b83614196565b6000601f84116001811461423b57600085156142235750838201355b600019600387901b1c1916600186901b178355611039565b600083815260209020601f19861690835b8281101561426c578685013582556020948501946001909201910161424c565b50868210156142895760001960f88860031b161c19848701351681555b505060018560011b0183555050505050565b6020808252601f908201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604082015260600190565b60208082526010908201526f494e56414c49445f5155414e5449545960801b604082015260600190565b634e487b7160e01b600052601160045260246000fd5b600081600019048311821515161561432c5761432c6142fc565b500290565b80820180821115610bc957610bc96142fc565b60208082526031908201527f4552433732313a207472616e736665722063616c6c6572206973206e6f74206f6040820152701ddb995c881b9bdc88185c1c1c9bdd9959607a1b606082015260800190565b634e487b7160e01b600052603260045260246000fd5b81516001600160401b038111156143c4576143c4613cec565b6143d8816143d28454614127565b84614196565b602080601f83116001811461440d57600084156143f55750858301515b600019600386901b1c1916600185901b178555612f5b565b600085815260208120601f198616915b8281101561443c5788860151825594840194600190910190840161441d565b508582101561445a5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b60006001820161447c5761447c6142fc565b5060010190565b600083516144958184602088016139f9565b8351908301906144a98183602088016139f9565b64173539b7b760d91b9101908152600501949350505050565b600082516144d48184602087016139f9565b9190910192915050565b81810381811115610bc957610bc96142fc565b60208082526032908201527f4552433732313a207472616e7366657220746f206e6f6e20455243373231526560408201527131b2b4bb32b91034b6b83632b6b2b73a32b960711b606082015260800190565b634e487b7160e01b600052601260045260246000fd5b60008261456857614568614543565b500490565b60008261457c5761457c614543565b500690565b7f416363657373436f6e74726f6c3a206163636f756e74200000000000000000008152600083516145b98160178501602088016139f9565b7001034b99036b4b9b9b4b733903937b6329607d1b60179184019182015283516145ea8160288401602088016139f9565b01602801949350505050565b634e487b7160e01b600052602160045260246000fd5b6001600160a01b038581168252841660208201526040810183905260806060820181905260009061463f90830184613a1d565b9695505050505050565b60006020828403121561465b57600080fd5b8151612638816139c6565b634e487b7160e01b600052603160045260246000fd5b60008161468b5761468b6142fc565b50600019019056fea26469706673582212206988be08ea1530646aaea37855dfbb18943d4326bede86f2160a9ddd45e939d664736f6c63430008100033697066733a2f2f6261666b7265696675636b6c6463727a6c377962656b356164776e656275667a347932706e357a3579373376346661796d6d7a6e796f746d656c79697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f362e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f312e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f352e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f322e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f372e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f342e6a736f6e697066733a2f2f626166796265696270346572366c6b3663766d346a79766c61347869637936736162677468746d767365647476706e323334776f627133773670612f332e6a736f6e

Deployed Bytecode

0x6080604052600436106103ce5760003560e01c80638462151c116101fd578063b88d4fde11610118578063d547741f116100ab578063e985e9c51161007a578063e985e9c514610b03578063eceaf40014610b23578063edf5354c14610b42578063f0293fd314610b57578063f2fde38b14610b8457600080fd5b8063d547741f14610a8e578063d6de205e14610aae578063daaa09a414610ace578063e8a3d48514610aee57600080fd5b8063c87b56dd116100e7578063c87b56dd14610a19578063c919578114610a39578063cc2abd6414610a4e578063d27bbe7914610a6e57600080fd5b8063b88d4fde146109ae578063bd370b3e146109ce578063c19fb568146109e3578063c7e9d141146109f957600080fd5b80639ff5a24b11610190578063a67b4bbb1161015f578063a67b4bbb14610938578063ac1a386a14610958578063afdf613414610978578063b228d9251461099857600080fd5b80639ff5a24b146108d9578063a217fddf146108ee578063a22cb46514610903578063a597106f1461092357600080fd5b80639257e044116101cc5780639257e0441461087b5780639382699214610891578063938e3d7b146108a457806395d89b41146108c457600080fd5b80638462151c146107fb5780638da5cb5b1461082857806391d14854146108465780639255d5681461086657600080fd5b80633ccfd60b116102ed5780636352211e116102805780636d41d4fb1161024f5780636d41d4fb1461077957806370a08231146107a6578063715018a6146107c6578063819d7c63146107db57600080fd5b80636352211e146106f957806369ec2f09146107195780636ad5b3ea146107395780636c19e7831461075957600080fd5b806349071a2b116102bc57806349071a2b146106765780634f6ccce71461068c5780635d655285146106ac5780635e58a509146106d957600080fd5b80633ccfd60b146105fa57806342842e0e1461060f57806343bfbe7c1461062f57806344a0d68a1461065657600080fd5b8063197db9c811610365578063248a9ca311610334578063248a9ca31461056a5780632f2ff15d1461059a5780632f745c59146105ba57806336568abe146105da57600080fd5b8063197db9c8146104f75780631b2ef1ca14610517578063238ac9331461052a57806323b872dd1461054a57600080fd5b8063095ea7b3116103a1578063095ea7b31461047c57806312653a341461049e57806313faede6146104be57806318160ddd146104e257600080fd5b806301ffc9a7146103d357806303a3c2221461040857806306fdde0314610422578063081812fc14610444575b600080fd5b3480156103df57600080fd5b506103f36103ee3660046139dc565b610ba4565b60405190151581526020015b60405180910390f35b34801561041457600080fd5b506018546103f39060ff1681565b34801561042e57600080fd5b50610437610bcf565b6040516103ff9190613a49565b34801561045057600080fd5b5061046461045f366004613a5c565b610c61565b6040516001600160a01b0390911681526020016103ff565b34801561048857600080fd5b5061049c610497366004613a91565b610cfb565b005b3480156104aa57600080fd5b5061049c6104b9366004613acb565b610e10565b3480156104ca57600080fd5b506104d4600f5481565b6040519081526020016103ff565b3480156104ee57600080fd5b506008546104d4565b34801561050357600080fd5b5061049c610512366004613b38565b610f14565b61049c610525366004613b91565b611041565b34801561053657600080fd5b50601154610464906001600160a01b031681565b34801561055657600080fd5b5061049c610565366004613bb3565b6111b1565b34801561057657600080fd5b506104d4610585366004613a5c565b6000908152600b602052604090206001015490565b3480156105a657600080fd5b5061049c6105b5366004613bef565b6111e2565b3480156105c657600080fd5b506104d46105d5366004613a91565b611207565b3480156105e657600080fd5b5061049c6105f5366004613bef565b61129d565b34801561060657600080fd5b5061049c611317565b34801561061b57600080fd5b5061049c61062a366004613bb3565b6113a9565b34801561063b57600080fd5b506106446113c4565b6040516103ff96959493929190613c12565b34801561066257600080fd5b5061049c610671366004613a5c565b611478565b34801561068257600080fd5b506104d4600d5481565b34801561069857600080fd5b506104d46106a7366004613a5c565b6114a7565b3480156106b857600080fd5b506104d46106c7366004613c53565b60176020526000908152604090205481565b3480156106e557600080fd5b5061049c6106f4366004613c6e565b61153a565b34801561070557600080fd5b50610464610714366004613a5c565b6115e5565b34801561072557600080fd5b5061049c610734366004613cb9565b61165c565b34801561074557600080fd5b50601254610464906001600160a01b031681565b34801561076557600080fd5b5061049c610774366004613c53565b6116df565b34801561078557600080fd5b506104d4610794366004613c53565b60166020526000908152604090205481565b3480156107b257600080fd5b506104d46107c1366004613c53565b61172b565b3480156107d257600080fd5b5061049c6117b2565b3480156107e757600080fd5b5061049c6107f6366004613dc4565b6117e8565b34801561080757600080fd5b5061081b610816366004613c53565b611924565b6040516103ff9190613e79565b34801561083457600080fd5b50600c546001600160a01b0316610464565b34801561085257600080fd5b506103f3610861366004613bef565b6119c5565b34801561087257600080fd5b506106446119f0565b34801561088757600080fd5b506104d460105481565b61049c61089f366004613ebd565b611a21565b3480156108b057600080fd5b5061049c6108bf366004613f20565b611d76565b3480156108d057600080fd5b50610437611dac565b3480156108e557600080fd5b50610644611dbb565b3480156108fa57600080fd5b506104d4600081565b34801561090f57600080fd5b5061049c61091e366004613f54565b611dec565b34801561092f57600080fd5b50610644611df7565b34801561094457600080fd5b506103f3610953366004613f7e565b611e28565b34801561096457600080fd5b5061049c610973366004613c53565b611e95565b34801561098457600080fd5b5061049c610993366004613a5c565b611f08565b3480156109a457600080fd5b506104d460145481565b3480156109ba57600080fd5b5061049c6109c9366004614021565b611f37565b3480156109da57600080fd5b50610644611f69565b3480156109ef57600080fd5b506104d4600e5481565b348015610a0557600080fd5b5061049c610a14366004613a5c565b611f9a565b348015610a2557600080fd5b50610437610a34366004613a5c565b611fc9565b348015610a4557600080fd5b50610644612392565b348015610a5a57600080fd5b5061049c610a69366004614088565b6123c3565b348015610a7a57600080fd5b5061049c610a893660046140cb565b612425565b348015610a9a57600080fd5b5061049c610aa9366004613bef565b61250e565b348015610aba57600080fd5b50610437610ac9366004613a5c565b612533565b348015610ada57600080fd5b506018546103f39062010000900460ff1681565b348015610afa57600080fd5b506104376125cd565b348015610b0f57600080fd5b506103f3610b1e3660046140fd565b6125dc565b348015610b2f57600080fd5b506018546103f390610100900460ff1681565b348015610b4e57600080fd5b5061064461263f565b348015610b6357600080fd5b506104d4610b72366004613c53565b60156020526000908152604090205481565b348015610b9057600080fd5b5061049c610b9f366004613c53565b612670565b60006001600160e01b03198216635b5e139f60e01b1480610bc95750610bc98261270b565b92915050565b606060008054610bde90614127565b80601f0160208091040260200160405190810160405280929190818152602001828054610c0a90614127565b8015610c575780601f10610c2c57610100808354040283529160200191610c57565b820191906000526020600020905b815481529060010190602001808311610c3a57829003601f168201915b5050505050905090565b6000818152600260205260408120546001600160a01b0316610cdf5760405162461bcd60e51b815260206004820152602c60248201527f4552433732313a20617070726f76656420717565727920666f72206e6f6e657860448201526b34b9ba32b73a103a37b5b2b760a11b60648201526084015b60405180910390fd5b506000908152600460205260409020546001600160a01b031690565b6000610d06826115e5565b9050806001600160a01b0316836001600160a01b031603610d735760405162461bcd60e51b815260206004820152602160248201527f4552433732313a20617070726f76616c20746f2063757272656e74206f776e656044820152603960f91b6064820152608401610cd6565b336001600160a01b0382161480610d8f5750610d8f81336125dc565b610e015760405162461bcd60e51b815260206004820152603860248201527f4552433732313a20617070726f76652063616c6c6572206973206e6f74206f7760448201527f6e6572206e6f7220617070726f76656420666f7220616c6c00000000000000006064820152608401610cd6565b610e0b8383612730565b505050565b600c546001600160a01b03163314610e3a5760405162461bcd60e51b8152600401610cd690614161565b81600103610e5957601d805461ff001916610100831515021790555050565b81600203610e78576022805461ff001916610100831515021790555050565b81600303610e97576027805461ff001916610100831515021790555050565b81600403610eb657602c805461ff001916610100831515021790555050565b81600503610ed5576031805461ff001916610100831515021790555050565b81600603610ef4576036805461ff001916610100831515021790555050565b81600703610f1057603b805461ff001916610100831515021790555b5050565b600c546001600160a01b03163314610f3e5760405162461bcd60e51b8152600401610cd690614161565b83600103610f6757601d805460ff1916841515179055601e610f618284836141dc565b5061103b565b83600203610f8a576022805460ff19168415151790556023610f618284836141dc565b83600303610fad576027805460ff19168415151790556028610f618284836141dc565b83600403610fd057602c805460ff1916841515179055602d610f618284836141dc565b83600503610ff3576031805460ff19168415151790556032610f618284836141dc565b83600603611016576036805460ff19168415151790556037610f618284836141dc565b8360070361103b57603b805460ff1916841515179055603c6110398284836141dc565b505b50505050565b6002600a54036110635760405162461bcd60e51b8152600401610cd69061429b565b6002600a5560185462010000900460ff16156110b65760405162461bcd60e51b8152602060048201526012602482015271141550931250d7d352539517d4105554d15160721b6044820152606401610cd6565b600082116110d65760405162461bcd60e51b8152600401610cd6906142d2565b81600f546110e49190614312565b3410156111235760405162461bcd60e51b815260206004820152600d60248201526c494e56414c49445f56414c554560981b6044820152606401610cd6565b60145433600090815260156020526040902054611141908490614331565b11156111885760405162461bcd60e51b8152602060048201526016602482015275115610d1515117d352539517d4115497d5d05313115560521b6044820152606401610cd6565b61119382823361279e565b50336000908152601560205260409020805490910190556001600a55565b6111bb3382612862565b6111d75760405162461bcd60e51b8152600401610cd690614344565b610e0b838383612939565b6000828152600b60205260409020600101546111fd81612ae0565b610e0b8383612aea565b60006112128361172b565b82106112745760405162461bcd60e51b815260206004820152602b60248201527f455243373231456e756d657261626c653a206f776e657220696e646578206f7560448201526a74206f6620626f756e647360a81b6064820152608401610cd6565b506001600160a01b03919091166000908152600660209081526040808320938352929052205490565b6001600160a01b038116331461130d5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b6064820152608401610cd6565b610f108282612b70565b600c546001600160a01b031633146113415760405162461bcd60e51b8152600401610cd690614161565b6002600a54036113635760405162461bcd60e51b8152600401610cd69061429b565b6002600a556012546040516001600160a01b03909116904780156108fc02916000818181858888f193505050501580156113a1573d6000803e3d6000fd5b506001600a55565b610e0b83838360405180602001604052806000815250611f37565b602e8054602f546030546031546032805494959394929360ff8084169461010090940416929091906113f590614127565b80601f016020809104026020016040519081016040528092919081815260200182805461142190614127565b801561146e5780601f106114435761010080835404028352916020019161146e565b820191906000526020600020905b81548152906001019060200180831161145157829003601f168201915b5050505050905086565b600c546001600160a01b031633146114a25760405162461bcd60e51b8152600401610cd690614161565b600f55565b60006114b260085490565b82106115155760405162461bcd60e51b815260206004820152602c60248201527f455243373231456e756d657261626c653a20676c6f62616c20696e646578206f60448201526b7574206f6620626f756e647360a01b6064820152608401610cd6565b6008828154811061152857611528614395565b90600052602060002001549050919050565b600c546001600160a01b031633146115645760405162461bcd60e51b8152600401610cd690614161565b6000838152601360205260408120805461157d90614127565b9050116115cc5760405162461bcd60e51b815260206004820152601860248201527f494e56414c49445f504152544e45525f544f4b454e5f494400000000000000006044820152606401610cd6565b600083815260136020526040902061103b8284836141dc565b6000818152600260205260408120546001600160a01b031680610bc95760405162461bcd60e51b815260206004820152602960248201527f4552433732313a206f776e657220717565727920666f72206e6f6e657869737460448201526832b73a103a37b5b2b760b91b6064820152608401610cd6565b600c546001600160a01b031633146116865760405162461bcd60e51b8152600401610cd690614161565b6002600a54036116a85760405162461bcd60e51b8152600401610cd69061429b565b6002600a55816116ca5760405162461bcd60e51b8152600401610cd6906142d2565b6116d582828561279e565b50506001600a5550565b600c546001600160a01b031633146117095760405162461bcd60e51b8152600401610cd690614161565b601180546001600160a01b0319166001600160a01b0392909216919091179055565b60006001600160a01b0382166117965760405162461bcd60e51b815260206004820152602a60248201527f4552433732313a2062616c616e636520717565727920666f7220746865207a65604482015269726f206164647265737360b01b6064820152608401610cd6565b506001600160a01b031660009081526003602052604090205490565b600c546001600160a01b031633146117dc5760405162461bcd60e51b8152600401610cd690614161565b6117e66000612bd7565b565b600c546001600160a01b031633146118125760405162461bcd60e51b8152600401610cd690614161565b80516000106118545760405162461bcd60e51b815260206004820152600e60248201526d0929cac82989288be988a9c8ea8960931b6044820152606401610cd6565b60005b8151811015610f1057600082828151811061187457611874614395565b602002602001015151116118b95760405162461bcd60e51b815260206004820152600c60248201526b52455155495245445f55524960a01b6044820152606401610cd6565b8181815181106118cb576118cb614395565b602002602001015160136000600e54815260200190815260200160002090816118f491906143ab565b5061191261190a600c546001600160a01b031690565b600e54612c29565b600e8054600190810190915501611857565b606060006119318361172b565b90506000816001600160401b0381111561194d5761194d613cec565b604051908082528060200260200182016040528015611976578160200160208202803683370190505b50905060005b828110156119bd5761198e8582611207565b8282815181106119a0576119a0614395565b6020908102919091010152806119b58161446a565b91505061197c565b509392505050565b6000918252600b602090815260408084206001600160a01b0393909316845291905290205460ff1690565b601f80546020546021546022546023805494959394929360ff8084169461010090940416929091906113f590614127565b6002600a5403611a435760405162461bcd60e51b8152600401610cd69061429b565b6002600a556040805160208082018590523360601b6bffffffffffffffffffffffff1916828401526054808301879052835180840390910181526074830184528051908201207f19457468657265756d205369676e6564204d6573736167653a0a333200000000609484015260b08084018290528451808503909101815260d090930190935281519101206011546001600160a01b0316611ae48285612c43565b6001600160a01b031614611b3a5760405162461bcd60e51b815260206004820152601960248201527f434f4e54524143545f4d494e545f4e4f545f414c4c4f574544000000000000006044820152606401610cd6565b601854610100900460ff16158015611b525750836002145b15611c0c5786601054611b659190614312565b341015611ba45760405162461bcd60e51b815260206004820152600d60248201526c494e56414c49445f56414c554560981b6044820152606401610cd6565b336000908152601760205260409020548590611bc1908990614331565b1115611c075760405162461bcd60e51b8152602060048201526015602482015274115610d1515117d5d2125511531254d517d3525395605a1b6044820152606401610cd6565b611cc3565b60185460ff16158015611c1f5750836001145b15611c8257336000908152601660205260409020548590611c41908990614331565b1115611c075760405162461bcd60e51b815260206004820152601060248201526f115610d1515117d194915157d352539560821b6044820152606401610cd6565b60405162461bcd60e51b8152602060048201526016602482015275494e56414c49445f5350454349414c5f4d494e545f3160501b6044820152606401610cd6565b60008711611ce35760405162461bcd60e51b8152600401610cd6906142d2565b611cee87873361279e565b336000908152601560205260409020805488019055601854610100900460ff16158015611d1b5750836002145b15611d3a57336000908152601760205260409020805488019055611d68565b60185460ff16158015611d4d5750836001145b15611d68573360009081526016602052604090208054880190555b50506001600a555050505050565b600c546001600160a01b03163314611da05760405162461bcd60e51b8152600401610cd690614161565b6019610f1082826143ab565b606060018054610bde90614127565b601a8054601b54601c54601d54601e805494959394929360ff8084169461010090940416929091906113f590614127565b610f10338383612c5f565b603380546034546035546036546037805494959394929360ff8084169461010090940416929091906113f590614127565b6000805b8251811015611e8b57611e57838281518110611e4a57611e4a614395565b60200260200101516115e5565b6001600160a01b0316846001600160a01b031614611e79576000915050610bc9565b80611e838161446a565b915050611e2c565b5060019392505050565b600c546001600160a01b03163314611ebf5760405162461bcd60e51b8152600401610cd690614161565b6002600a5403611ee15760405162461bcd60e51b8152600401610cd69061429b565b601280546001600160a01b0319166001600160a01b03929092169190911790556001600a55565b600c546001600160a01b03163314611f325760405162461bcd60e51b8152600401610cd690614161565b601455565b611f413383612862565b611f5d5760405162461bcd60e51b8152600401610cd690614344565b61103b84848484612d2d565b60298054602a54602b54602c54602d805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b03163314611fc45760405162461bcd60e51b8152600401610cd690614161565b601055565b6000818152600260205260409020546060906001600160a01b03166120255760405162461bcd60e51b81526020600482015260126024820152711513d2d15397d254d7d393d517d1561254d560721b6044820152606401610cd6565b6000828152601360205260408120805461203e90614127565b905011156120e4576000828152601360205260409020805461205f90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461208b90614127565b80156120d85780601f106120ad576101008083540402835291602001916120d8565b820191906000526020600020905b8154815290600101906020018083116120bb57829003601f168201915b50505050509050919050565b6000606083601a60000154111580156120ff5750601b548411155b156121a157601d54601e805460ff90921693509061211c90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461214890614127565b80156121955780601f1061216a57610100808354040283529160200191612195565b820191906000526020600020905b81548152906001019060200180831161217857829003601f168201915b50505050509050612348565b601f5484108015906121b557506020548411155b156121d2576022546023805460ff90921693509061211c90614127565b60245484108015906121e657506025548411155b15612203576027546028805460ff90921693509061211c90614127565b60295484108015906122175750602a548411155b1561223457602c54602d805460ff90921693509061211c90614127565b602e5484108015906122485750602f548411155b15612265576031546032805460ff90921693509061211c90614127565b603354841080159061227957506034548411155b15612296576036546037805460ff90921693509061211c90614127565b60385484108015906122aa57506039548411155b1561234857603b54603c805460ff9092169350906122c790614127565b80601f01602080910402602001604051908101604052809291908181526020018280546122f390614127565b80156123405780601f1061231557610100808354040283529160200191612340565b820191906000526020600020905b81548152906001019060200180831161232357829003601f168201915b505050505090505b8115612381578061235885612d60565b604051602001612369929190614483565b60405160208183030381529060405292505050919050565b8060405160200161236991906144c2565b602480546025546026546027546028805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b031633146123ed5760405162461bcd60e51b8152600401610cd690614161565b6018805462ffff001916620100009415159490940261ff00191693909317610100921515929092029190911760ff1916901515179055565b600c546001600160a01b0316331461244f5760405162461bcd60e51b8152600401610cd690614161565b8360010361246b57601a839055601b829055601c81905561103b565b8360020361248757601f8390556020829055602181905561103b565b836003036124a35760248390556025829055602681905561103b565b836004036124bf576029839055602a829055602b81905561103b565b836005036124db57602e839055602f829055603081905561103b565b836006036124f75760338390556034829055603581905561103b565b8360070361103b57603892909255603955603a5550565b6000828152600b602052604090206001015461252981612ae0565b610e0b8383612b70565b6013602052600090815260409020805461254c90614127565b80601f016020809104026020016040519081016040528092919081815260200182805461257890614127565b80156125c55780601f1061259a576101008083540402835291602001916125c5565b820191906000526020600020905b8154815290600101906020018083116125a857829003601f168201915b505050505081565b606060198054610bde90614127565b60006126087f4a0c3698e72495f6d49f6ef074f2b34cac5b153c817a7cc37789cccbb873cf5d836119c5565b8061263857506001600160a01b0380841660009081526005602090815260408083209386168352929052205460ff165b9392505050565b60388054603954603a54603b54603c805494959394929360ff8084169461010090940416929091906113f590614127565b600c546001600160a01b0316331461269a5760405162461bcd60e51b8152600401610cd690614161565b6001600160a01b0381166126ff5760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610cd6565b61270881612bd7565b50565b60006001600160e01b03198216637965db0b60e01b1480610bc95750610bc982612e60565b600081815260046020526040902080546001600160a01b0319166001600160a01b0384169081179091558190612765826115e5565b6001600160a01b03167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a45050565b816001036127b257610e0b83601a83612e85565b816002036127c657610e0b83601f83612e85565b816003036127da57610e0b83602483612e85565b816004036127ee57610e0b83602983612e85565b8160050361280257610e0b83602e83612e85565b8160060361281657610e0b83603383612e85565b8160070361282a57610e0b83603883612e85565b60405162461bcd60e51b815260206004820152600d60248201526c0494e56414c49445f47524f555609c1b6044820152606401610cd6565b6000818152600260205260408120546001600160a01b03166128db5760405162461bcd60e51b815260206004820152602c60248201527f4552433732313a206f70657261746f7220717565727920666f72206e6f6e657860448201526b34b9ba32b73a103a37b5b2b760a11b6064820152608401610cd6565b60006128e6836115e5565b9050806001600160a01b0316846001600160a01b0316148061290d575061290d81856125dc565b806129315750836001600160a01b031661292684610c61565b6001600160a01b0316145b949350505050565b826001600160a01b031661294c826115e5565b6001600160a01b0316146129b05760405162461bcd60e51b815260206004820152602560248201527f4552433732313a207472616e736665722066726f6d20696e636f72726563742060448201526437bbb732b960d91b6064820152608401610cd6565b6001600160a01b038216612a125760405162461bcd60e51b8152602060048201526024808201527f4552433732313a207472616e7366657220746f20746865207a65726f206164646044820152637265737360e01b6064820152608401610cd6565b612a1d838383612f63565b612a28600082612730565b6001600160a01b0383166000908152600360205260408120805460019290612a519084906144de565b90915550506001600160a01b0382166000908152600360205260408120805460019290612a7f908490614331565b909155505060008181526002602052604080822080546001600160a01b0319166001600160a01b0386811691821790925591518493918716917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef91a4505050565b612708813361301b565b612af482826119c5565b610f10576000828152600b602090815260408083206001600160a01b03851684529091529020805460ff19166001179055612b2c3390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b612b7a82826119c5565b15610f10576000828152600b602090815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b600c80546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b610f1082826040518060200160405280600081525061307f565b6000806000612c5285856130b2565b915091506119bd81613120565b816001600160a01b0316836001600160a01b031603612cc05760405162461bcd60e51b815260206004820152601960248201527f4552433732313a20617070726f766520746f2063616c6c6572000000000000006044820152606401610cd6565b6001600160a01b03838116600081815260056020908152604080832094871680845294825291829020805460ff191686151590811790915591519182527f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a3505050565b612d38848484612939565b612d44848484846132d6565b61103b5760405162461bcd60e51b8152600401610cd6906144f1565b606081600003612d875750506040805180820190915260018152600360fc1b602082015290565b8160005b8115612db15780612d9b8161446a565b9150612daa9050600a83614559565b9150612d8b565b6000816001600160401b03811115612dcb57612dcb613cec565b6040519080825280601f01601f191660200182016040528015612df5576020820181803683370190505b5090505b841561293157612e0a6001836144de565b9150612e17600a8661456d565b612e22906030614331565b60f81b818381518110612e3757612e37614395565b60200101906001600160f81b031916908160001a905350612e59600a86614559565b9450612df9565b60006001600160e01b0319821663780e9d6360e01b1480610bc95750610bc9826133d7565b60038201548290610100900460ff1615612ecf5760405162461bcd60e51b815260206004820152600b60248201526a47524f55505f504155534560a81b6044820152606401610cd6565b8054600182015460028301549082900390910190850160001901811015612f2e5760405162461bcd60e51b81526020600482015260136024820152724e4f545f454e4f5547485f535550504c49455360681b6044820152606401610cd6565b60005b85811015612f5b57612f47848460020154612c29565b600283018054600190810190915501612f31565b505050505050565b6001600160a01b038316612fbe57612fb981600880546000838152600960205260408120829055600182018355919091527ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee30155565b612fe1565b816001600160a01b0316836001600160a01b031614612fe157612fe18382613427565b6001600160a01b038216612ff857610e0b816134c4565b826001600160a01b0316826001600160a01b031614610e0b57610e0b8282613573565b61302582826119c5565b610f105761303d816001600160a01b031660146135b7565b6130488360206135b7565b604051602001613059929190614581565b60408051601f198184030181529082905262461bcd60e51b8252610cd691600401613a49565b6130898383613752565b61309660008484846132d6565b610e0b5760405162461bcd60e51b8152600401610cd6906144f1565b60008082516041036130e85760208301516040840151606085015160001a6130dc878285856138a0565b94509450505050613119565b8251604003613111576020830151604084015161310686838361398d565b935093505050613119565b506000905060025b9250929050565b6000816004811115613134576131346145f6565b0361313c5750565b6001816004811115613150576131506145f6565b0361319d5760405162461bcd60e51b815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610cd6565b60028160048111156131b1576131b16145f6565b036131fe5760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610cd6565b6003816004811115613212576132126145f6565b0361326a5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c604482015261756560f01b6064820152608401610cd6565b600481600481111561327e5761327e6145f6565b036127085760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c604482015261756560f01b6064820152608401610cd6565b60006001600160a01b0384163b156133cc57604051630a85bd0160e11b81526001600160a01b0385169063150b7a029061331a90339089908890889060040161460c565b6020604051808303816000875af1925050508015613355575060408051601f3d908101601f1916820190925261335291810190614649565b60015b6133b2573d808015613383576040519150601f19603f3d011682016040523d82523d6000602084013e613388565b606091505b5080516000036133aa5760405162461bcd60e51b8152600401610cd6906144f1565b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050612931565b506001949350505050565b60006001600160e01b031982166380ac58cd60e01b148061340857506001600160e01b03198216635b5e139f60e01b145b80610bc957506301ffc9a760e01b6001600160e01b0319831614610bc9565b600060016134348461172b565b61343e91906144de565b600083815260076020526040902054909150808214613491576001600160a01b03841660009081526006602090815260408083208584528252808320548484528184208190558352600790915290208190555b5060009182526007602090815260408084208490556001600160a01b039094168352600681528383209183525290812055565b6008546000906134d6906001906144de565b600083815260096020526040812054600880549394509092849081106134fe576134fe614395565b90600052602060002001549050806008838154811061351f5761351f614395565b600091825260208083209091019290925582815260099091526040808220849055858252812055600880548061355757613557614666565b6001900381819060005260206000200160009055905550505050565b600061357e8361172b565b6001600160a01b039093166000908152600660209081526040808320868452825280832085905593825260079052919091209190915550565b606060006135c6836002614312565b6135d1906002614331565b6001600160401b038111156135e8576135e8613cec565b6040519080825280601f01601f191660200182016040528015613612576020820181803683370190505b509050600360fc1b8160008151811061362d5761362d614395565b60200101906001600160f81b031916908160001a905350600f60fb1b8160018151811061365c5761365c614395565b60200101906001600160f81b031916908160001a9053506000613680846002614312565b61368b906001614331565b90505b6001811115613703576f181899199a1a9b1b9c1cb0b131b232b360811b85600f16601081106136bf576136bf614395565b1a60f81b8282815181106136d5576136d5614395565b60200101906001600160f81b031916908160001a90535060049490941c936136fc8161467c565b905061368e565b5083156126385760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e746044820152606401610cd6565b6001600160a01b0382166137a85760405162461bcd60e51b815260206004820181905260248201527f4552433732313a206d696e7420746f20746865207a65726f20616464726573736044820152606401610cd6565b6000818152600260205260409020546001600160a01b03161561380d5760405162461bcd60e51b815260206004820152601c60248201527f4552433732313a20746f6b656e20616c7265616479206d696e746564000000006044820152606401610cd6565b61381960008383612f63565b6001600160a01b0382166000908152600360205260408120805460019290613842908490614331565b909155505060008181526002602052604080822080546001600160a01b0319166001600160a01b03861690811790915590518392907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a45050565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a08311156138d75750600090506003613984565b8460ff16601b141580156138ef57508460ff16601c14155b156139005750600090506004613984565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015613954573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b03811661397d57600060019250925050613984565b9150600090505b94509492505050565b6000806001600160ff1b038316816139aa60ff86901c601b614331565b90506139b8878288856138a0565b935093505050935093915050565b6001600160e01b03198116811461270857600080fd5b6000602082840312156139ee57600080fd5b8135612638816139c6565b60005b83811015613a145781810151838201526020016139fc565b50506000910152565b60008151808452613a358160208601602086016139f9565b601f01601f19169290920160200192915050565b6020815260006126386020830184613a1d565b600060208284031215613a6e57600080fd5b5035919050565b80356001600160a01b0381168114613a8c57600080fd5b919050565b60008060408385031215613aa457600080fd5b613aad83613a75565b946020939093013593505050565b80358015158114613a8c57600080fd5b60008060408385031215613ade57600080fd5b82359150613aee60208401613abb565b90509250929050565b60008083601f840112613b0957600080fd5b5081356001600160401b03811115613b2057600080fd5b60208301915083602082850101111561311957600080fd5b60008060008060608587031215613b4e57600080fd5b84359350613b5e60208601613abb565b925060408501356001600160401b03811115613b7957600080fd5b613b8587828801613af7565b95989497509550505050565b60008060408385031215613ba457600080fd5b50508035926020909101359150565b600080600060608486031215613bc857600080fd5b613bd184613a75565b9250613bdf60208501613a75565b9150604084013590509250925092565b60008060408385031215613c0257600080fd5b82359150613aee60208401613a75565b8681528560208201528460408201528315156060820152821515608082015260c060a08201526000613c4760c0830184613a1d565b98975050505050505050565b600060208284031215613c6557600080fd5b61263882613a75565b600080600060408486031215613c8357600080fd5b8335925060208401356001600160401b03811115613ca057600080fd5b613cac86828701613af7565b9497909650939450505050565b600080600060608486031215613cce57600080fd5b613cd784613a75565b95602085013595506040909401359392505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715613d2a57613d2a613cec565b604052919050565b60006001600160401b03821115613d4b57613d4b613cec565b5060051b60200190565b600082601f830112613d6657600080fd5b81356001600160401b03811115613d7f57613d7f613cec565b613d92601f8201601f1916602001613d02565b818152846020838601011115613da757600080fd5b816020850160208301376000918101602001919091529392505050565b60006020808385031215613dd757600080fd5b82356001600160401b0380821115613dee57600080fd5b818501915085601f830112613e0257600080fd5b8135613e15613e1082613d32565b613d02565b81815260059190911b83018401908481019088831115613e3457600080fd5b8585015b83811015613e6c57803585811115613e505760008081fd5b613e5e8b89838a0101613d55565b845250918601918601613e38565b5098975050505050505050565b6020808252825182820181905260009190848201906040850190845b81811015613eb157835183529284019291840191600101613e95565b50909695505050505050565b600080600080600060a08688031215613ed557600080fd5b8535945060208601359350604086013592506060860135915060808601356001600160401b03811115613f0757600080fd5b613f1388828901613d55565b9150509295509295909350565b600060208284031215613f3257600080fd5b81356001600160401b03811115613f4857600080fd5b61293184828501613d55565b60008060408385031215613f6757600080fd5b613f7083613a75565b9150613aee60208401613abb565b60008060408385031215613f9157600080fd5b613f9a83613a75565b91506020808401356001600160401b03811115613fb657600080fd5b8401601f81018613613fc757600080fd5b8035613fd5613e1082613d32565b81815260059190911b82018301908381019088831115613ff457600080fd5b928401925b8284101561401257833582529284019290840190613ff9565b80955050505050509250929050565b6000806000806080858703121561403757600080fd5b61404085613a75565b935061404e60208601613a75565b92506040850135915060608501356001600160401b0381111561407057600080fd5b61407c87828801613d55565b91505092959194509250565b60008060006060848603121561409d57600080fd5b6140a684613abb565b92506140b460208501613abb565b91506140c260408501613abb565b90509250925092565b600080600080608085870312156140e157600080fd5b5050823594602084013594506040840135936060013592509050565b6000806040838503121561411057600080fd5b61411983613a75565b9150613aee60208401613a75565b600181811c9082168061413b57607f821691505b60208210810361415b57634e487b7160e01b600052602260045260246000fd5b50919050565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b601f821115610e0b57600081815260208120601f850160051c810160208610156141bd5750805b601f850160051c820191505b81811015612f5b578281556001016141c9565b6001600160401b038311156141f3576141f3613cec565b614207836142018354614127565b83614196565b6000601f84116001811461423b57600085156142235750838201355b600019600387901b1c1916600186901b178355611039565b600083815260209020601f19861690835b8281101561426c578685013582556020948501946001909201910161424c565b50868210156142895760001960f88860031b161c19848701351681555b505060018560011b0183555050505050565b6020808252601f908201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604082015260600190565b60208082526010908201526f494e56414c49445f5155414e5449545960801b604082015260600190565b634e487b7160e01b600052601160045260246000fd5b600081600019048311821515161561432c5761432c6142fc565b500290565b80820180821115610bc957610bc96142fc565b60208082526031908201527f4552433732313a207472616e736665722063616c6c6572206973206e6f74206f6040820152701ddb995c881b9bdc88185c1c1c9bdd9959607a1b606082015260800190565b634e487b7160e01b600052603260045260246000fd5b81516001600160401b038111156143c4576143c4613cec565b6143d8816143d28454614127565b84614196565b602080601f83116001811461440d57600084156143f55750858301515b600019600386901b1c1916600185901b178555612f5b565b600085815260208120601f198616915b8281101561443c5788860151825594840194600190910190840161441d565b508582101561445a5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b60006001820161447c5761447c6142fc565b5060010190565b600083516144958184602088016139f9565b8351908301906144a98183602088016139f9565b64173539b7b760d91b9101908152600501949350505050565b600082516144d48184602087016139f9565b9190910192915050565b81810381811115610bc957610bc96142fc565b60208082526032908201527f4552433732313a207472616e7366657220746f206e6f6e20455243373231526560408201527131b2b4bb32b91034b6b83632b6b2b73a32b960711b606082015260800190565b634e487b7160e01b600052601260045260246000fd5b60008261456857614568614543565b500490565b60008261457c5761457c614543565b500690565b7f416363657373436f6e74726f6c3a206163636f756e74200000000000000000008152600083516145b98160178501602088016139f9565b7001034b99036b4b9b9b4b733903937b6329607d1b60179184019182015283516145ea8160288401602088016139f9565b01602801949350505050565b634e487b7160e01b600052602160045260246000fd5b6001600160a01b038581168252841660208201526040810183905260806060820181905260009061463f90830184613a1d565b9695505050505050565b60006020828403121561465b57600080fd5b8151612638816139c6565b634e487b7160e01b600052603160045260246000fd5b60008161468b5761468b6142fc565b50600019019056fea26469706673582212206988be08ea1530646aaea37855dfbb18943d4326bede86f2160a9ddd45e939d664736f6c63430008100033

Deployed Bytecode Sourcemap

69188:15976:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;84912:249;;;;;;;;;;-1:-1:-1;84912:249:0;;;;;:::i;:::-;;:::i;:::-;;;565:14:1;;558:22;540:41;;528:2;513:18;84912:249:0;;;;;;;;70199:33;;;;;;;;;;-1:-1:-1;70199:33:0;;;;;;;;49765:100;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;51325:221::-;;;;;;;;;;-1:-1:-1;51325:221:0;;;;;:::i;:::-;;:::i;:::-;;;-1:-1:-1;;;;;1697:32:1;;;1679:51;;1667:2;1652:18;51325:221:0;1533:203:1;50848:411:0;;;;;;;;;;-1:-1:-1;50848:411:0;;;;;:::i;:::-;;:::i;:::-;;77788:821;;;;;;;;;;-1:-1:-1;77788:821:0;;;;;:::i;:::-;;:::i;69677:32::-;;;;;;;;;;;;;;;;;;;2742:25:1;;;2730:2;2715:18;69677:32:0;2596:177:1;63586:113:0;;;;;;;;;;-1:-1:-1;63674:10:0;:17;63586:113;;78618:1185;;;;;;;;;;-1:-1:-1;78618:1185:0;;;;;:::i;:::-;;:::i;72687:478::-;;;;;;:::i;:::-;;:::i;69769:66::-;;;;;;;;;;-1:-1:-1;69769:66:0;;;;-1:-1:-1;;;;;69769:66:0;;;52075:339;;;;;;;;;;-1:-1:-1;52075:339:0;;;;;:::i;:::-;;:::i;36797:131::-;;;;;;;;;;-1:-1:-1;36797:131:0;;;;;:::i;:::-;36871:7;36898:12;;;:6;:12;;;;;:22;;;;36797:131;37238:147;;;;;;;;;;-1:-1:-1;37238:147:0;;;;;:::i;:::-;;:::i;63254:256::-;;;;;;;;;;-1:-1:-1;63254:256:0;;;;;:::i;:::-;;:::i;38382:218::-;;;;;;;;;;-1:-1:-1;38382:218:0;;;;;:::i;:::-;;:::i;82289:126::-;;;;;;;;;;;;;:::i;52485:185::-;;;;;;;;;;-1:-1:-1;52485:185:0;;;;;:::i;:::-;;:::i;71450:145::-;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;:::i;81751:78::-;;;;;;;;;;-1:-1:-1;81751:78:0;;;;;:::i;:::-;;:::i;69585:41::-;;;;;;;;;;;;;;;;63776:233;;;;;;;;;;-1:-1:-1;63776:233:0;;;;;:::i;:::-;;:::i;70141:49::-;;;;;;;;;;-1:-1:-1;70141:49:0;;;;;:::i;:::-;;;;;;;;;;;;;;76787:230;;;;;;;;;;-1:-1:-1;76787:230:0;;;;;:::i;:::-;;:::i;49459:239::-;;;;;;;;;;-1:-1:-1;49459:239:0;;;;;:::i;:::-;;:::i;81933:208::-;;;;;;;;;;-1:-1:-1;81933:208:0;;;;;:::i;:::-;;:::i;69842:73::-;;;;;;;;;;-1:-1:-1;69842:73:0;;;;-1:-1:-1;;;;;69842:73:0;;;81837:87;;;;;;;;;;-1:-1:-1;81837:87:0;;;;;:::i;:::-;;:::i;70088:44::-;;;;;;;;;;-1:-1:-1;70088:44:0;;;;;:::i;:::-;;;;;;;;;;;;;;49189:208;;;;;;;;;;-1:-1:-1;49189:208:0;;;;;:::i;:::-;;:::i;20064:103::-;;;;;;;;;;;;;:::i;77026:515::-;;;;;;;;;;-1:-1:-1;77026:515:0;;;;;:::i;:::-;;:::i;84425:358::-;;;;;;;;;;-1:-1:-1;84425:358:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;19413:87::-;;;;;;;;;;-1:-1:-1;19486:6:0;;-1:-1:-1;;;;;19486:6:0;19413:87;;35257:147;;;;;;;;;;-1:-1:-1;35257:147:0;;;;;:::i;:::-;;:::i;70718:138::-;;;;;;;;;;;;;:::i;69717:41::-;;;;;;;;;;;;;;;;73177:1453;;;;;;:::i;:::-;;:::i;84798:102::-;;;;;;;;;;-1:-1:-1;84798:102:0;;;;;:::i;:::-;;:::i;49934:104::-;;;;;;;;;;;;;:::i;70487:133::-;;;;;;;;;;;;;:::i;34362:49::-;;;;;;;;;;-1:-1:-1;34362:49:0;34407:4;34362:49;;51618:155;;;;;;;;;;-1:-1:-1;51618:155:0;;;;;:::i;:::-;;:::i;71699:141::-;;;;;;;;;;;;;:::i;74640:310::-;;;;;;;;;;-1:-1:-1;74640:310:0;;;;;:::i;:::-;;:::i;82149:132::-;;;;;;;;;;-1:-1:-1;82149:132:0;;;;;:::i;:::-;;:::i;81495:126::-;;;;;;;;;;-1:-1:-1;81495:126:0;;;;;:::i;:::-;;:::i;69990:36::-;;;;;;;;;;;;;;;;52741:328;;;;;;;;;;-1:-1:-1;52741:328:0;;;;;:::i;:::-;;:::i;71200:141::-;;;;;;;;;;;;;:::i;69634:29::-;;;;;;;;;;;;;;;;81629:114;;;;;;;;;;-1:-1:-1;81629:114:0;;;;;:::i;:::-;;:::i;82514:1901::-;;;;;;;;;;-1:-1:-1;82514:1901:0;;;;;:::i;:::-;;:::i;70959:141::-;;;;;;;;;;;;;:::i;77553:225::-;;;;;;;;;;-1:-1:-1;77553:225:0;;;;;:::i;:::-;;:::i;79812:1669::-;;;;;;;;;;-1:-1:-1;79812:1669:0;;;;;:::i;:::-;;:::i;37678:149::-;;;;;;;;;;-1:-1:-1;37678:149:0;;;;;:::i;:::-;;:::i;69929:48::-;;;;;;;;;;-1:-1:-1;69929:48:0;;;;;:::i;:::-;;:::i;70280:31::-;;;;;;;;;;-1:-1:-1;70280:31:0;;;;;;;;;;;72320:99;;;;;;;;;;;;;:::i;72427:247::-;;;;;;;;;;-1:-1:-1;72427:247:0;;;;;:::i;:::-;;:::i;70239:34::-;;;;;;;;;;-1:-1:-1;70239:34:0;;;;;;;;;;;71942:140;;;;;;;;;;;;;:::i;70033:46::-;;;;;;;;;;-1:-1:-1;70033:46:0;;;;;:::i;:::-;;;;;;;;;;;;;;20322:201;;;;;;;;;;-1:-1:-1;20322:201:0;;;;;:::i;:::-;;:::i;84912:249::-;85029:4;-1:-1:-1;;;;;;85054:48:0;;-1:-1:-1;;;85054:48:0;;:99;;;85117:36;85141:11;85117:23;:36::i;:::-;85047:106;84912:249;-1:-1:-1;;84912:249:0:o;49765:100::-;49819:13;49852:5;49845:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;49765:100;:::o;51325:221::-;51401:7;54668:16;;;:7;:16;;;;;;-1:-1:-1;;;;;54668:16:0;51421:73;;;;-1:-1:-1;;;51421:73:0;;13671:2:1;51421:73:0;;;13653:21:1;13710:2;13690:18;;;13683:30;13749:34;13729:18;;;13722:62;-1:-1:-1;;;13800:18:1;;;13793:42;13852:19;;51421:73:0;;;;;;;;;-1:-1:-1;51514:24:0;;;;:15;:24;;;;;;-1:-1:-1;;;;;51514:24:0;;51325:221::o;50848:411::-;50929:13;50945:23;50960:7;50945:14;:23::i;:::-;50929:39;;50993:5;-1:-1:-1;;;;;50987:11:0;:2;-1:-1:-1;;;;;50987:11:0;;50979:57;;;;-1:-1:-1;;;50979:57:0;;14084:2:1;50979:57:0;;;14066:21:1;14123:2;14103:18;;;14096:30;14162:34;14142:18;;;14135:62;-1:-1:-1;;;14213:18:1;;;14206:31;14254:19;;50979:57:0;13882:397:1;50979:57:0;18217:10;-1:-1:-1;;;;;51071:21:0;;;;:62;;-1:-1:-1;51096:37:0;51113:5;18217:10;72427:247;:::i;51096:37::-;51049:168;;;;-1:-1:-1;;;51049:168:0;;14486:2:1;51049:168:0;;;14468:21:1;14525:2;14505:18;;;14498:30;14564:34;14544:18;;;14537:62;14635:26;14615:18;;;14608:54;14679:19;;51049:168:0;14284:420:1;51049:168:0;51230:21;51239:2;51243:7;51230:8;:21::i;:::-;50918:341;50848:411;;:::o;77788:821::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;77877:8:::1;77889:1;77877:13:::0;77874:727:::1;;77929:18:::0;:29;;-1:-1:-1;;77929:29:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;77874:727::-:1;77978:8;77990:1;77978:13:::0;77975:626:::1;;78032:18:::0;:29;;-1:-1:-1;;78032:29:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;77975:626::-:1;78081:8;78093:1;78081:13:::0;78078:523:::1;;78136:19:::0;:30;;-1:-1:-1;;78136:30:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;78078:523::-:1;78186:8;78198:1;78186:13:::0;78183:418:::1;;78241:19:::0;:30;;-1:-1:-1;;78241:30:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;78183:418::-:1;78291:8;78303:1;78291:13:::0;78288:313:::1;;78350:23:::0;:34;;-1:-1:-1;;78350:34:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;78288:313::-:1;78404:8;78416:1;78404:13:::0;78401:200:::1;;78459:19:::0;:30;;-1:-1:-1;;78459:30:0::1;;::::0;::::1;;;;::::0;;77788:821;;:::o;78401:200::-:1;78509:8;78521:1;78509:13:::0;78506:95:::1;;78561:17:::0;:28;;-1:-1:-1;;78561:28:0::1;;::::0;::::1;;;;::::0;;78506:95:::1;77788:821:::0;;:::o;78618:1185::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;78741:8:::1;78753:1;78741:13:::0;78738:1057:::1;;78793:19:::0;:31;;-1:-1:-1;;78793:31:0::1;::::0;::::1;;;::::0;;78839:18;:29:::1;78860:8:::0;;78839:18;:29:::1;:::i;:::-;;78738:1057;;;78888:8;78900:1;78888:13:::0;78885:910:::1;;78942:19:::0;:31;;-1:-1:-1;;78942:31:0::1;::::0;::::1;;;::::0;;78988:18;:29:::1;79009:8:::0;;78988:18;:29:::1;:::i;78885:910::-;79038:8;79050:1;79038:13:::0;79035:760:::1;;79093:20:::0;:32;;-1:-1:-1;;79093:32:0::1;::::0;::::1;;;::::0;;79140:19;:30:::1;79162:8:::0;;79140:19;:30:::1;:::i;79035:760::-;79190:8;79202:1;79190:13:::0;79187:608:::1;;79245:20:::0;:32;;-1:-1:-1;;79245:32:0::1;::::0;::::1;;;::::0;;79292:19;:30:::1;79314:8:::0;;79292:19;:30:::1;:::i;79187:608::-;79342:8;79354:1;79342:13:::0;79339:456:::1;;79401:24:::0;:36;;-1:-1:-1;;79401:36:0::1;::::0;::::1;;;::::0;;79452:23;:34:::1;79478:8:::0;;79452:23;:34:::1;:::i;79339:456::-;79506:8;79518:1;79506:13:::0;79503:292:::1;;79561:20:::0;:32;;-1:-1:-1;;79561:32:0::1;::::0;::::1;;;::::0;;79608:19;:30:::1;79630:8:::0;;79608:19;:30:::1;:::i;79503:292::-;79658:8;79670:1;79658:13:::0;79655:140:::1;;79710:18:::0;:30;;-1:-1:-1;;79710:30:0::1;::::0;::::1;;;::::0;;79755:17;:28:::1;79775:8:::0;;79755:17;:28:::1;:::i;:::-;;79655:140;78618:1185:::0;;;;:::o;72687:478::-;4853:1;5451:7;;:19;5443:63;;;;-1:-1:-1;;;5443:63:0;;;;;;;:::i;:::-;4853:1;5584:7;:18;72786:11:::1;::::0;;;::::1;;;72785:12;72777:42;;;::::0;-1:-1:-1;;;72777:42:0;;17690:2:1;72777:42:0::1;::::0;::::1;17672:21:1::0;17729:2;17709:18;;;17702:30;-1:-1:-1;;;17748:18:1;;;17741:48;17806:18;;72777:42:0::1;17488:342:1::0;72777:42:0::1;72851:1;72839:9;:13;72831:41;;;;-1:-1:-1::0;;;72831:41:0::1;;;;;;;:::i;:::-;72913:9;72906:4;;:16;;;;:::i;:::-;72893:9;:29;;72885:55;;;::::0;-1:-1:-1;;;72885:55:0;;18687:2:1;72885:55:0::1;::::0;::::1;18669:21:1::0;18726:2;18706:18;;;18699:30;-1:-1:-1;;;18745:18:1;;;18738:43;18798:18;;72885:55:0::1;18485:337:1::0;72885:55:0::1;72998:16;::::0;72971:10:::1;72959:23;::::0;;;:11:::1;:23;::::0;;;;;:35:::1;::::0;72985:9;;72959:35:::1;:::i;:::-;:55;;72951:90;;;::::0;-1:-1:-1;;;72951:90:0;;19159:2:1;72951:90:0::1;::::0;::::1;19141:21:1::0;19198:2;19178:18;;;19171:30;-1:-1:-1;;;19217:18:1;;;19210:52;19279:18;;72951:90:0::1;18957:346:1::0;72951:90:0::1;73054:41;73065:9;73075:8;73084:10;73054;:41::i;:::-;-1:-1:-1::0;73131:10:0::1;73119:23;::::0;;;:11:::1;:23;::::0;;;;:36;;;;::::1;::::0;;-1:-1:-1;5763:7:0;:22;72687:478::o;52075:339::-;52270:41;18217:10;52303:7;52270:18;:41::i;:::-;52262:103;;;;-1:-1:-1;;;52262:103:0;;;;;;;:::i;:::-;52378:28;52388:4;52394:2;52398:7;52378:9;:28::i;37238:147::-;36871:7;36898:12;;;:6;:12;;;;;:22;;;34853:16;34864:4;34853:10;:16::i;:::-;37352:25:::1;37363:4;37369:7;37352:10;:25::i;63254:256::-:0;63351:7;63387:23;63404:5;63387:16;:23::i;:::-;63379:5;:31;63371:87;;;;-1:-1:-1;;;63371:87:0;;19928:2:1;63371:87:0;;;19910:21:1;19967:2;19947:18;;;19940:30;20006:34;19986:18;;;19979:62;-1:-1:-1;;;20057:18:1;;;20050:41;20108:19;;63371:87:0;19726:407:1;63371:87:0;-1:-1:-1;;;;;;63476:19:0;;;;;;;;:12;:19;;;;;;;;:26;;;;;;;;;63254:256::o;38382:218::-;-1:-1:-1;;;;;38478:23:0;;18217:10;38478:23;38470:83;;;;-1:-1:-1;;;38470:83:0;;20340:2:1;38470:83:0;;;20322:21:1;20379:2;20359:18;;;20352:30;20418:34;20398:18;;;20391:62;-1:-1:-1;;;20469:18:1;;;20462:45;20524:19;;38470:83:0;20138:411:1;38470:83:0;38566:26;38578:4;38584:7;38566:11;:26::i;82289:126::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;4853:1:::1;5451:7;;:19:::0;5443:63:::1;;;;-1:-1:-1::0;;;5443:63:0::1;;;;;;;:::i;:::-;4853:1;5584:7;:18:::0;82361:13:::2;::::0;82353:54:::2;::::0;-1:-1:-1;;;;;82361:13:0;;::::2;::::0;82385:21:::2;82353:54:::0;::::2;;;::::0;82361:13:::2;82353:54:::0;82361:13;82353:54;82385:21;82361:13;82353:54;::::2;;;;;;;;;;;;;::::0;::::2;;;;;-1:-1:-1::0;4809:1:0::1;5763:7;:22:::0;82289:126::o;52485:185::-;52623:39;52640:4;52646:2;52650:7;52623:39;;;;;;;;;;;;:16;:39::i;71450:145::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;81751:78::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;81809:4:::1;:12:::0;81751:78::o;63776:233::-;63851:7;63887:30;63674:10;:17;;63586:113;63887:30;63879:5;:38;63871:95;;;;-1:-1:-1;;;63871:95:0;;20756:2:1;63871:95:0;;;20738:21:1;20795:2;20775:18;;;20768:30;20834:34;20814:18;;;20807:62;-1:-1:-1;;;20885:18:1;;;20878:42;20937:19;;63871:95:0;20554:408:1;63871:95:0;63984:10;63995:5;63984:17;;;;;;;;:::i;:::-;;;;;;;;;63977:24;;63776:233;;;:::o;76787:230::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;76937:1:::1;76902:24:::0;;;:14:::1;:24;::::0;;;;76896:38;;::::1;::::0;::::1;:::i;:::-;;;:42;76888:78;;;::::0;-1:-1:-1;;;76888:78:0;;21301:2:1;76888:78:0::1;::::0;::::1;21283:21:1::0;21340:2;21320:18;;;21313:30;21379:26;21359:18;;;21352:54;21423:18;;76888:78:0::1;21099:348:1::0;76888:78:0::1;76978:24;::::0;;;:14:::1;:24;::::0;;;;:31:::1;77005:4:::0;;76978:24;:31:::1;:::i;49459:239::-:0;49531:7;49567:16;;;:7;:16;;;;;;-1:-1:-1;;;;;49567:16:0;;49594:73;;;;-1:-1:-1;;;49594:73:0;;21654:2:1;49594:73:0;;;21636:21:1;21693:2;21673:18;;;21666:30;21732:34;21712:18;;;21705:62;-1:-1:-1;;;21783:18:1;;;21776:39;21832:19;;49594:73:0;21452:405:1;81933:208:0;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;4853:1:::1;5451:7;;:19:::0;5443:63:::1;;;;-1:-1:-1::0;;;5443:63:0::1;;;;;;;:::i;:::-;4853:1;5584:7;:18:::0;82051:13;82043:41:::2;;;;-1:-1:-1::0;;;82043:41:0::2;;;;;;;:::i;:::-;82099:34;82110:9;82120:8;82129:3;82099:10;:34::i;:::-;-1:-1:-1::0;;4809:1:0::1;5763:7;:22:::0;-1:-1:-1;81933:208:0:o;81837:87::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;81900:6:::1;:16:::0;;-1:-1:-1;;;;;;81900:16:0::1;-1:-1:-1::0;;;;;81900:16:0;;;::::1;::::0;;;::::1;::::0;;81837:87::o;49189:208::-;49261:7;-1:-1:-1;;;;;49289:19:0;;49281:74;;;;-1:-1:-1;;;49281:74:0;;22064:2:1;49281:74:0;;;22046:21:1;22103:2;22083:18;;;22076:30;22142:34;22122:18;;;22115:62;-1:-1:-1;;;22193:18:1;;;22186:40;22243:19;;49281:74:0;21862:406:1;49281:74:0;-1:-1:-1;;;;;;49373:16:0;;;;;:9;:16;;;;;;;49189:208::o;20064:103::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;20129:30:::1;20156:1;20129:18;:30::i;:::-;20064:103::o:0;77026:515::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;77127:12:::1;:19;77123:1;:23;77115:50;;;::::0;-1:-1:-1;;;77115:50:0;;22475:2:1;77115:50:0::1;::::0;::::1;22457:21:1::0;22514:2;22494:18;;;22487:30;-1:-1:-1;;;22533:18:1;;;22526:44;22587:18;;77115:50:0::1;22273:338:1::0;77115:50:0::1;77216:9;77212:310;77236:12;:19;77232:1;:23;77212:310;;;77325:1;77299:12;77312:1;77299:15;;;;;;;;:::i;:::-;;;;;;;77293:29;:33;77285:57;;;::::0;-1:-1:-1;;;77285:57:0;;22818:2:1;77285:57:0::1;::::0;::::1;22800:21:1::0;22857:2;22837:18;;;22830:30;-1:-1:-1;;;22876:18:1;;;22869:42;22928:18;;77285:57:0::1;22616:336:1::0;77285:57:0::1;77399:12;77412:1;77399:15;;;;;;;;:::i;:::-;;;;;;;77366:14;:30;77381:14;;77366:30;;;;;;;;;;;:48;;;;;;:::i;:::-;;77435:33;77445:7;19486:6:::0;;-1:-1:-1;;;;;19486:6:0;;19413:87;77445:7:::1;77453:14;;77435:9;:33::i;:::-;77488:14;:16:::0;;::::1;::::0;;::::1;::::0;;;77257:4:::1;77212:310;;84425:358:::0;84485:16;84514:23;84540:17;84550:6;84540:9;:17::i;:::-;84514:43;;84568:25;84610:15;-1:-1:-1;;;;;84596:30:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;84596:30:0;;84568:58;;84642:9;84637:113;84657:15;84653:1;:19;84637:113;;;84708:30;84728:6;84736:1;84708:19;:30::i;:::-;84694:8;84703:1;84694:11;;;;;;;;:::i;:::-;;;;;;;;;;:44;84674:3;;;;:::i;:::-;;;;84637:113;;;-1:-1:-1;84767:8:0;84425:358;-1:-1:-1;;;84425:358:0:o;35257:147::-;35343:4;35367:12;;;:6;:12;;;;;;;;-1:-1:-1;;;;;35367:29:0;;;;;;;;;;;;;;;35257:147::o;70718:138::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;73177:1453::-;4853:1;5451:7;;:19;5443:63;;;;-1:-1:-1;;;5443:63:0;;;;;;;:::i;:::-;4853:1;5584:7;:18;73365:49:::1;::::0;;::::1;::::0;;::::1;24639:19:1::0;;;73394:10:0::1;24696:2:1::0;24692:15;-1:-1:-1;;24688:53:1;24674:12;;;24667:75;24758:12;;;;24751:28;;;73365:49:0;;;;;;;;;;24795:12:1;;;73365:49:0;;73355:60;;;;::::1;::::0;29875:66:1;16345:58:0;;;29863:79:1;29958:12;;;;29951:28;;;16345:58:0;;;;;;;;;;29995:12:1;;;;16345:58:0;;;16335:69;;;;;73532:6:::1;::::0;-1:-1:-1;;;;;73532:6:0::1;73500:28;16335:69:::0;73523:4;73500:13:::1;:28::i;:::-;-1:-1:-1::0;;;;;73500:38:0::1;;73492:76;;;::::0;-1:-1:-1;;;73492:76:0;;25020:2:1;73492:76:0::1;::::0;::::1;25002:21:1::0;25059:2;25039:18;;;25032:30;25098:27;25078:18;;;25071:55;25143:18;;73492:76:0::1;24818:349:1::0;73492:76:0::1;73646:14;::::0;::::1;::::0;::::1;;;73645:15;:34:::0;::::1;;;;73664:10;73678:1;73664:15;73645:34;73642:491;;;73763:9;73747:13;;:25;;;;:::i;:::-;73734:9;:38;;73726:64;;;::::0;-1:-1:-1;;;73726:64:0;;18687:2:1;73726:64:0::1;::::0;::::1;18669:21:1::0;18726:2;18706:18;;;18699:30;-1:-1:-1;;;18745:18:1;;;18738:43;18798:18;;73726:64:0::1;18485:337:1::0;73726:64:0::1;73828:10;73813:26;::::0;;;:14:::1;:26;::::0;;;;;73855:7;;73813:38:::1;::::0;73842:9;;73813:38:::1;:::i;:::-;:49;;73805:83;;;::::0;-1:-1:-1;;;73805:83:0;;25374:2:1;73805:83:0::1;::::0;::::1;25356:21:1::0;25413:2;25393:18;;;25386:30;-1:-1:-1;;;25432:18:1;;;25425:51;25493:18;;73805:83:0::1;25172:345:1::0;73805:83:0::1;73642:491;;;73911:13;::::0;::::1;;73910:14;:33:::0;::::1;;;;73928:10;73942:1;73928:15;73910:33;73906:227;;;74002:10;73992:21;::::0;;;:9:::1;:21;::::0;;;;;74029:7;;73992:33:::1;::::0;74016:9;;73992:33:::1;:::i;:::-;:44;;73984:73;;;::::0;-1:-1:-1;;;73984:73:0;;25724:2:1;73984:73:0::1;::::0;::::1;25706:21:1::0;25763:2;25743:18;;;25736:30;-1:-1:-1;;;25782:18:1;;;25775:46;25838:18;;73984:73:0::1;25522:340:1::0;73906:227:0::1;74089:32;::::0;-1:-1:-1;;;74089:32:0;;26069:2:1;74089:32:0::1;::::0;::::1;26051:21:1::0;26108:2;26088:18;;;26081:30;-1:-1:-1;;;26127:18:1;;;26120:52;26189:18;;74089:32:0::1;25867:346:1::0;73906:227:0::1;74170:1;74158:9;:13;74150:41;;;;-1:-1:-1::0;;;74150:41:0::1;;;;;;;:::i;:::-;74207;74218:9;74228:8;74237:10;74207;:41::i;:::-;74284:10;74272:23;::::0;;;:11:::1;:23;::::0;;;;:36;;;::::1;::::0;;74335:14:::1;::::0;::::1;::::0;::::1;;;74334:15;:34:::0;::::1;;;;74353:10;74367:1;74353:15;74334:34;74331:292;;;74442:10;74427:26;::::0;;;:14:::1;:26;::::0;;;;:39;;;::::1;::::0;;74331:292:::1;;;74490:13;::::0;::::1;;74489:14;:33:::0;::::1;;;;74507:10;74521:1;74507:15;74489:33;74485:138;;;74585:10;74575:21;::::0;;;:9:::1;:21;::::0;;;;:34;;;::::1;::::0;;74485:138:::1;-1:-1:-1::0;;4809:1:0;5763:7;:22;-1:-1:-1;;;;;73177:1453:0:o;84798:102::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;84872:13:::1;:20;84888:4:::0;84872:13;:20:::1;:::i;49934:104::-:0;49990:13;50023:7;50016:14;;;;;:::i;70487:133::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;51618:155::-;51713:52;18217:10;51746:8;51756;51713:18;:52::i;71699:141::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;74640:310::-;74749:4;;74766:154;74790:8;:15;74786:1;:19;74766:154;;;74840:20;74848:8;74857:1;74848:11;;;;;;;;:::i;:::-;;;;;;;74840:7;:20::i;:::-;-1:-1:-1;;;;;74831:29:0;:5;-1:-1:-1;;;;;74831:29:0;;74827:82;;74888:5;74881:12;;;;;74827:82;74807:3;;;;:::i;:::-;;;;74766:154;;;-1:-1:-1;74938:4:0;;74640:310;-1:-1:-1;;;74640:310:0:o;82149:132::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;4853:1:::1;5451:7;;:19:::0;5443:63:::1;;;;-1:-1:-1::0;;;5443:63:0::1;;;;;;;:::i;:::-;82243:13:::2;:30:::0;;-1:-1:-1;;;;;;82243:30:0::2;-1:-1:-1::0;;;;;82243:30:0;;;::::2;::::0;;;::::2;::::0;;-1:-1:-1;5584:7:0::1;5763:22:::0;82149:132::o;81495:126::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;81577:16:::1;:36:::0;81495:126::o;52741:328::-;52916:41;18217:10;52949:7;52916:18;:41::i;:::-;52908:103;;;;-1:-1:-1;;;52908:103:0;;;;;;;:::i;:::-;53022:39;53036:4;53042:2;53046:7;53055:5;53022:13;:39::i;71200:141::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;81629:114::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;81705:13:::1;:30:::0;81629:114::o;82514:1901::-;54644:4;54668:16;;;:7;:16;;;;;;82580:13;;-1:-1:-1;;;;;54668:16:0;82607:48;;;;-1:-1:-1;;;82607:48:0;;26420:2:1;82607:48:0;;;26402:21:1;26459:2;26439:18;;;26432:30;-1:-1:-1;;;26478:18:1;;;26471:48;26536:18;;82607:48:0;26218:342:1;82607:48:0;82713:1;82678:24;;;:14;:24;;;;;82672:38;;;;;:::i;:::-;;;:42;82668:107;;;82739:24;;;;:14;:24;;;;;82732:31;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;82514:1901;;;:::o;82668:107::-;82787:13;82820:21;82884:8;82857:10;:23;;;:35;;:72;;;;-1:-1:-1;82897:21:0;;:32;-1:-1:-1;82897:32:0;82857:72;82854:1294;;;82957:19;;83001:18;82991:28;;82957:19;;;;;-1:-1:-1;83001:18:0;82991:28;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;82854:1294;;;83039:10;:23;:35;-1:-1:-1;83039:35:0;;;:72;;-1:-1:-1;83079:21:0;;:32;-1:-1:-1;83079:32:0;83039:72;83036:1112;;;83139:19;;83183:18;83173:28;;83139:19;;;;;-1:-1:-1;83183:18:0;83173:28;;;:::i;83036:1112::-;83221:11;:24;:36;-1:-1:-1;83221:36:0;;;:74;;-1:-1:-1;83262:22:0;;:33;-1:-1:-1;83262:33:0;83221:74;83218:930;;;83323:20;;83368:19;83358:29;;83323:20;;;;;-1:-1:-1;83368:19:0;83358:29;;;:::i;83218:930::-;83407:11;:24;:36;-1:-1:-1;83407:36:0;;;:74;;-1:-1:-1;83448:22:0;;:33;-1:-1:-1;83448:33:0;83407:74;83404:744;;;83509:20;;83554:19;83544:29;;83509:20;;;;;-1:-1:-1;83554:19:0;83544:29;;;:::i;83404:744::-;83593:15;:28;:40;-1:-1:-1;83593:40:0;;;:82;;-1:-1:-1;83638:26:0;;:37;-1:-1:-1;83638:37:0;83593:82;83590:558;;;83702:24;;83751:23;83741:33;;83702:24;;;;;-1:-1:-1;83751:23:0;83741:33;;;:::i;83590:558::-;83794:11;:24;:36;-1:-1:-1;83794:36:0;;;:74;;-1:-1:-1;83835:22:0;;:33;-1:-1:-1;83835:33:0;83794:74;83791:357;;;83895:20;;83940:19;83930:29;;83895:20;;;;;-1:-1:-1;83940:19:0;83930:29;;;:::i;83791:357::-;83979:9;:22;:34;-1:-1:-1;83979:34:0;;;:70;;-1:-1:-1;84018:20:0;;:31;-1:-1:-1;84018:31:0;83979:70;83976:172;;;84076:18;;84119:17;84109:27;;84076:18;;;;;-1:-1:-1;84119:17:0;84109:27;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;83976:172;84164:8;84161:246;;;84237:7;84246:19;:8;:17;:19::i;:::-;84220:55;;;;;;;;;:::i;:::-;;;;;;;;;;;;;84188:102;;;;82514:1901;;;:::o;84161:246::-;84371:7;84354:25;;;;;;;;:::i;70959:141::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;77553:225::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;77660:11:::1;:26:::0;;-1:-1:-1;;77697:32:0;77660:26;;::::1;;::::0;;;::::1;-1:-1:-1::0;;77697:32:0;;;;;77660:26:::1;77697:32:::0;::::1;;::::0;;;::::1;::::0;;;::::1;-1:-1:-1::0;;77740:30:0::1;::::0;::::1;;;::::0;;77553:225::o;79812:1669::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;79945:8:::1;79957:1;79945:13:::0;79942:1531:::1;;79997:10;:39:::0;;;80051:21;:35;;;80101:22;:37;;;79942:1531:::1;;;80158:8;80170:1;80158:13:::0;80155:1318:::1;;80213:10;:39:::0;;;80267:21;:35;;;80317:22;:37;;;80155:1318:::1;;;80374:8;80386:1;80374:13:::0;80371:1102:::1;;80430:11;:40:::0;;;80485:22;:36;;;80536:23;:38;;;80371:1102:::1;;;80594:8;80606:1;80594:13:::0;80591:882:::1;;80650:11;:40:::0;;;80705:22;:36;;;80756:23;:38;;;80591:882:::1;;;80814:8;80826:1;80814:13:::0;80811:662:::1;;80874:15;:44:::0;;;80933:26;:40;;;80988:27;:42;;;80811:662:::1;;;81050:8;81062:1;81050:13:::0;81047:426:::1;;81106:11;:40:::0;;;81161:22;:36;;;81212:23;:38;;;81047:426:::1;;;81270:8;81282:1;81270:13:::0;81267:206:::1;;81323:9;:38:::0;;;;81376:20;:34;81425:21;:36;-1:-1:-1;79812:1669:0:o;37678:149::-;36871:7;36898:12;;;:6;:12;;;;;:22;;;34853:16;34864:4;34853:10;:16::i;:::-;37793:26:::1;37805:4;37811:7;37793:11;:26::i;69929:48::-:0;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;72320:99::-;72365:13;72398;72391:20;;;;;:::i;72427:247::-;72556:4;72580:33;69546:26;72604:8;72580:7;:33::i;:::-;:86;;;-1:-1:-1;;;;;;51965:25:0;;;51941:4;51965:25;;;:18;:25;;;;;;;;:35;;;;;;;;;;;;72627:39;72573:93;72427:247;-1:-1:-1;;;72427:247:0:o;71942:140::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;20322:201::-;19486:6;;-1:-1:-1;;;;;19486:6:0;18217:10;19633:23;19625:68;;;;-1:-1:-1;;;19625:68:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;20411:22:0;::::1;20403:73;;;::::0;-1:-1:-1;;;20403:73:0;;27729:2:1;20403:73:0::1;::::0;::::1;27711:21:1::0;27768:2;27748:18;;;27741:30;27807:34;27787:18;;;27780:62;-1:-1:-1;;;27858:18:1;;;27851:36;27904:19;;20403:73:0::1;27527:402:1::0;20403:73:0::1;20487:28;20506:8;20487:18;:28::i;:::-;20322:201:::0;:::o;34961:204::-;35046:4;-1:-1:-1;;;;;;35070:47:0;;-1:-1:-1;;;35070:47:0;;:87;;;35121:36;35145:11;35121:23;:36::i;58725:174::-;58800:24;;;;:15;:24;;;;;:29;;-1:-1:-1;;;;;;58800:29:0;-1:-1:-1;;;;;58800:29:0;;;;;;;;:24;;58854:23;58800:24;58854:14;:23::i;:::-;-1:-1:-1;;;;;58845:46:0;;;;;;;;;;;58725:174;;:::o;75654:949::-;75744:8;75756:1;75744:13;75741:852;;75803:36;75814:9;75824:10;75835:3;75803:10;:36::i;75741:852::-;75861:8;75873:1;75861:13;75858:735;;75917:36;75928:9;75938:10;75949:3;75917:10;:36::i;75858:735::-;75973:8;75985:1;75973:13;75970:623;;76030:37;76041:9;76051:11;76063:3;76030:10;:37::i;75970:623::-;76087:8;76099:1;76087:13;76084:509;;76144:37;76155:9;76165:11;76177:3;76144:10;:37::i;76084:509::-;76201:8;76213:1;76201:13;76198:395;;76262:41;76273:9;76283:15;76299:3;76262:10;:41::i;76198:395::-;76323:8;76335:1;76323:13;76320:273;;76380:37;76391:9;76401:11;76413:3;76380:10;:37::i;76320:273::-;76437:8;76449:1;76437:13;76434:159;;76492:35;76503:9;76513;76523:3;76492:10;:35::i;76434:159::-;76558:23;;-1:-1:-1;;;76558:23:0;;28136:2:1;76558:23:0;;;28118:21:1;28175:2;28155:18;;;28148:30;-1:-1:-1;;;28194:18:1;;;28187:43;28247:18;;76558:23:0;27934:337:1;54873:348:0;54966:4;54668:16;;;:7;:16;;;;;;-1:-1:-1;;;;;54668:16:0;54983:73;;;;-1:-1:-1;;;54983:73:0;;28478:2:1;54983:73:0;;;28460:21:1;28517:2;28497:18;;;28490:30;28556:34;28536:18;;;28529:62;-1:-1:-1;;;28607:18:1;;;28600:42;28659:19;;54983:73:0;28276:408:1;54983:73:0;55067:13;55083:23;55098:7;55083:14;:23::i;:::-;55067:39;;55136:5;-1:-1:-1;;;;;55125:16:0;:7;-1:-1:-1;;;;;55125:16:0;;:52;;;;55145:32;55162:5;55169:7;55145:16;:32::i;:::-;55125:87;;;;55205:7;-1:-1:-1;;;;;55181:31:0;:20;55193:7;55181:11;:20::i;:::-;-1:-1:-1;;;;;55181:31:0;;55125:87;55117:96;54873:348;-1:-1:-1;;;;54873:348:0:o;57982:625::-;58141:4;-1:-1:-1;;;;;58114:31:0;:23;58129:7;58114:14;:23::i;:::-;-1:-1:-1;;;;;58114:31:0;;58106:81;;;;-1:-1:-1;;;58106:81:0;;28891:2:1;58106:81:0;;;28873:21:1;28930:2;28910:18;;;28903:30;28969:34;28949:18;;;28942:62;-1:-1:-1;;;29020:18:1;;;29013:35;29065:19;;58106:81:0;28689:401:1;58106:81:0;-1:-1:-1;;;;;58206:16:0;;58198:65;;;;-1:-1:-1;;;58198:65:0;;29297:2:1;58198:65:0;;;29279:21:1;29336:2;29316:18;;;29309:30;29375:34;29355:18;;;29348:62;-1:-1:-1;;;29426:18:1;;;29419:34;29470:19;;58198:65:0;29095:400:1;58198:65:0;58276:39;58297:4;58303:2;58307:7;58276:20;:39::i;:::-;58380:29;58397:1;58401:7;58380:8;:29::i;:::-;-1:-1:-1;;;;;58422:15:0;;;;;;:9;:15;;;;;:20;;58441:1;;58422:15;:20;;58441:1;;58422:20;:::i;:::-;;;;-1:-1:-1;;;;;;;58453:13:0;;;;;;:9;:13;;;;;:18;;58470:1;;58453:13;:18;;58470:1;;58453:18;:::i;:::-;;;;-1:-1:-1;;58482:16:0;;;;:7;:16;;;;;;:21;;-1:-1:-1;;;;;;58482:21:0;-1:-1:-1;;;;;58482:21:0;;;;;;;;;58521:27;;58482:16;;58521:27;;;;;;;50918:341;50848:411;;:::o;35708:105::-;35775:30;35786:4;18217:10;35775;:30::i;39979:238::-;40063:22;40071:4;40077:7;40063;:22::i;:::-;40058:152;;40102:12;;;;:6;:12;;;;;;;;-1:-1:-1;;;;;40102:29:0;;;;;;;;;:36;;-1:-1:-1;;40102:36:0;40134:4;40102:36;;;40185:12;18217:10;;18137:98;40185:12;-1:-1:-1;;;;;40158:40:0;40176:7;-1:-1:-1;;;;;40158:40:0;40170:4;40158:40;;;;;;;;;;39979:238;;:::o;40397:239::-;40481:22;40489:4;40495:7;40481;:22::i;:::-;40477:152;;;40552:5;40520:12;;;:6;:12;;;;;;;;-1:-1:-1;;;;;40520:29:0;;;;;;;;;;:37;;-1:-1:-1;;40520:37:0;;;40577:40;18217:10;;40520:12;;40577:40;;40552:5;40577:40;40397:239;;:::o;20683:191::-;20776:6;;;-1:-1:-1;;;;;20793:17:0;;;-1:-1:-1;;;;;;20793:17:0;;;;;;;20826:40;;20776:6;;;20793:17;20776:6;;20826:40;;20757:16;;20826:40;20746:128;20683:191;:::o;55563:110::-;55639:26;55649:2;55653:7;55639:26;;;;;;;;;;;;:9;:26::i;12341:231::-;12419:7;12440:17;12459:18;12481:27;12492:4;12498:9;12481:10;:27::i;:::-;12439:69;;;;12519:18;12531:5;12519:11;:18::i;59041:315::-;59196:8;-1:-1:-1;;;;;59187:17:0;:5;-1:-1:-1;;;;;59187:17:0;;59179:55;;;;-1:-1:-1;;;59179:55:0;;30220:2:1;59179:55:0;;;30202:21:1;30259:2;30239:18;;;30232:30;30298:27;30278:18;;;30271:55;30343:18;;59179:55:0;30018:349:1;59179:55:0;-1:-1:-1;;;;;59245:25:0;;;;;;;:18;:25;;;;;;;;:35;;;;;;;;;;;;;:46;;-1:-1:-1;;59245:46:0;;;;;;;;;;59307:41;;540::1;;;59307::0;;513:18:1;59307:41:0;;;;;;;59041:315;;;:::o;53951:::-;54108:28;54118:4;54124:2;54128:7;54108:9;:28::i;:::-;54155:48;54178:4;54184:2;54188:7;54197:5;54155:22;:48::i;:::-;54147:111;;;;-1:-1:-1;;;54147:111:0;;;;;;;:::i;6165:723::-;6221:13;6442:5;6451:1;6442:10;6438:53;;-1:-1:-1;;6469:10:0;;;;;;;;;;;;-1:-1:-1;;;6469:10:0;;;;;6165:723::o;6438:53::-;6516:5;6501:12;6557:78;6564:9;;6557:78;;6590:8;;;;:::i;:::-;;-1:-1:-1;6613:10:0;;-1:-1:-1;6621:2:0;6613:10;;:::i;:::-;;;6557:78;;;6645:19;6677:6;-1:-1:-1;;;;;6667:17:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;6667:17:0;;6645:39;;6695:154;6702:10;;6695:154;;6729:11;6739:1;6729:11;;:::i;:::-;;-1:-1:-1;6798:10:0;6806:2;6798:5;:10;:::i;:::-;6785:24;;:2;:24;:::i;:::-;6772:39;;6755:6;6762;6755:14;;;;;;;;:::i;:::-;;;;:56;-1:-1:-1;;;;;6755:56:0;;;;;;;;-1:-1:-1;6826:11:0;6835:2;6826:11;;:::i;:::-;;;6695:154;;62946:224;63048:4;-1:-1:-1;;;;;;63072:50:0;;-1:-1:-1;;;63072:50:0;;:90;;;63126:36;63150:11;63126:23;:36::i;75042:597::-;75188:13;;;;;;;;;;;75187:14;75179:37;;;;-1:-1:-1;;;75179:37:0;;31367:2:1;75179:37:0;;;31349:21:1;31406:2;31386:18;;;31379:30;-1:-1:-1;;;31425:18:1;;;31418:41;31476:18;;75179:37:0;31165:335:1;75179:37:0;75335:18;;75354:1;75288:16;;;75381:17;;;;75288:37;;;;75286:70;;;;75380:35;;-1:-1:-1;;75380:35:0;:52;-1:-1:-1;75380:52:0;75372:83;;;;-1:-1:-1;;;75372:83:0;;31707:2:1;75372:83:0;;;31689:21:1;31746:2;31726:18;;;31719:30;-1:-1:-1;;;31765:18:1;;;31758:49;31824:18;;75372:83:0;31505:343:1;75372:83:0;75478:9;75473:146;75497:9;75493:1;:13;75473:146;;;75532:33;75542:3;75547:5;:17;;;75532:9;:33::i;:::-;75584:17;;;:19;;;;;;;;;75508:3;75473:146;;;;75237:395;75125:514;75042:597;;;:::o;64622:589::-;-1:-1:-1;;;;;64828:18:0;;64824:187;;64863:40;64895:7;66038:10;:17;;66011:24;;;;:15;:24;;;;;:44;;;66066:24;;;;;;;;;;;;65934:164;64863:40;64824:187;;;64933:2;-1:-1:-1;;;;;64925:10:0;:4;-1:-1:-1;;;;;64925:10:0;;64921:90;;64952:47;64985:4;64991:7;64952:32;:47::i;:::-;-1:-1:-1;;;;;65025:16:0;;65021:183;;65058:45;65095:7;65058:36;:45::i;65021:183::-;65131:4;-1:-1:-1;;;;;65125:10:0;:2;-1:-1:-1;;;;;65125:10:0;;65121:83;;65152:40;65180:2;65184:7;65152:27;:40::i;36103:505::-;36192:22;36200:4;36206:7;36192;:22::i;:::-;36187:414;;36380:41;36408:7;-1:-1:-1;;;;;36380:41:0;36418:2;36380:19;:41::i;:::-;36494:38;36522:4;36529:2;36494:19;:38::i;:::-;36285:270;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;36285:270:0;;;;;;;;;;-1:-1:-1;;;36231:358:0;;;;;;;:::i;55900:321::-;56030:18;56036:2;56040:7;56030:5;:18::i;:::-;56081:54;56112:1;56116:2;56120:7;56129:5;56081:22;:54::i;:::-;56059:154;;;;-1:-1:-1;;;56059:154:0;;;;;;;:::i;10231:1308::-;10312:7;10321:12;10546:9;:16;10566:2;10546:22;10542:990;;10842:4;10827:20;;10821:27;10892:4;10877:20;;10871:27;10950:4;10935:20;;10929:27;10585:9;10921:36;10993:25;11004:4;10921:36;10821:27;10871;10993:10;:25::i;:::-;10986:32;;;;;;;;;10542:990;11040:9;:16;11060:2;11040:22;11036:496;;11315:4;11300:20;;11294:27;11366:4;11351:20;;11345:27;11408:23;11419:4;11294:27;11345;11408:10;:23::i;:::-;11401:30;;;;;;;;11036:496;-1:-1:-1;11480:1:0;;-1:-1:-1;11484:35:0;11036:496;10231:1308;;;;;:::o;8502:643::-;8580:20;8571:5;:29;;;;;;;;:::i;:::-;;8567:571;;8502:643;:::o;8567:571::-;8678:29;8669:5;:38;;;;;;;;:::i;:::-;;8665:473;;8724:34;;-1:-1:-1;;;8724:34:0;;33004:2:1;8724:34:0;;;32986:21:1;33043:2;33023:18;;;33016:30;33082:26;33062:18;;;33055:54;33126:18;;8724:34:0;32802:348:1;8665:473:0;8789:35;8780:5;:44;;;;;;;;:::i;:::-;;8776:362;;8841:41;;-1:-1:-1;;;8841:41:0;;33357:2:1;8841:41:0;;;33339:21:1;33396:2;33376:18;;;33369:30;33435:33;33415:18;;;33408:61;33486:18;;8841:41:0;33155:355:1;8776:362:0;8913:30;8904:5;:39;;;;;;;;:::i;:::-;;8900:238;;8960:44;;-1:-1:-1;;;8960:44:0;;33717:2:1;8960:44:0;;;33699:21:1;33756:2;33736:18;;;33729:30;33795:34;33775:18;;;33768:62;-1:-1:-1;;;33846:18:1;;;33839:32;33888:19;;8960:44:0;33515:398:1;8900:238:0;9035:30;9026:5;:39;;;;;;;;:::i;:::-;;9022:116;;9082:44;;-1:-1:-1;;;9082:44:0;;34120:2:1;9082:44:0;;;34102:21:1;34159:2;34139:18;;;34132:30;34198:34;34178:18;;;34171:62;-1:-1:-1;;;34249:18:1;;;34242:32;34291:19;;9082:44:0;33918:398:1;59921:799:0;60076:4;-1:-1:-1;;;;;60097:13:0;;22409:19;:23;60093:620;;60133:72;;-1:-1:-1;;;60133:72:0;;-1:-1:-1;;;;;60133:36:0;;;;;:72;;18217:10;;60184:4;;60190:7;;60199:5;;60133:72;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;-1:-1:-1;60133:72:0;;;;;;;;-1:-1:-1;;60133:72:0;;;;;;;;;;;;:::i;:::-;;;60129:529;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;60375:6;:13;60392:1;60375:18;60371:272;;60418:60;;-1:-1:-1;;;60418:60:0;;;;;;;:::i;60371:272::-;60593:6;60587:13;60578:6;60574:2;60570:15;60563:38;60129:529;-1:-1:-1;;;;;;60256:51:0;-1:-1:-1;;;60256:51:0;;-1:-1:-1;60249:58:0;;60093:620;-1:-1:-1;60697:4:0;59921:799;;;;;;:::o;48820:305::-;48922:4;-1:-1:-1;;;;;;48959:40:0;;-1:-1:-1;;;48959:40:0;;:105;;-1:-1:-1;;;;;;;49016:48:0;;-1:-1:-1;;;49016:48:0;48959:105;:158;;;-1:-1:-1;;;;;;;;;;32329:40:0;;;49081:36;32220:157;66725:988;66991:22;67041:1;67016:22;67033:4;67016:16;:22::i;:::-;:26;;;;:::i;:::-;67053:18;67074:26;;;:17;:26;;;;;;66991:51;;-1:-1:-1;67207:28:0;;;67203:328;;-1:-1:-1;;;;;67274:18:0;;67252:19;67274:18;;;:12;:18;;;;;;;;:34;;;;;;;;;67325:30;;;;;;:44;;;67442:30;;:17;:30;;;;;:43;;;67203:328;-1:-1:-1;67627:26:0;;;;:17;:26;;;;;;;;67620:33;;;-1:-1:-1;;;;;67671:18:0;;;;;:12;:18;;;;;:34;;;;;;;67664:41;66725:988::o;68008:1079::-;68286:10;:17;68261:22;;68286:21;;68306:1;;68286:21;:::i;:::-;68318:18;68339:24;;;:15;:24;;;;;;68712:10;:26;;68261:46;;-1:-1:-1;68339:24:0;;68261:46;;68712:26;;;;;;:::i;:::-;;;;;;;;;68690:48;;68776:11;68751:10;68762;68751:22;;;;;;;;:::i;:::-;;;;;;;;;;;;:36;;;;68856:28;;;:15;:28;;;;;;;:41;;;69028:24;;;;;69021:31;69063:10;:16;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;68079:1008;;;68008:1079;:::o;65512:221::-;65597:14;65614:20;65631:2;65614:16;:20::i;:::-;-1:-1:-1;;;;;65645:16:0;;;;;;;:12;:16;;;;;;;;:24;;;;;;;;:34;;;65690:26;;;:17;:26;;;;;;:35;;;;-1:-1:-1;65512:221:0:o;7466:451::-;7541:13;7567:19;7599:10;7603:6;7599:1;:10;:::i;:::-;:14;;7612:1;7599:14;:::i;:::-;-1:-1:-1;;;;;7589:25:0;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;7589:25:0;;7567:47;;-1:-1:-1;;;7625:6:0;7632:1;7625:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;7625:15:0;;;;;;;;;-1:-1:-1;;;7651:6:0;7658:1;7651:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;7651:15:0;;;;;;;;-1:-1:-1;7682:9:0;7694:10;7698:6;7694:1;:10;:::i;:::-;:14;;7707:1;7694:14;:::i;:::-;7682:26;;7677:135;7714:1;7710;:5;7677:135;;;-1:-1:-1;;;7762:5:0;7770:3;7762:11;7749:25;;;;;;;:::i;:::-;;;;7737:6;7744:1;7737:9;;;;;;;;:::i;:::-;;;;:37;-1:-1:-1;;;;;7737:37:0;;;;;;;;-1:-1:-1;7799:1:0;7789:11;;;;;7717:3;;;:::i;:::-;;;7677:135;;;-1:-1:-1;7830:10:0;;7822:55;;;;-1:-1:-1;;;7822:55:0;;35544:2:1;7822:55:0;;;35526:21:1;;;35563:18;;;35556:30;35622:34;35602:18;;;35595:62;35674:18;;7822:55:0;35342:356:1;56557:439:0;-1:-1:-1;;;;;56637:16:0;;56629:61;;;;-1:-1:-1;;;56629:61:0;;35905:2:1;56629:61:0;;;35887:21:1;;;35924:18;;;35917:30;35983:34;35963:18;;;35956:62;36035:18;;56629:61:0;35703:356:1;56629:61:0;54644:4;54668:16;;;:7;:16;;;;;;-1:-1:-1;;;;;54668:16:0;:30;56701:58;;;;-1:-1:-1;;;56701:58:0;;36266:2:1;56701:58:0;;;36248:21:1;36305:2;36285:18;;;36278:30;36344;36324:18;;;36317:58;36392:18;;56701:58:0;36064:352:1;56701:58:0;56772:45;56801:1;56805:2;56809:7;56772:20;:45::i;:::-;-1:-1:-1;;;;;56830:13:0;;;;;;:9;:13;;;;;:18;;56847:1;;56830:13;:18;;56847:1;;56830:18;:::i;:::-;;;;-1:-1:-1;;56859:16:0;;;;:7;:16;;;;;;:21;;-1:-1:-1;;;;;;56859:21:0;-1:-1:-1;;;;;56859:21:0;;;;;;;;56898:33;;56859:16;;;56898:33;;56859:16;;56898:33;77788:821;;:::o;13793:1632::-;13924:7;;14858:66;14845:79;;14841:163;;;-1:-1:-1;14957:1:0;;-1:-1:-1;14961:30:0;14941:51;;14841:163;15018:1;:7;;15023:2;15018:7;;:18;;;;;15029:1;:7;;15034:2;15029:7;;15018:18;15014:102;;;-1:-1:-1;15069:1:0;;-1:-1:-1;15073:30:0;15053:51;;15014:102;15230:24;;;15213:14;15230:24;;;;;;;;;36648:25:1;;;36721:4;36709:17;;36689:18;;;36682:45;;;;36743:18;;;36736:34;;;36786:18;;;36779:34;;;15230:24:0;;36620:19:1;;15230:24:0;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;15230:24:0;;-1:-1:-1;;15230:24:0;;;-1:-1:-1;;;;;;;15269:20:0;;15265:103;;15322:1;15326:29;15306:50;;;;;;;15265:103;15388:6;-1:-1:-1;15396:20:0;;-1:-1:-1;13793:1632:0;;;;;;;;:::o;12835:344::-;12949:7;;-1:-1:-1;;;;;12995:80:0;;12949:7;13102:25;13118:3;13103:18;;;13125:2;13102:25;:::i;:::-;13086:42;;13146:25;13157:4;13163:1;13166;13169;13146:10;:25::i;:::-;13139:32;;;;;;12835:344;;;;;;:::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;592:250::-;677:1;687:113;701:6;698:1;695:13;687:113;;;777:11;;;771:18;758:11;;;751:39;723:2;716:10;687:113;;;-1:-1:-1;;834:1:1;816:16;;809:27;592:250::o;847:271::-;889:3;927:5;921:12;954:6;949:3;942:19;970:76;1039:6;1032:4;1027:3;1023:14;1016:4;1009:5;1005:16;970:76;:::i;:::-;1100:2;1079:15;-1:-1:-1;;1075:29:1;1066:39;;;;1107:4;1062:50;;847:271;-1:-1:-1;;847:271:1:o;1123:220::-;1272:2;1261:9;1254:21;1235:4;1292:45;1333:2;1322:9;1318:18;1310:6;1292:45;:::i;1348:180::-;1407:6;1460:2;1448:9;1439:7;1435:23;1431:32;1428:52;;;1476:1;1473;1466:12;1428:52;-1:-1:-1;1499:23:1;;1348:180;-1:-1:-1;1348:180:1:o;1741:173::-;1809:20;;-1:-1:-1;;;;;1858:31:1;;1848:42;;1838:70;;1904:1;1901;1894:12;1838:70;1741:173;;;:::o;1919:254::-;1987:6;1995;2048:2;2036:9;2027:7;2023:23;2019:32;2016:52;;;2064:1;2061;2054:12;2016:52;2087:29;2106:9;2087:29;:::i;:::-;2077:39;2163:2;2148:18;;;;2135:32;;-1:-1:-1;;;1919:254:1:o;2178:160::-;2243:20;;2299:13;;2292:21;2282:32;;2272:60;;2328:1;2325;2318:12;2343:248;2408:6;2416;2469:2;2457:9;2448:7;2444:23;2440:32;2437:52;;;2485:1;2482;2475:12;2437:52;2521:9;2508:23;2498:33;;2550:35;2581:2;2570:9;2566:18;2550:35;:::i;:::-;2540:45;;2343:248;;;;;:::o;2778:348::-;2830:8;2840:6;2894:3;2887:4;2879:6;2875:17;2871:27;2861:55;;2912:1;2909;2902:12;2861:55;-1:-1:-1;2935:20:1;;-1:-1:-1;;;;;2967:30:1;;2964:50;;;3010:1;3007;3000:12;2964:50;3047:4;3039:6;3035:17;3023:29;;3099:3;3092:4;3083:6;3075;3071:19;3067:30;3064:39;3061:59;;;3116:1;3113;3106:12;3131:547;3217:6;3225;3233;3241;3294:2;3282:9;3273:7;3269:23;3265:32;3262:52;;;3310:1;3307;3300:12;3262:52;3346:9;3333:23;3323:33;;3375:35;3406:2;3395:9;3391:18;3375:35;:::i;:::-;3365:45;;3461:2;3450:9;3446:18;3433:32;-1:-1:-1;;;;;3480:6:1;3477:30;3474:50;;;3520:1;3517;3510:12;3474:50;3559:59;3610:7;3601:6;3590:9;3586:22;3559:59;:::i;:::-;3131:547;;;;-1:-1:-1;3637:8:1;-1:-1:-1;;;;3131:547:1:o;3683:248::-;3751:6;3759;3812:2;3800:9;3791:7;3787:23;3783:32;3780:52;;;3828:1;3825;3818:12;3780:52;-1:-1:-1;;3851:23:1;;;3921:2;3906:18;;;3893:32;;-1:-1:-1;3683:248:1:o;3936:328::-;4013:6;4021;4029;4082:2;4070:9;4061:7;4057:23;4053:32;4050:52;;;4098:1;4095;4088:12;4050:52;4121:29;4140:9;4121:29;:::i;:::-;4111:39;;4169:38;4203:2;4192:9;4188:18;4169:38;:::i;:::-;4159:48;;4254:2;4243:9;4239:18;4226:32;4216:42;;3936:328;;;;;:::o;4636:254::-;4704:6;4712;4765:2;4753:9;4744:7;4740:23;4736:32;4733:52;;;4781:1;4778;4771:12;4733:52;4817:9;4804:23;4794:33;;4846:38;4880:2;4869:9;4865:18;4846:38;:::i;4895:599::-;5172:6;5161:9;5154:25;5215:6;5210:2;5199:9;5195:18;5188:34;5258:6;5253:2;5242:9;5238:18;5231:34;5315:6;5308:14;5301:22;5296:2;5285:9;5281:18;5274:50;5375:6;5368:14;5361:22;5355:3;5344:9;5340:19;5333:51;5421:3;5415;5404:9;5400:19;5393:32;5135:4;5442:46;5483:3;5472:9;5468:19;5460:6;5442:46;:::i;:::-;5434:54;4895:599;-1:-1:-1;;;;;;;;4895:599:1:o;5499:186::-;5558:6;5611:2;5599:9;5590:7;5586:23;5582:32;5579:52;;;5627:1;5624;5617:12;5579:52;5650:29;5669:9;5650:29;:::i;5690:479::-;5770:6;5778;5786;5839:2;5827:9;5818:7;5814:23;5810:32;5807:52;;;5855:1;5852;5845:12;5807:52;5891:9;5878:23;5868:33;;5952:2;5941:9;5937:18;5924:32;-1:-1:-1;;;;;5971:6:1;5968:30;5965:50;;;6011:1;6008;6001:12;5965:50;6050:59;6101:7;6092:6;6081:9;6077:22;6050:59;:::i;:::-;5690:479;;6128:8;;-1:-1:-1;6024:85:1;;-1:-1:-1;;;;5690:479:1:o;6174:322::-;6251:6;6259;6267;6320:2;6308:9;6299:7;6295:23;6291:32;6288:52;;;6336:1;6333;6326:12;6288:52;6359:29;6378:9;6359:29;:::i;:::-;6349:39;6435:2;6420:18;;6407:32;;-1:-1:-1;6486:2:1;6471:18;;;6458:32;;6174:322;-1:-1:-1;;;6174:322:1:o;6501:127::-;6562:10;6557:3;6553:20;6550:1;6543:31;6593:4;6590:1;6583:15;6617:4;6614:1;6607:15;6633:275;6704:2;6698:9;6769:2;6750:13;;-1:-1:-1;;6746:27:1;6734:40;;-1:-1:-1;;;;;6789:34:1;;6825:22;;;6786:62;6783:88;;;6851:18;;:::i;:::-;6887:2;6880:22;6633:275;;-1:-1:-1;6633:275:1:o;6913:182::-;6972:4;-1:-1:-1;;;;;6997:6:1;6994:30;6991:56;;;7027:18;;:::i;:::-;-1:-1:-1;7072:1:1;7068:14;7084:4;7064:25;;6913:182::o;7100:531::-;7143:5;7196:3;7189:4;7181:6;7177:17;7173:27;7163:55;;7214:1;7211;7204:12;7163:55;7250:6;7237:20;-1:-1:-1;;;;;7272:2:1;7269:26;7266:52;;;7298:18;;:::i;:::-;7342:55;7385:2;7366:13;;-1:-1:-1;;7362:27:1;7391:4;7358:38;7342:55;:::i;:::-;7422:2;7413:7;7406:19;7468:3;7461:4;7456:2;7448:6;7444:15;7440:26;7437:35;7434:55;;;7485:1;7482;7475:12;7434:55;7550:2;7543:4;7535:6;7531:17;7524:4;7515:7;7511:18;7498:55;7598:1;7573:16;;;7591:4;7569:27;7562:38;;;;7577:7;7100:531;-1:-1:-1;;;7100:531:1:o;7636:1132::-;7730:6;7761:2;7804;7792:9;7783:7;7779:23;7775:32;7772:52;;;7820:1;7817;7810:12;7772:52;7860:9;7847:23;-1:-1:-1;;;;;7930:2:1;7922:6;7919:14;7916:34;;;7946:1;7943;7936:12;7916:34;7984:6;7973:9;7969:22;7959:32;;8029:7;8022:4;8018:2;8014:13;8010:27;8000:55;;8051:1;8048;8041:12;8000:55;8087:2;8074:16;8110:59;8126:42;8165:2;8126:42;:::i;:::-;8110:59;:::i;:::-;8203:15;;;8285:1;8281:10;;;;8273:19;;8269:28;;;8234:12;;;;8309:19;;;8306:39;;;8341:1;8338;8331:12;8306:39;8373:2;8369;8365:11;8385:353;8401:6;8396:3;8393:15;8385:353;;;8487:3;8474:17;8523:2;8510:11;8507:19;8504:109;;;8567:1;8596:2;8592;8585:14;8504:109;8638:57;8687:7;8682:2;8668:11;8664:2;8660:20;8656:29;8638:57;:::i;:::-;8626:70;;-1:-1:-1;8716:12:1;;;;8418;;8385:353;;;-1:-1:-1;8757:5:1;7636:1132;-1:-1:-1;;;;;;;;7636:1132:1:o;8773:632::-;8944:2;8996:21;;;9066:13;;8969:18;;;9088:22;;;8915:4;;8944:2;9167:15;;;;9141:2;9126:18;;;8915:4;9210:169;9224:6;9221:1;9218:13;9210:169;;;9285:13;;9273:26;;9354:15;;;;9319:12;;;;9246:1;9239:9;9210:169;;;-1:-1:-1;9396:3:1;;8773:632;-1:-1:-1;;;;;;8773:632:1:o;9410:595::-;9514:6;9522;9530;9538;9546;9599:3;9587:9;9578:7;9574:23;9570:33;9567:53;;;9616:1;9613;9606:12;9567:53;9652:9;9639:23;9629:33;;9709:2;9698:9;9694:18;9681:32;9671:42;;9760:2;9749:9;9745:18;9732:32;9722:42;;9811:2;9800:9;9796:18;9783:32;9773:42;;9866:3;9855:9;9851:19;9838:33;-1:-1:-1;;;;;9886:6:1;9883:30;9880:50;;;9926:1;9923;9916:12;9880:50;9949;9991:7;9982:6;9971:9;9967:22;9949:50;:::i;:::-;9939:60;;;9410:595;;;;;;;;:::o;10010:322::-;10079:6;10132:2;10120:9;10111:7;10107:23;10103:32;10100:52;;;10148:1;10145;10138:12;10100:52;10188:9;10175:23;-1:-1:-1;;;;;10213:6:1;10210:30;10207:50;;;10253:1;10250;10243:12;10207:50;10276;10318:7;10309:6;10298:9;10294:22;10276:50;:::i;10337:254::-;10402:6;10410;10463:2;10451:9;10442:7;10438:23;10434:32;10431:52;;;10479:1;10476;10469:12;10431:52;10502:29;10521:9;10502:29;:::i;:::-;10492:39;;10550:35;10581:2;10570:9;10566:18;10550:35;:::i;10596:964::-;10689:6;10697;10750:2;10738:9;10729:7;10725:23;10721:32;10718:52;;;10766:1;10763;10756:12;10718:52;10789:29;10808:9;10789:29;:::i;:::-;10779:39;;10837:2;10890;10879:9;10875:18;10862:32;-1:-1:-1;;;;;10909:6:1;10906:30;10903:50;;;10949:1;10946;10939:12;10903:50;10972:22;;11025:4;11017:13;;11013:27;-1:-1:-1;11003:55:1;;11054:1;11051;11044:12;11003:55;11090:2;11077:16;11113:59;11129:42;11168:2;11129:42;:::i;11113:59::-;11206:15;;;11288:1;11284:10;;;;11276:19;;11272:28;;;11237:12;;;;11312:19;;;11309:39;;;11344:1;11341;11334:12;11309:39;11368:11;;;;11388:142;11404:6;11399:3;11396:15;11388:142;;;11470:17;;11458:30;;11421:12;;;;11508;;;;11388:142;;;11549:5;11539:15;;;;;;;10596:964;;;;;:::o;11565:538::-;11660:6;11668;11676;11684;11737:3;11725:9;11716:7;11712:23;11708:33;11705:53;;;11754:1;11751;11744:12;11705:53;11777:29;11796:9;11777:29;:::i;:::-;11767:39;;11825:38;11859:2;11848:9;11844:18;11825:38;:::i;:::-;11815:48;;11910:2;11899:9;11895:18;11882:32;11872:42;;11965:2;11954:9;11950:18;11937:32;-1:-1:-1;;;;;11984:6:1;11981:30;11978:50;;;12024:1;12021;12014:12;11978:50;12047;12089:7;12080:6;12069:9;12065:22;12047:50;:::i;:::-;12037:60;;;11565:538;;;;;;;:::o;12108:316::-;12176:6;12184;12192;12245:2;12233:9;12224:7;12220:23;12216:32;12213:52;;;12261:1;12258;12251:12;12213:52;12284:26;12300:9;12284:26;:::i;:::-;12274:36;;12329:35;12360:2;12349:9;12345:18;12329:35;:::i;:::-;12319:45;;12383:35;12414:2;12403:9;12399:18;12383:35;:::i;:::-;12373:45;;12108:316;;;;;:::o;12429:385::-;12515:6;12523;12531;12539;12592:3;12580:9;12571:7;12567:23;12563:33;12560:53;;;12609:1;12606;12599:12;12560:53;-1:-1:-1;;12632:23:1;;;12702:2;12687:18;;12674:32;;-1:-1:-1;12753:2:1;12738:18;;12725:32;;12804:2;12789:18;12776:32;;-1:-1:-1;12429:385:1;-1:-1:-1;12429:385:1:o;12819:260::-;12887:6;12895;12948:2;12936:9;12927:7;12923:23;12919:32;12916:52;;;12964:1;12961;12954:12;12916:52;12987:29;13006:9;12987:29;:::i;:::-;12977:39;;13035:38;13069:2;13058:9;13054:18;13035:38;:::i;13084:380::-;13163:1;13159:12;;;;13206;;;13227:61;;13281:4;13273:6;13269:17;13259:27;;13227:61;13334:2;13326:6;13323:14;13303:18;13300:38;13297:161;;13380:10;13375:3;13371:20;13368:1;13361:31;13415:4;13412:1;13405:15;13443:4;13440:1;13433:15;13297:161;;13084:380;;;:::o;14709:356::-;14911:2;14893:21;;;14930:18;;;14923:30;14989:34;14984:2;14969:18;;14962:62;15056:2;15041:18;;14709:356::o;15196:545::-;15298:2;15293:3;15290:11;15287:448;;;15334:1;15359:5;15355:2;15348:17;15404:4;15400:2;15390:19;15474:2;15462:10;15458:19;15455:1;15451:27;15445:4;15441:38;15510:4;15498:10;15495:20;15492:47;;;-1:-1:-1;15533:4:1;15492:47;15588:2;15583:3;15579:12;15576:1;15572:20;15566:4;15562:31;15552:41;;15643:82;15661:2;15654:5;15651:13;15643:82;;;15706:17;;;15687:1;15676:13;15643:82;;15917:1206;-1:-1:-1;;;;;16036:3:1;16033:27;16030:53;;;16063:18;;:::i;:::-;16092:94;16182:3;16142:38;16174:4;16168:11;16142:38;:::i;:::-;16136:4;16092:94;:::i;:::-;16212:1;16237:2;16232:3;16229:11;16254:1;16249:616;;;;16909:1;16926:3;16923:93;;;-1:-1:-1;16982:19:1;;;16969:33;16923:93;-1:-1:-1;;15874:1:1;15870:11;;;15866:24;15862:29;15852:40;15898:1;15894:11;;;15849:57;17029:78;;16222:895;;16249:616;15143:1;15136:14;;;15180:4;15167:18;;-1:-1:-1;;16285:17:1;;;16386:9;16408:229;16422:7;16419:1;16416:14;16408:229;;;16511:19;;;16498:33;16483:49;;16618:4;16603:20;;;;16571:1;16559:14;;;;16438:12;16408:229;;;16412:3;16665;16656:7;16653:16;16650:159;;;16789:1;16785:6;16779:3;16773;16770:1;16766:11;16762:21;16758:34;16754:39;16741:9;16736:3;16732:19;16719:33;16715:79;16707:6;16700:95;16650:159;;;16852:1;16846:3;16843:1;16839:11;16835:19;16829:4;16822:33;16222:895;;15917:1206;;;:::o;17128:355::-;17330:2;17312:21;;;17369:2;17349:18;;;17342:30;17408:33;17403:2;17388:18;;17381:61;17474:2;17459:18;;17128:355::o;17835:340::-;18037:2;18019:21;;;18076:2;18056:18;;;18049:30;-1:-1:-1;;;18110:2:1;18095:18;;18088:46;18166:2;18151:18;;17835:340::o;18180:127::-;18241:10;18236:3;18232:20;18229:1;18222:31;18272:4;18269:1;18262:15;18296:4;18293:1;18286:15;18312:168;18352:7;18418:1;18414;18410:6;18406:14;18403:1;18400:21;18395:1;18388:9;18381:17;18377:45;18374:71;;;18425:18;;:::i;:::-;-1:-1:-1;18465:9:1;;18312:168::o;18827:125::-;18892:9;;;18913:10;;;18910:36;;;18926:18;;:::i;19308:413::-;19510:2;19492:21;;;19549:2;19529:18;;;19522:30;19588:34;19583:2;19568:18;;19561:62;-1:-1:-1;;;19654:2:1;19639:18;;19632:47;19711:3;19696:19;;19308:413::o;20967:127::-;21028:10;21023:3;21019:20;21016:1;21009:31;21059:4;21056:1;21049:15;21083:4;21080:1;21073:15;22957:1352;23083:3;23077:10;-1:-1:-1;;;;;23102:6:1;23099:30;23096:56;;;23132:18;;:::i;:::-;23161:97;23251:6;23211:38;23243:4;23237:11;23211:38;:::i;:::-;23205:4;23161:97;:::i;:::-;23313:4;;23377:2;23366:14;;23394:1;23389:663;;;;24096:1;24113:6;24110:89;;;-1:-1:-1;24165:19:1;;;24159:26;24110:89;-1:-1:-1;;15874:1:1;15870:11;;;15866:24;15862:29;15852:40;15898:1;15894:11;;;15849:57;24212:81;;23359:944;;23389:663;15143:1;15136:14;;;15180:4;15167:18;;-1:-1:-1;;23425:20:1;;;23543:236;23557:7;23554:1;23551:14;23543:236;;;23646:19;;;23640:26;23625:42;;23738:27;;;;23706:1;23694:14;;;;23573:19;;23543:236;;;23547:3;23807:6;23798:7;23795:19;23792:201;;;23868:19;;;23862:26;-1:-1:-1;;23951:1:1;23947:14;;;23963:3;23943:24;23939:37;23935:42;23920:58;23905:74;;23792:201;-1:-1:-1;;;;;24039:1:1;24023:14;;;24019:22;24006:36;;-1:-1:-1;22957:1352:1:o;24314:135::-;24353:3;24374:17;;;24371:43;;24394:18;;:::i;:::-;-1:-1:-1;24441:1:1;24430:13;;24314:135::o;26565:663::-;26845:3;26883:6;26877:13;26899:66;26958:6;26953:3;26946:4;26938:6;26934:17;26899:66;:::i;:::-;27028:13;;26987:16;;;;27050:70;27028:13;26987:16;27097:4;27085:17;;27050:70;:::i;:::-;-1:-1:-1;;;27142:20:1;;27171:22;;;27220:1;27209:13;;26565:663;-1:-1:-1;;;;26565:663:1:o;27233:289::-;27364:3;27402:6;27396:13;27418:66;27477:6;27472:3;27465:4;27457:6;27453:17;27418:66;:::i;:::-;27500:16;;;;;27233:289;-1:-1:-1;;27233:289:1:o;29500:128::-;29567:9;;;29588:11;;;29585:37;;;29602:18;;:::i;30372:414::-;30574:2;30556:21;;;30613:2;30593:18;;;30586:30;30652:34;30647:2;30632:18;;30625:62;-1:-1:-1;;;30718:2:1;30703:18;;30696:48;30776:3;30761:19;;30372:414::o;30791:127::-;30852:10;30847:3;30843:20;30840:1;30833:31;30883:4;30880:1;30873:15;30907:4;30904:1;30897:15;30923:120;30963:1;30989;30979:35;;30994:18;;:::i;:::-;-1:-1:-1;31028:9:1;;30923:120::o;31048:112::-;31080:1;31106;31096:35;;31111:18;;:::i;:::-;-1:-1:-1;31145:9:1;;31048:112::o;31853:812::-;32264:25;32259:3;32252:38;32234:3;32319:6;32313:13;32335:75;32403:6;32398:2;32393:3;32389:12;32382:4;32374:6;32370:17;32335:75;:::i;:::-;-1:-1:-1;;;32469:2:1;32429:16;;;32461:11;;;32454:40;32519:13;;32541:76;32519:13;32603:2;32595:11;;32588:4;32576:17;;32541:76;:::i;:::-;32637:17;32656:2;32633:26;;31853:812;-1:-1:-1;;;;31853:812:1:o;32670:127::-;32731:10;32726:3;32722:20;32719:1;32712:31;32762:4;32759:1;32752:15;32786:4;32783:1;32776:15;34321:489;-1:-1:-1;;;;;34590:15:1;;;34572:34;;34642:15;;34637:2;34622:18;;34615:43;34689:2;34674:18;;34667:34;;;34737:3;34732:2;34717:18;;34710:31;;;34515:4;;34758:46;;34784:19;;34776:6;34758:46;:::i;:::-;34750:54;34321:489;-1:-1:-1;;;;;;34321:489:1:o;34815:249::-;34884:6;34937:2;34925:9;34916:7;34912:23;34908:32;34905:52;;;34953:1;34950;34943:12;34905:52;34985:9;34979:16;35004:30;35028:5;35004:30;:::i;35069:127::-;35130:10;35125:3;35121:20;35118:1;35111:31;35161:4;35158:1;35151:15;35185:4;35182:1;35175:15;35201:136;35240:3;35268:5;35258:39;;35277:18;;:::i;:::-;-1:-1:-1;;;35313:18:1;;35201:136::o

Swarm Source

ipfs://6988be08ea1530646aaea37855dfbb18943d4326bede86f2160a9ddd45e939d6
Loading...
Loading
Loading...
Loading
[ Download: CSV Export  ]
[ Download: CSV Export  ]

A token is a representation of an on-chain or off-chain asset. The token page shows information such as price, total supply, holders, transfers and social links. Learn more about this page in our Knowledge Base.