Feature Tip: Add private address tag to any address under My Name Tag !
Overview
ETH Balance
0 ETH
Eth Value
$0.00More Info
Private Name Tags
ContractCreator
TokenTracker
Latest 25 from a total of 210 transactions
Transaction Hash |
Method
|
Block
|
From
|
To
|
|||||
---|---|---|---|---|---|---|---|---|---|
Safe Transfer Fr... | 17402626 | 513 days ago | IN | 0 ETH | 0.00131981 | ||||
Set Approval For... | 17335000 | 522 days ago | IN | 0 ETH | 0.00121112 | ||||
Transfer From | 17115732 | 553 days ago | IN | 0 ETH | 0.00273246 | ||||
Safe Transfer Fr... | 17115688 | 553 days ago | IN | 0 ETH | 0.00986928 | ||||
Set Approval For... | 17026355 | 566 days ago | IN | 0 ETH | 0.00129323 | ||||
Mint | 17012061 | 568 days ago | IN | 0 ETH | 0.01054703 | ||||
Set | 17011982 | 568 days ago | IN | 0 ETH | 0.00521721 | ||||
Set | 17011981 | 568 days ago | IN | 0 ETH | 0.00444547 | ||||
Set | 17011980 | 568 days ago | IN | 0 ETH | 0.00601675 | ||||
Set | 17011979 | 568 days ago | IN | 0 ETH | 0.01184408 | ||||
Set | 17011978 | 568 days ago | IN | 0 ETH | 0.0041308 | ||||
Set | 17011977 | 568 days ago | IN | 0 ETH | 0.00437746 | ||||
Set | 17011976 | 568 days ago | IN | 0 ETH | 0.00591356 | ||||
Set | 17011975 | 568 days ago | IN | 0 ETH | 0.00711911 | ||||
Set | 17011974 | 568 days ago | IN | 0 ETH | 0.00643757 | ||||
Set | 17011973 | 568 days ago | IN | 0 ETH | 0.00628183 | ||||
Set | 17011970 | 568 days ago | IN | 0 ETH | 0.00883929 | ||||
Set | 17011962 | 568 days ago | IN | 0 ETH | 0.00541856 | ||||
Set | 17011961 | 568 days ago | IN | 0 ETH | 0.0041196 | ||||
Set | 17011902 | 568 days ago | IN | 0 ETH | 0.00303342 | ||||
Set | 17011901 | 568 days ago | IN | 0 ETH | 0.00463101 | ||||
Set | 17011900 | 568 days ago | IN | 0 ETH | 0.0030239 | ||||
Set | 17011897 | 568 days ago | IN | 0 ETH | 0.00296518 | ||||
Set | 17011896 | 568 days ago | IN | 0 ETH | 0.00595302 | ||||
Set | 17011895 | 568 days ago | IN | 0 ETH | 0.00595111 |
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Loading...
Loading
Contract Name:
RomeoAndJuliape
Compiler Version
v0.8.4+commit.c7e474f2
Contract Source Code (Solidity)
/** *Submitted for verification at Etherscan.io on 2023-04-09 */ // Sources flattened with hardhat v2.9.2 https://hardhat.org // File contracts/dependencies/Context.sol /// @title Base64 /// @author Brecht Devos - <[email protected]> /// @notice Provides a function for encoding some bytes in base64 // import "@openzeppelin/contracts/utils/Strings.sol"; library Base64 { string internal constant TABLE = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; function encode(bytes memory data) internal pure returns (string memory) { if (data.length == 0) return ""; // load the table into memory string memory table = TABLE; // multiply by 4/3 rounded up uint256 encodedLen = 4 * ((data.length + 2) / 3); // add some extra buffer at the end required for the writing string memory result = new string(encodedLen + 32); assembly { // set the actual output length mstore(result, encodedLen) // prepare the lookup table let tablePtr := add(table, 1) // input ptr let dataPtr := data let endPtr := add(dataPtr, mload(data)) // result ptr, jump over length let resultPtr := add(result, 32) // run over the input, 3 bytes at a time for { } lt(dataPtr, endPtr) { } { dataPtr := add(dataPtr, 3) // read 3 bytes let input := mload(dataPtr) // write 4 characters mstore( resultPtr, shl(248, mload(add(tablePtr, and(shr(18, input), 0x3F)))) ) resultPtr := add(resultPtr, 1) mstore( resultPtr, shl(248, mload(add(tablePtr, and(shr(12, input), 0x3F)))) ) resultPtr := add(resultPtr, 1) mstore( resultPtr, shl(248, mload(add(tablePtr, and(shr(6, input), 0x3F)))) ) resultPtr := add(resultPtr, 1) mstore( resultPtr, shl(248, mload(add(tablePtr, and(input, 0x3F)))) ) resultPtr := add(resultPtr, 1) } // padding with '=' switch mod(mload(data), 3) case 1 { mstore(sub(resultPtr, 2), shl(240, 0x3d3d)) } case 2 { mstore(sub(resultPtr, 1), shl(248, 0x3d)) } } return result; } } /** * @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 contracts/dependencies/EnumerableSet.sol /** * @dev Library for managing * https://en.wikipedia.org/wiki/Set_(abstract_data_type)[sets] of primitive * types. * * Sets have the following properties: * * - Elements are added, removed, and checked for existence in constant time * (O(1)). * - Elements are enumerated in O(n). No guarantees are made on the ordering. * * ``` * contract Example { * // Add the library methods * using EnumerableSet for EnumerableSet.AddressSet; * * // Declare a set state variable * EnumerableSet.AddressSet private mySet; * } * ``` * * As of v3.0.0, only sets of type `address` (`AddressSet`) and `uint256` * (`UintSet`) are supported. */ library EnumerableSet { // To implement this library for multiple types with as little code // repetition as possible, we write it in terms of a generic Set type with // bytes32 values. // The Set implementation uses private functions, and user-facing // implementations (such as AddressSet) are just wrappers around the // underlying Set. // This means that we can only create new EnumerableSets for types that fit // in bytes32. struct Set { // Storage of set values bytes32[] _values; // Position of the value in the `values` array, plus 1 because index 0 // means a value is not in the set. mapping(bytes32 => uint256) _indexes; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function _add(Set storage set, bytes32 value) private returns (bool) { if (!_contains(set, value)) { set._values.push(value); // The value is stored at length-1, but we add 1 to all indexes // and use 0 as a sentinel value set._indexes[value] = set._values.length; return true; } else { return false; } } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function _remove(Set storage set, bytes32 value) private returns (bool) { // We read and store the value's index to prevent multiple reads from the same storage slot uint256 valueIndex = set._indexes[value]; if (valueIndex != 0) { // Equivalent to contains(set, value) // To delete an element from the _values array in O(1), we swap the element to delete with the last one in // the array, and then remove the last element (sometimes called as 'swap and pop'). // This modifies the order of the array, as noted in {at}. uint256 toDeleteIndex = valueIndex - 1; uint256 lastIndex = set._values.length - 1; if (lastIndex != toDeleteIndex) { bytes32 lastValue = set._values[lastIndex]; // Move the last value to the index where the value to delete is set._values[toDeleteIndex] = lastValue; // Update the index for the moved value set._indexes[lastValue] = valueIndex; // Replace lastValue's index to valueIndex } // Delete the slot where the moved value was stored set._values.pop(); // Delete the index for the deleted slot delete set._indexes[value]; return true; } else { return false; } } /** * @dev Returns true if the value is in the set. O(1). */ function _contains(Set storage set, bytes32 value) private view returns (bool) { return set._indexes[value] != 0; } /** * @dev Returns the number of values on the set. O(1). */ function _length(Set storage set) private view returns (uint256) { return set._values.length; } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function _at(Set storage set, uint256 index) private view returns (bytes32) { return set._values[index]; } /** * @dev Return the entire set in an array * * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that * this function has an unbounded cost, and using it as part of a state-changing function may render the function * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block. */ function _values(Set storage set) private view returns (bytes32[] memory) { return set._values; } // Bytes32Set struct Bytes32Set { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(Bytes32Set storage set, bytes32 value) internal returns (bool) { return _add(set._inner, value); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(Bytes32Set storage set, bytes32 value) internal returns (bool) { return _remove(set._inner, value); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(Bytes32Set storage set, bytes32 value) internal view returns (bool) { return _contains(set._inner, value); } /** * @dev Returns the number of values in the set. O(1). */ function length(Bytes32Set storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(Bytes32Set storage set, uint256 index) internal view returns (bytes32) { return _at(set._inner, index); } /** * @dev Return the entire set in an array * * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that * this function has an unbounded cost, and using it as part of a state-changing function may render the function * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block. */ function values(Bytes32Set storage set) internal view returns (bytes32[] memory) { return _values(set._inner); } // AddressSet struct AddressSet { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(AddressSet storage set, address value) internal returns (bool) { return _add(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(AddressSet storage set, address value) internal returns (bool) { return _remove(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(AddressSet storage set, address value) internal view returns (bool) { return _contains(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Returns the number of values in the set. O(1). */ function length(AddressSet storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(AddressSet storage set, uint256 index) internal view returns (address) { return address(uint160(uint256(_at(set._inner, index)))); } /** * @dev Return the entire set in an array * * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that * this function has an unbounded cost, and using it as part of a state-changing function may render the function * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block. */ function values(AddressSet storage set) internal view returns (address[] memory) { bytes32[] memory store = _values(set._inner); address[] memory result; assembly { result := store } return result; } // UintSet struct UintSet { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(UintSet storage set, uint256 value) internal returns (bool) { return _add(set._inner, bytes32(value)); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(UintSet storage set, uint256 value) internal returns (bool) { return _remove(set._inner, bytes32(value)); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(UintSet storage set, uint256 value) internal view returns (bool) { return _contains(set._inner, bytes32(value)); } /** * @dev Returns the number of values on the set. O(1). */ function length(UintSet storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(UintSet storage set, uint256 index) internal view returns (uint256) { return uint256(_at(set._inner, index)); } /** * @dev Return the entire set in an array * * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that * this function has an unbounded cost, and using it as part of a state-changing function may render the function * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block. */ function values(UintSet storage set) internal view returns (uint256[] memory) { bytes32[] memory store = _values(set._inner); uint256[] memory result; assembly { result := store } return result; } } // File contracts/dependencies/Address.sol /** * @dev Collection of functions related to the address type */ library Address { /** * @dev Returns whether the target address is a contract. * @param _addr Address to check. * @return addressCheck True if _addr is a contract, false if not. */ function isContract(address _addr) internal view returns (bool addressCheck) { // This method relies in extcodesize, which returns 0 for contracts in // construction, since the code is only stored at the end of the // constructor execution. // According to EIP-1052, 0x0 is the value returned for not-yet created accounts // and 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470 is returned // for accounts without code, i.e. `keccak256('')` bytes32 codehash; bytes32 accountHash = 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470; assembly { codehash := extcodehash(_addr) } // solhint-disable-line addressCheck = (codehash != 0x0 && codehash != accountHash); } /** * @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 contracts/dependencies/AccessControl.sol /** * @dev Contract module that allows children to implement role-based access * control mechanisms. * * 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 { using EnumerableSet for EnumerableSet.AddressSet; using Address for address; struct RoleData { EnumerableSet.AddressSet members; bytes32 adminRole; } mapping (bytes32 => RoleData) private _roles; bytes32 public constant DEFAULT_ADMIN_ROLE = 0x00; /** * @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 {_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) public view returns (bool) { return _roles[role].members.contains(account); } /** * @dev Returns the number of accounts that have `role`. Can be used * together with {getRoleMember} to enumerate all bearers of a role. */ function getRoleMemberCount(bytes32 role) public view returns (uint256) { return _roles[role].members.length(); } /** * @dev Returns one of the accounts that have `role`. `index` must be a * value between 0 and {getRoleMemberCount}, non-inclusive. * * Role bearers are not sorted in any particular way, and their ordering may * change at any point. * * WARNING: When using {getRoleMember} and {getRoleMemberCount}, make sure * you perform all queries on the same block. See the following * https://forum.openzeppelin.com/t/iterating-over-elements-on-enumerableset-in-openzeppelin-contracts/2296[forum post] * for more information. */ function getRoleMember(bytes32 role, uint256 index) public view returns (address) { return _roles[role].members.at(index); } /** * @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 returns (bytes32) { return _roles[role].adminRole; } /** * @dev Grants `role` to `account`. * * If `account` had not been already granted `role`, emits a {RoleGranted} * event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function grantRole(bytes32 role, address account) public virtual { require(hasRole(_roles[role].adminRole, _msgSender()), "AccessControl: sender must be an admin to grant"); _grantRole(role, account); } /** * @dev Revokes `role` from `account`. * * If `account` had been granted `role`, emits a {RoleRevoked} event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function revokeRole(bytes32 role, address account) public virtual { require(hasRole(_roles[role].adminRole, _msgSender()), "AccessControl: sender must be an admin to revoke"); _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 granted `role`, emits a {RoleRevoked} * event. * * Requirements: * * - the caller must be `account`. */ function renounceRole(bytes32 role, address account) public virtual { require(account == _msgSender(), "AccessControl: can only renounce roles for self"); _revokeRole(role, account); } /** * @dev Grants `role` to `account`. * * If `account` had not been already granted `role`, emits a {RoleGranted} * event. Note that unlike {grantRole}, this function doesn't perform any * checks on the calling account. * * [WARNING] * ==== * This function should only be called from the constructor when setting * up the initial roles for the system. * * Using this function in any other way is effectively circumventing the admin * system imposed by {AccessControl}. * ==== */ 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 { emit RoleAdminChanged(role, _roles[role].adminRole, adminRole); _roles[role].adminRole = adminRole; } function _grantRole(bytes32 role, address account) private { if (_roles[role].members.add(account)) { emit RoleGranted(role, account, _msgSender()); } } function _revokeRole(bytes32 role, address account) private { if (_roles[role].members.remove(account)) { emit RoleRevoked(role, account, _msgSender()); } } } // File contracts/dependencies/IERC165.sol /** * @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); /* function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return interfaceId == type(IERC165).interfaceId; } */ } // File contracts/dependencies/ERC165.sol /** * @dev Implementation of the {IERC165} interface. * * Contracts may inherit from this and call {_registerInterface} to declare * their support of an interface. */ contract ERC165 is IERC165 { /* * bytes4(keccak256('supportsInterface(bytes4)')) == 0x01ffc9a7 */ bytes4 private constant _INTERFACE_ID_ERC165 = 0x01ffc9a7; /** * @dev Mapping of interface ids to whether or not it's supported. */ mapping(bytes4 => bool) private _supportedInterfaces; constructor () { // Derived contracts need only register support for their own interfaces, // we register support for ERC165 itself here _registerInterface(_INTERFACE_ID_ERC165); } /** * @dev See {IERC165-supportsInterface}. * * Time complexity O(1), guaranteed to always use less than 30 000 gas. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return _supportedInterfaces[interfaceId]; } /** * @dev Registers the contract as an implementer of the interface defined by * `interfaceId`. Support of the actual ERC165 interface is automatic and * registering its interface id is not required. * * See {IERC165-supportsInterface}. * * Requirements: * * - `interfaceId` cannot be the ERC165 invalid interface (`0xffffffff`). */ function _registerInterface(bytes4 interfaceId) internal virtual { require(interfaceId != 0xffffffff, "ERC165: invalid interface id"); _supportedInterfaces[interfaceId] = true; } } // File contracts/dependencies/IERC721.sol /** * @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`, 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 Returns the account approved for `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function getApproved(uint256 tokenId) external view returns (address operator); /** * @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 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); /** * @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; } // File contracts/dependencies/IERC721Metadata.sol /** * @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 contracts/dependencies/IERC721Receiver.sol /** * @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 `IERC721.onERC721Received.selector`. */ function onERC721Received( address operator, address from, uint256 tokenId, bytes calldata data ) external returns (bytes4); } // File contracts/dependencies/Strings.sol /** * @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 contracts/dependencies/ERC721A.sol error ApprovalCallerNotOwnerNorApproved(); error ApprovalQueryForNonexistentToken(); error ApproveToCaller(); error ApprovalToCurrentOwner(); error BalanceQueryForZeroAddress(); error MintToZeroAddress(); error MintZeroQuantity(); error OwnerQueryForNonexistentToken(); error TransferCallerNotOwnerNorApproved(); error TransferFromIncorrectOwner(); error TransferToNonERC721ReceiverImplementer(); error TransferToZeroAddress(); error URIQueryForNonexistentToken(); /** * @dev Implementation of https://eips.ethereum.org/EIPS/eip-721[ERC721] Non-Fungible Token Standard, including * the Metadata extension. Built to optimize for lower gas during batch mints. * * Assumes serials are sequentially minted starting at _startTokenId() (defaults to 0, e.g. 0, 1, 2, 3..). * * Assumes that an owner cannot have more than 2**64 - 1 (max value of uint64) of supply. * * Assumes that the maximum token id cannot exceed 2**256 - 1 (max value of uint256). */ contract ERC721A is Context, ERC165, IERC721, IERC721Metadata { using Address for address; using Strings for uint256; mapping (address => bool) public whitelists; // Compiler will pack this into a single 256bit word. struct TokenOwnership { // The address of the owner. address addr; // Keeps track of the start time of ownership with minimal overhead for tokenomics. uint64 startTimestamp; // Whether the token has been burned. bool burned; } // Compiler will pack this into a single 256bit word. struct AddressData { // Realistically, 2**64-1 is more than enough. uint64 balance; // Keeps track of mint count with minimal overhead for tokenomics. uint64 numberMinted; // Keeps track of burn count with minimal overhead for tokenomics. uint64 numberBurned; // For miscellaneous variable(s) pertaining to the address // (e.g. number of whitelist mint slots used). // If there are multiple variables, please pack them into a uint64. uint64 aux; } // The tokenId of the next token to be minted. uint256 internal _currentIndex; // The number of tokens burned. uint256 internal _burnCounter; // uint256 public ind; // Token name string private _name; // Token symbol string private _symbol; // Base URI string private _baseURI; /** * @dev Internal function to set the base URI for all token IDs. It is * automatically added as a prefix to the value returned in {tokenURI}, * or to the token ID if {tokenURI} is empty. */ function _setBaseURI(string memory baseURI_) internal virtual { _baseURI = baseURI_; } /** * @dev Returns the base URI set via {_setBaseURI}. This will be * automatically added as a prefix in {tokenURI} to each token's URI, or * to the token ID if no specific URI is set for that token ID. */ function baseURI() public view returns (string memory) { return _baseURI; } // Mapping from token ID to ownership details // An empty struct value does not necessarily mean the token is unowned. See _ownershipOf implementation for details. mapping(uint256 => TokenOwnership) internal _ownerships; // Mapping owner address to address data mapping(address => AddressData) private _addressData; // Mapping from token ID to approved address mapping(uint256 => address) private _tokenApprovals; // Mapping from owner to operator approvals mapping(address => mapping(address => bool)) private _operatorApprovals; constructor(string memory name_, string memory symbol_) { _name = name_; _symbol = symbol_; _currentIndex = _startTokenId(); } /** * To change the starting tokenId, please override this function. */ function _startTokenId() internal view virtual returns (uint256) { return 1; } /** * @dev Burned tokens are calculated here, use _totalMinted() if you want to count just minted tokens. */ function totalSupply() public view returns (uint256) { // Counter underflow is impossible as _burnCounter cannot be incremented // more than _currentIndex - _startTokenId() times unchecked { return _currentIndex - _burnCounter - _startTokenId(); } } /** * Returns the total amount of tokens minted in the contract. */ function _totalMinted() internal view returns (uint256) { // Counter underflow is impossible as _currentIndex does not decrement, // and it is initialized to _startTokenId() unchecked { return _currentIndex - _startTokenId(); } } /** * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override(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 override returns (uint256) { if (owner == address(0)) revert BalanceQueryForZeroAddress(); return uint256(_addressData[owner].balance); } /** * Returns the number of tokens minted by `owner`. */ function _numberMinted(address owner) internal view returns (uint256) { return uint256(_addressData[owner].numberMinted); } /** * Returns the number of tokens burned by or on behalf of `owner`. */ function _numberBurned(address owner) internal view returns (uint256) { return uint256(_addressData[owner].numberBurned); } /** * Returns the auxillary data for `owner`. (e.g. number of whitelist mint slots used). */ function _getAux(address owner) internal view returns (uint64) { return _addressData[owner].aux; } /** * Sets the auxillary data for `owner`. (e.g. number of whitelist mint slots used). * If there are multiple variables, please pack them into a uint64. */ function _setAux(address owner, uint64 aux) internal { _addressData[owner].aux = aux; } /** * Gas spent here starts off proportional to the maximum mint batch size. * It gradually moves to O(1) as tokens get transferred around in the collection over time. */ function _ownershipOf(uint256 tokenId) internal view returns (TokenOwnership memory) { uint256 curr = tokenId; unchecked { if (_startTokenId() <= curr && curr < _currentIndex) { TokenOwnership memory ownership = _ownerships[curr]; if (!ownership.burned) { if (ownership.addr != address(0)) { return ownership; } // Invariant: // There will always be an ownership that has an address and is not burned // before an ownership that does not have an address and is not burned. // Hence, curr will not underflow. while (true) { curr--; ownership = _ownerships[curr]; if (ownership.addr != address(0)) { return ownership; } } } } } revert OwnerQueryForNonexistentToken(); } /** * @dev See {IERC721-ownerOf}. */ function ownerOf(uint256 tokenId) public view override returns (address) { return _ownershipOf(tokenId).addr; } /** * @dev See {IERC721Metadata-name}. */ function name() public view virtual override returns (string memory) { return _name; } /** * @dev See {IERC721Metadata-symbol}. */ function symbol() public view virtual override returns (string memory) { return _symbol; } /** * @dev See {IERC721Metadata-tokenURI}. */ function tokenURI(uint256 tokenId) public view virtual override returns (string memory) { if (!_exists(tokenId)) revert URIQueryForNonexistentToken(); string memory base_URI = baseURI(); return string(abi.encodePacked(_baseURI, tokenId.toString(), ".json")); } /** * @dev See {IERC721-approve}. */ function approve(address to, uint256 tokenId) public override { address owner = ERC721A.ownerOf(tokenId); if (to == owner) revert ApprovalToCurrentOwner(); if (_msgSender() != owner && !isApprovedForAll(owner, _msgSender())) { revert ApprovalCallerNotOwnerNorApproved(); } _approve(to, tokenId, owner); } /** * @dev See {IERC721-getApproved}. */ function getApproved(uint256 tokenId) public view override returns (address) { if (!_exists(tokenId)) revert ApprovalQueryForNonexistentToken(); return _tokenApprovals[tokenId]; } /** * @dev See {IERC721-setApprovalForAll}. */ function setApprovalForAll(address operator, bool approved) public virtual override { if (operator == _msgSender()) revert ApproveToCaller(); _operatorApprovals[_msgSender()][operator] = approved; emit ApprovalForAll(_msgSender(), operator, approved); } /** * @dev See {IERC721-isApprovedForAll}. */ function isApprovedForAll(address owner, address operator) public view virtual override returns (bool) { return _operatorApprovals[owner][operator]; } /** * @dev See {IERC721-transferFrom}. */ function transferFrom( address from, address to, uint256 tokenId ) public virtual override { _transfer(from, to, tokenId); } /** * @dev See {IERC721-safeTransferFrom}. */ function safeTransferFrom( address from, address to, uint256 tokenId ) public virtual override { safeTransferFrom(from, to, tokenId, ''); } /** * @dev See {IERC721-safeTransferFrom}. */ function safeTransferFrom( address from, address to, uint256 tokenId, bytes memory _data ) public virtual override { _transfer(from, to, tokenId); if (to.isContract() && !_checkContractOnERC721Received(from, to, tokenId, _data)) { revert TransferToNonERC721ReceiverImplementer(); } } /** * @dev Returns whether `tokenId` exists. * * Tokens can be managed by their owner or approved accounts via {approve} or {setApprovalForAll}. * * Tokens start existing when they are minted (`_mint`), */ function _exists(uint256 tokenId) internal view returns (bool) { return _startTokenId() <= tokenId && tokenId < _currentIndex && !_ownerships[tokenId].burned; } function _safeMint(address to, uint256 quantity) internal { _safeMint(to, quantity, ''); } /** * @dev Safely mints `quantity` tokens and transfers them to `to`. * * Requirements: * * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called for each safe transfer. * - `quantity` must be greater than 0. * * Emits a {Transfer} event. */ function _safeMint( address to, uint256 quantity, bytes memory _data ) internal { _mint(to, quantity, _data, true); } /** * @dev Mints `quantity` tokens and transfers them to `to`. * * Requirements: * * - `to` cannot be the zero address. * - `quantity` must be greater than 0. * * Emits a {Transfer} event. */ function _mint( address to, uint256 quantity, bytes memory _data, bool safe ) internal { uint256 startTokenId = _currentIndex; if (to == address(0)) revert MintToZeroAddress(); if (quantity == 0) revert MintZeroQuantity(); _beforeTokenTransfers(address(0), to, startTokenId, quantity); // Overflows are incredibly unrealistic. // balance or numberMinted overflow if current value of either + quantity > 1.8e19 (2**64) - 1 // updatedIndex overflows if _currentIndex + quantity > 1.2e77 (2**256) - 1 unchecked { _addressData[to].balance += uint64(quantity); _addressData[to].numberMinted += uint64(quantity); _ownerships[startTokenId].addr = to; _ownerships[startTokenId].startTimestamp = uint64(block.timestamp); uint256 updatedIndex = startTokenId; uint256 end = updatedIndex + quantity; if (safe && to.isContract()) { do { emit Transfer(address(0), to, updatedIndex); if (!_checkContractOnERC721Received(address(0), to, updatedIndex++, _data)) { revert TransferToNonERC721ReceiverImplementer(); } } while (updatedIndex != end); // Reentrancy protection if (_currentIndex != startTokenId) revert(); } else { do { emit Transfer(address(0), to, updatedIndex++); } while (updatedIndex != end); } _currentIndex = updatedIndex; } _afterTokenTransfers(address(0), to, startTokenId, quantity); } /** * @dev Transfers `tokenId` from `from` to `to`. * * Requirements: * * - `to` cannot be the zero address. * - `tokenId` token must be owned by `from`. * * Emits a {Transfer} event. */ function _transfer( address from, address to, uint256 tokenId ) private { TokenOwnership memory prevOwnership = _ownershipOf(tokenId); if (prevOwnership.addr != from) revert TransferFromIncorrectOwner(); bool isApprovedOrOwner = (_msgSender() == from || isApprovedForAll(from, _msgSender()) || getApproved(tokenId) == _msgSender()); if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved(); if (to == address(0)) revert TransferToZeroAddress(); _beforeTokenTransfers(from, to, tokenId, 1); // Clear approvals from the previous owner _approve(address(0), tokenId, from); // Underflow of the sender's balance is impossible because we check for // ownership above and the recipient's balance can't realistically overflow. // Counter overflow is incredibly unrealistic as tokenId would have to be 2**256. unchecked { _addressData[from].balance -= 1; _addressData[to].balance += 1; TokenOwnership storage currSlot = _ownerships[tokenId]; currSlot.addr = to; currSlot.startTimestamp = uint64(block.timestamp); // If the ownership slot of tokenId+1 is not explicitly set, that means the transfer initiator owns it. // Set the slot of tokenId+1 explicitly in storage to maintain correctness for ownerOf(tokenId+1) calls. uint256 nextTokenId = tokenId + 1; TokenOwnership storage nextSlot = _ownerships[nextTokenId]; if (nextSlot.addr == address(0)) { // This will suffice for checking _exists(nextTokenId), // as a burned slot cannot contain the zero address. if (nextTokenId != _currentIndex) { nextSlot.addr = from; nextSlot.startTimestamp = prevOwnership.startTimestamp; } } } emit Transfer(from, to, tokenId); _afterTokenTransfers(from, to, tokenId, 1); } /** * @dev This is equivalent to _burn(tokenId, false) */ function _burn(uint256 tokenId) internal virtual { _burn(tokenId, false); } /** * @dev Destroys `tokenId`. * The approval is cleared when the token is burned. * * Requirements: * * - `tokenId` must exist. * * Emits a {Transfer} event. */ function _burn(uint256 tokenId, bool approvalCheck) internal virtual { TokenOwnership memory prevOwnership = _ownershipOf(tokenId); address from = prevOwnership.addr; if (approvalCheck) { bool isApprovedOrOwner = (_msgSender() == from || isApprovedForAll(from, _msgSender()) || getApproved(tokenId) == _msgSender()); if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved(); } _beforeTokenTransfers(from, address(0), tokenId, 1); // Clear approvals from the previous owner _approve(address(0), tokenId, from); // Underflow of the sender's balance is impossible because we check for // ownership above and the recipient's balance can't realistically overflow. // Counter overflow is incredibly unrealistic as tokenId would have to be 2**256. unchecked { AddressData storage addressData = _addressData[from]; addressData.balance -= 1; addressData.numberBurned += 1; // Keep track of who burned the token, and the timestamp of burning. TokenOwnership storage currSlot = _ownerships[tokenId]; currSlot.addr = from; currSlot.startTimestamp = uint64(block.timestamp); currSlot.burned = true; // If the ownership slot of tokenId+1 is not explicitly set, that means the burn initiator owns it. // Set the slot of tokenId+1 explicitly in storage to maintain correctness for ownerOf(tokenId+1) calls. uint256 nextTokenId = tokenId + 1; TokenOwnership storage nextSlot = _ownerships[nextTokenId]; if (nextSlot.addr == address(0)) { // This will suffice for checking _exists(nextTokenId), // as a burned slot cannot contain the zero address. if (nextTokenId != _currentIndex) { nextSlot.addr = from; nextSlot.startTimestamp = prevOwnership.startTimestamp; } } } emit Transfer(from, address(0), tokenId); _afterTokenTransfers(from, address(0), tokenId, 1); // Overflow not possible, as _burnCounter cannot be exceed _currentIndex times. unchecked { _burnCounter++; } } /** * @dev Approve `to` to operate on `tokenId` * * Emits a {Approval} event. */ function _approve( address to, uint256 tokenId, address owner ) private { _tokenApprovals[tokenId] = to; emit Approval(owner, to, tokenId); } /** * @dev Internal function to invoke {IERC721Receiver-onERC721Received} on a target contract. * * @param from address representing the previous owner of the given token ID * @param to target address that will receive the tokens * @param tokenId uint256 ID of the token to be transferred * @param _data bytes optional data to send along with the call * @return bool whether the call correctly returned the expected magic value */ function _checkContractOnERC721Received( address from, address to, uint256 tokenId, bytes memory _data ) private returns (bool) { try IERC721Receiver(to).onERC721Received(_msgSender(), from, tokenId, _data) returns (bytes4 retval) { return retval == IERC721Receiver(to).onERC721Received.selector; } catch (bytes memory reason) { if (reason.length == 0) { revert TransferToNonERC721ReceiverImplementer(); } else { assembly { revert(add(32, reason), mload(reason)) } } } } /** * @dev Hook that is called before a set of serially-ordered token ids are about to be transferred. This includes minting. * And also called before burning one token. * * startTokenId - the first token id to be transferred * quantity - the amount to be transferred * * Calling conditions: * * - When `from` and `to` are both non-zero, `from`'s `tokenId` will be * transferred to `to`. * - When `from` is zero, `tokenId` will be minted for `to`. * - When `to` is zero, `tokenId` will be burned by `from`. * - `from` and `to` are never both zero. */ function _beforeTokenTransfers( address from, address to, uint256 startTokenId, uint256 quantity ) internal virtual {} function _beforeTokenTransfer( address from, address to, uint256 tokenId ) internal virtual {} /** * @dev Hook that is called after a set of serially-ordered token ids have been transferred. This includes * minting. * And also called after one token has been burned. * * startTokenId - the first token id to be transferred * quantity - the amount to be transferred * * Calling conditions: * * - When `from` and `to` are both non-zero, `from`'s `tokenId` has been * transferred to `to`. * - When `from` is zero, `tokenId` has been minted for `to`. * - When `to` is zero, `tokenId` has been burned by `from`. * - `from` and `to` are never both zero. */ function _afterTokenTransfers( address from, address to, uint256 startTokenId, uint256 quantity ) internal virtual {} } // File contracts/dependencies/Pausable.sol /** * @dev Contract module which allows children to implement an emergency stop * mechanism that can be triggered by an authorized account. * * This module is used through inheritance. It will make available the * modifiers `whenNotPaused` and `whenPaused`, which can be applied to * the functions of your contract. Note that they will not be pausable by * simply including this module, only once the modifiers are put in place. */ abstract contract Pausable is Context { /** * @dev Emitted when the pause is triggered by `account`. */ event Paused(address account); /** * @dev Emitted when the pause is lifted by `account`. */ event Unpaused(address account); bool private _paused; /** * @dev Initializes the contract in unpaused state. */ constructor() { _paused = false; } /** * @dev Returns true if the contract is paused, and false otherwise. */ function paused() public view virtual returns (bool) { return _paused; } /** * @dev Modifier to make a function callable only when the contract is not paused. * * Requirements: * * - The contract must not be paused. */ modifier whenNotPaused() { require(!paused(), "Pausable: paused"); _; } /** * @dev Modifier to make a function callable only when the contract is paused. * * Requirements: * * - The contract must be paused. */ modifier whenPaused() { require(paused(), "Pausable: not paused"); _; } /** * @dev Triggers stopped state. * * Requirements: * * - The contract must not be paused. */ function _pause() internal virtual whenNotPaused { _paused = true; emit Paused(_msgSender()); } /** * @dev Returns to normal state. * * Requirements: * * - The contract must be paused. */ function _unpause() internal virtual whenPaused { _paused = false; emit Unpaused(_msgSender()); } } // File contracts/dependencies/ERC721Pausable.sol /** * @dev ERC721 token with pausable token transfers, minting and burning. * * Useful for scenarios such as preventing trades until the end of an evaluation * period, or having an emergency switch for freezing all token transfers in the * event of a large bug. */ abstract contract ERC721Pausable is ERC721A, Pausable { /** * @dev See {ERC721-_beforeTokenTransfer}. * * Requirements: * * - the contract must not be paused. */ function _beforeTokenTransfer( address from, address to, uint256 tokenId ) internal virtual override { super._beforeTokenTransfer(from, to, tokenId); require(!paused(), "ERC721Pausable: token transfer while paused"); } } // File contracts/dependencies/SafeMath.sol /** * @dev Wrappers over Solidity's arithmetic operations with added overflow * checks. * * Arithmetic operations in Solidity wrap on overflow. This can easily result * in bugs, because programmers usually assume that an overflow raises an * error, which is the standard behavior in high level programming languages. * `SafeMath` restores this intuition by reverting the transaction when an * operation overflows. * * Using this library instead of the unchecked operations eliminates an entire * class of bugs, so it's recommended to use it always. */ library SafeMath { /** * @dev Returns the addition of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `+` operator. * * Requirements: * * - Addition cannot overflow. */ function add(uint256 a, uint256 b) internal pure returns (uint256) { uint256 c = a + b; require(c >= a, "SafeMath: addition overflow"); return c; } /** * @dev Returns the subtraction of two unsigned integers, reverting on * overflow (when the result is negative). * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b) internal pure returns (uint256) { return sub(a, b, "SafeMath: subtraction overflow"); } /** * @dev Returns the subtraction of two unsigned integers, reverting with custom message on * overflow (when the result is negative). * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b <= a, errorMessage); uint256 c = a - b; return c; } /** * @dev Returns the multiplication of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `*` operator. * * Requirements: * * - Multiplication cannot overflow. */ function mul(uint256 a, uint256 b) internal pure returns (uint256) { // Gas optimization: this is cheaper than requiring 'a' not being zero, but the // benefit is lost if 'b' is also tested. // See: https://github.com/OpenZeppelin/openzeppelin-contracts/pull/522 if (a == 0) { return 0; } uint256 c = a * b; require(c / a == b, "SafeMath: multiplication overflow"); return c; } /** * @dev Returns the integer division of two unsigned integers. Reverts on * division by zero. The result is rounded towards zero. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b) internal pure returns (uint256) { return div(a, b, "SafeMath: division by zero"); } /** * @dev Returns the integer division of two unsigned integers. Reverts with custom message on * division by zero. The result is rounded towards zero. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b > 0, errorMessage); uint256 c = a / b; // assert(a == b * c + a % b); // There is no case in which this doesn't hold return c; } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * Reverts when dividing by zero. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b) internal pure returns (uint256) { return mod(a, b, "SafeMath: modulo by zero"); } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * Reverts with custom message when dividing by zero. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b != 0, errorMessage); return a % b; } } // File contracts/erc721/nft.sol // SPDX-License-Identifier: MIT pragma solidity 0.8.4; /** * @dev {ERC721} token, including: * * - ability for holders to burn (destroy) their tokens * - a minter role that allows for token minting (creation) * - a pauser role that allows to stop all token transfers * - token ID and URI autogeneration * * This contract uses {AccessControl} to lock permissioned functions using the * different roles - head to its documentation for details. * * The account that deploys the contract will be granted the minter and pauser * roles, as well as the default admin role, which will let it grant both minter * and pauser roles to other accounts. */ contract RomeoAndJuliape is Context, ERC721A { using SafeMath for uint256; using Address for address; string public description; mapping(uint256 => string) public wordsToTokenId; mapping(uint256 => string) public wordsToTokenId2; mapping(uint256 => string) public wordsToTokenId3; mapping(uint256 => string) public author; mapping(uint256 => bool) public textSet; address public owner; address public admin = 0x95DC9f3E4206D54F68bB8741EdCBDE72701D7E15; uint public maxToMint = 203; /** * @dev Grants `DEFAULT_ADMIN_ROLE`, `MINTER_ROLE` and `PAUSER_ROLE` to the * account that deploys the contract. * * Token URIs will be autogenerated based on `baseURI` and their token IDs. * See {ERC721-tokenURI}. */ constructor() ERC721A("Romeo and Juliape", "RAJ") { owner = msg.sender; description = "An on-chain human-AI love story. A play written by Kalen Iwamoto and AI."; } function setOwner(address _owner) public virtual { require((owner == msg.sender), "NonFungibleToken: must have admin role"); owner = _owner; } function mint() public virtual payable{ uint256 totalMinted = totalSupply(); require (totalMinted.add(1) <= maxToMint, "Max supply reached"); _safeMint(msg.sender, 203); } function set(uint256 tokenId, string memory _userText, string memory _userText2, string memory _userText3, string memory _author) public virtual{ // We cannot just use balanceOf to create the new tokenId because tokens // can be burned (destroyed), so we need a separate counter. require(msg.sender == owner || msg.sender == admin, "Not allowed"); require(! textSet[tokenId], "Already set"); wordsToTokenId[tokenId] = _userText; //Add word to mapping @tokenId wordsToTokenId2[tokenId] = _userText2; wordsToTokenId3[tokenId] = _userText3; author[tokenId] = _author; textSet[tokenId] = true; } function buildImage(uint256 _tokenId) private view returns (string memory) { string memory currentWord = wordsToTokenId[_tokenId]; string memory currentWord2 = wordsToTokenId2[_tokenId]; string memory currentWord3 = wordsToTokenId3[_tokenId]; string memory author1 = author[_tokenId]; return Base64.encode( bytes( abi.encodePacked( '<svg width="1200" height="300" xmlns="http://www.w3.org/2000/svg">', '<rect height="300" width="1200" fill="hsl(328, 100%, 100%)"/>', '<text x="50%" y="40%" fill="hsl(random, 100%, 80%)" text-anchor="middle" font-size="23">',currentWord,'</text>', '<text x="50%" y="50%" fill="hsl(random, 100%, 80%)" text-anchor="middle" font-size="23">',currentWord2,'</text>', '<text x="50%" y="60%" fill="hsl(random, 100%, 80%)" text-anchor="middle" font-size="23">',currentWord3,'</text>', '<text x="50%" y="20%" dominant-baseline="middle" fill="hsl(random, 100%, 80%)" text-anchor="middle" font-size="41">',author1,'</text>', '</svg>' ) ) ); } function buildMetadata(uint256 _tokenId) private view returns (string memory) { string memory mem = Strings.toString(_tokenId); return string( abi.encodePacked( "data:application/json;base64,", Base64.encode( bytes( abi.encodePacked( '{"name":"', "Line #", mem, '", "description":"', description, '", "image": "', "data:image/svg+xml;base64,", buildImage(_tokenId), '", "attributes": ', "[]", "}" ) ) ) ) ); } function tokenURI(uint256 _tokenId) public view virtual override returns (string memory) { require( _exists(_tokenId), "ERC721Metadata: URI query for nonexistent token" ); return buildMetadata(_tokenId); } }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
[{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ApprovalCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"ApprovalQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"ApprovalToCurrentOwner","type":"error"},{"inputs":[],"name":"ApproveToCaller","type":"error"},{"inputs":[],"name":"BalanceQueryForZeroAddress","type":"error"},{"inputs":[],"name":"MintToZeroAddress","type":"error"},{"inputs":[],"name":"MintZeroQuantity","type":"error"},{"inputs":[],"name":"OwnerQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"TransferCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"TransferFromIncorrectOwner","type":"error"},{"inputs":[],"name":"TransferToNonERC721ReceiverImplementer","type":"error"},{"inputs":[],"name":"TransferToZeroAddress","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"approved","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":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":"admin","outputs":[{"internalType":"address","name":"","type":"address"}],"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":"uint256","name":"","type":"uint256"}],"name":"author","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"baseURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"description","outputs":[{"internalType":"string","name":"","type":"string"}],"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":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maxToMint","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"mint","outputs":[],"stateMutability":"payable","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":"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":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_userText","type":"string"},{"internalType":"string","name":"_userText2","type":"string"},{"internalType":"string","name":"_userText3","type":"string"},{"internalType":"string","name":"_author","type":"string"}],"name":"set","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_owner","type":"address"}],"name":"setOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"textSet","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"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":"","type":"address"}],"name":"whitelists","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"wordsToTokenId","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"wordsToTokenId2","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"wordsToTokenId3","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"}]
Contract Creation Code
6080604052601280546001600160a01b0319167395dc9f3e4206d54f68bb8741edcbde72701d7e1517905560cb6013553480156200003c57600080fd5b506040805180820182526011815270526f6d656f20616e64204a756c6961706560781b602080830191909152825180840190935260038352622920a560e91b9083015290620000926301ffc9a760e01b6200010d565b8151620000a790600490602085019062000191565b508051620000bd90600590602084019062000191565b5060016002555050601180546001600160a01b0319163317905560408051608081019091526048808252620026ca602083013980516200010691600b9160209091019062000191565b5062000274565b6001600160e01b031980821614156200016c5760405162461bcd60e51b815260206004820152601c60248201527f4552433136353a20696e76616c696420696e7465726661636520696400000000604482015260640160405180910390fd5b6001600160e01b0319166000908152602081905260409020805460ff19166001179055565b8280546200019f9062000237565b90600052602060002090601f016020900481019282620001c357600085556200020e565b82601f10620001de57805160ff19168380011785556200020e565b828001600101855582156200020e579182015b828111156200020e578251825591602001919060010190620001f1565b506200021c92915062000220565b5090565b5b808211156200021c576000815560010162000221565b600181811c908216806200024c57607f821691505b602082108114156200026e57634e487b7160e01b600052602260045260246000fd5b50919050565b61244680620002846000396000f3fe6080604052600436106101b75760003560e01c80637284e416116100ec578063b88d4fde1161008a578063e985e9c511610064578063e985e9c5146104d5578063ec4eb4421461051e578063f851a4401461053e578063fbfaf17e1461055e57600080fd5b8063b88d4fde14610475578063c87b56dd14610495578063e271a64a146104b557600080fd5b806395d89b41116100c657806395d89b4114610400578063a22cb46514610415578063a958327b14610435578063ae39c7b81461045557600080fd5b80637284e4161461039b5780638da5cb5b146103b0578063922753a2146103d057600080fd5b806318160ddd1161015957806342842e0e1161013357806342842e0e146103265780636352211e146103465780636c0360eb1461036657806370a082311461037b57600080fd5b806318160ddd146102b95780631e7be210146102d657806323b872dd1461030657600080fd5b8063095ea7b311610195578063095ea7b31461024b5780630ba133c51461026d5780631249c58b1461029157806313af40351461029957600080fd5b806301ffc9a7146101bc57806306fdde03146101f1578063081812fc14610213575b600080fd5b3480156101c857600080fd5b506101dc6101d7366004611c13565b61057e565b60405190151581526020015b60405180910390f35b3480156101fd57600080fd5b506102066105d9565b6040516101e8919061226d565b34801561021f57600080fd5b5061023361022e366004611c4b565b61066b565b6040516001600160a01b0390911681526020016101e8565b34801561025757600080fd5b5061026b610266366004611bea565b6106af565b005b34801561027957600080fd5b5061028360135481565b6040519081526020016101e8565b61026b61073d565b3480156102a557600080fd5b5061026b6102b4366004611ab0565b6107b3565b3480156102c557600080fd5b506003546002540360001901610283565b3480156102e257600080fd5b506101dc6102f1366004611ab0565b60016020526000908152604090205460ff1681565b34801561031257600080fd5b5061026b610321366004611afc565b61083e565b34801561033257600080fd5b5061026b610341366004611afc565b610849565b34801561035257600080fd5b50610233610361366004611c4b565b610864565b34801561037257600080fd5b50610206610876565b34801561038757600080fd5b50610283610396366004611ab0565b610885565b3480156103a757600080fd5b506102066108d4565b3480156103bc57600080fd5b50601154610233906001600160a01b031681565b3480156103dc57600080fd5b506101dc6103eb366004611c4b565b60106020526000908152604090205460ff1681565b34801561040c57600080fd5b50610206610962565b34801561042157600080fd5b5061026b610430366004611bb0565b610971565b34801561044157600080fd5b50610206610450366004611c4b565b610a07565b34801561046157600080fd5b5061026b610470366004611c63565b610a20565b34801561048157600080fd5b5061026b610490366004611b37565b610b69565b3480156104a157600080fd5b506102066104b0366004611c4b565b610bbf565b3480156104c157600080fd5b506102066104d0366004611c4b565b610c37565b3480156104e157600080fd5b506101dc6104f0366004611aca565b6001600160a01b039182166000908152600a6020908152604080832093909416825291909152205460ff1690565b34801561052a57600080fd5b50610206610539366004611c4b565b610c50565b34801561054a57600080fd5b50601254610233906001600160a01b031681565b34801561056a57600080fd5b50610206610579366004611c4b565b610c69565b60006001600160e01b031982166380ac58cd60e01b14806105af57506001600160e01b03198216635b5e139f60e01b145b806105d357506001600160e01b0319821660009081526020819052604090205460ff165b92915050565b6060600480546105e89061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546106149061230e565b80156106615780601f1061063657610100808354040283529160200191610661565b820191906000526020600020905b81548152906001019060200180831161064457829003601f168201915b5050505050905090565b600061067682610c82565b610693576040516333d1c03960e21b815260040160405180910390fd5b506000908152600960205260409020546001600160a01b031690565b60006106ba82610864565b9050806001600160a01b0316836001600160a01b031614156106ef5760405163250fdee360e21b815260040160405180910390fd5b336001600160a01b0382161480159061070f575061070d81336104f0565b155b1561072d576040516367d9dca160e11b815260040160405180910390fd5b610738838383610cbb565b505050565b60035460025460009190036000190160135490915061075d826001610d17565b11156107a55760405162461bcd60e51b815260206004820152601260248201527113585e081cdd5c1c1b1e481c995858da195960721b60448201526064015b60405180910390fd5b6107b03360cb610d7d565b50565b6011546001600160a01b0316331461081c5760405162461bcd60e51b815260206004820152602660248201527f4e6f6e46756e6769626c65546f6b656e3a206d75737420686176652061646d696044820152656e20726f6c6560d01b606482015260840161079c565b601180546001600160a01b0319166001600160a01b0392909216919091179055565b610738838383610d9b565b61073883838360405180602001604052806000815250610b69565b600061086f82610f8b565b5192915050565b6060600680546105e89061230e565b60006001600160a01b0382166108ae576040516323d3ad8160e21b815260040160405180910390fd5b506001600160a01b031660009081526008602052604090205467ffffffffffffffff1690565b600b80546108e19061230e565b80601f016020809104026020016040519081016040528092919081815260200182805461090d9061230e565b801561095a5780601f1061092f5761010080835404028352916020019161095a565b820191906000526020600020905b81548152906001019060200180831161093d57829003601f168201915b505050505081565b6060600580546105e89061230e565b6001600160a01b03821633141561099b5760405163b06307db60e01b815260040160405180910390fd5b336000818152600a602090815260408083206001600160a01b03871680855290835292819020805460ff191686151590811790915590519081529192917f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a35050565b600d60205260009081526040902080546108e19061230e565b6011546001600160a01b0316331480610a4357506012546001600160a01b031633145b610a7d5760405162461bcd60e51b815260206004820152600b60248201526a139bdd08185b1b1bddd95960aa1b604482015260640161079c565b60008581526010602052604090205460ff1615610aca5760405162461bcd60e51b815260206004820152600b60248201526a105b1c9958591e481cd95d60aa1b604482015260640161079c565b6000858152600c602090815260409091208551610ae992870190611966565b506000858152600d602090815260409091208451610b0992860190611966565b506000858152600e602090815260409091208351610b2992850190611966565b506000858152600f602090815260409091208251610b4992840190611966565b50505060009283525050601060205260409020805460ff19166001179055565b610b74848484610d9b565b610b86836001600160a01b03166110b4565b8015610b9b5750610b99848484846110f0565b155b15610bb9576040516368d2bf6b60e11b815260040160405180910390fd5b50505050565b6060610bca82610c82565b610c2e5760405162461bcd60e51b815260206004820152602f60248201527f4552433732314d657461646174613a2055524920717565727920666f72206e6f60448201526e3732bc34b9ba32b73a103a37b5b2b760891b606482015260840161079c565b6105d3826111e7565b600e60205260009081526040902080546108e19061230e565b600f60205260009081526040902080546108e19061230e565b600c60205260009081526040902080546108e19061230e565b600081600111158015610c96575060025482105b80156105d3575050600090815260076020526040902054600160e01b900460ff161590565b60008281526009602052604080822080546001600160a01b0319166001600160a01b0387811691821790925591518593918516917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591a4505050565b600080610d248385612280565b905083811015610d765760405162461bcd60e51b815260206004820152601b60248201527f536166654d6174683a206164646974696f6e206f766572666c6f770000000000604482015260640161079c565b9392505050565b610d97828260405180602001604052806000815250611252565b5050565b6000610da682610f8b565b9050836001600160a01b031681600001516001600160a01b031614610ddd5760405162a1148160e81b815260040160405180910390fd5b6000336001600160a01b0386161480610dfb5750610dfb85336104f0565b80610e16575033610e0b8461066b565b6001600160a01b0316145b905080610e3657604051632ce44b5f60e11b815260040160405180910390fd5b6001600160a01b038416610e5d57604051633a954ecd60e21b815260040160405180910390fd5b610e6960008487610cbb565b6001600160a01b038581166000908152600860209081526040808320805467ffffffffffffffff1980821667ffffffffffffffff92831660001901831617909255898616808652838620805493841693831660019081018416949094179055898652600790945282852080546001600160e01b031916909417600160a01b42909216919091021783558701808452922080549193909116610f3f576002548214610f3f578054602086015167ffffffffffffffff16600160a01b026001600160e01b03199091166001600160a01b038a16171781555b50505082846001600160a01b0316866001600160a01b03167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a45b5050505050565b60408051606081018252600080825260208201819052918101919091528180600111158015610fbb575060025481105b1561109b57600081815260076020908152604091829020825160608101845290546001600160a01b0381168252600160a01b810467ffffffffffffffff1692820192909252600160e01b90910460ff161515918101829052906110995780516001600160a01b03161561102f579392505050565b5060001901600081815260076020908152604091829020825160608101845290546001600160a01b038116808352600160a01b820467ffffffffffffffff1693830193909352600160e01b900460ff1615159281019290925215611094579392505050565b61102f565b505b604051636f96cda160e11b815260040160405180910390fd5b6000813f7fc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a47081158015906110e85750808214155b949350505050565b604051630a85bd0160e11b81526000906001600160a01b0385169063150b7a029061112590339089908890889060040161223a565b602060405180830381600087803b15801561113f57600080fd5b505af192505050801561116f575060408051601f3d908101601f1916820190925261116c91810190611c2f565b60015b6111ca573d80801561119d576040519150601f19603f3d011682016040523d82523d6000602084013e6111a2565b606091505b5080516111c2576040516368d2bf6b60e11b815260040160405180910390fd5b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050949350505050565b606060006111f48361125f565b905061122b81600b61120586611379565b60405160200161121793929190611d5d565b60405160208183030381529060405261161b565b60405160200161123b91906121f5565b604051602081830303815290604052915050919050565b6107388383836001611791565b6060816112835750506040805180820190915260018152600360fc1b602082015290565b8160005b81156112ad578061129781612349565b91506112a69050600a83612298565b9150611287565b60008167ffffffffffffffff8111156112d657634e487b7160e01b600052604160045260246000fd5b6040519080825280601f01601f191660200182016040528015611300576020820181803683370190505b5090505b84156110e8576113156001836122cb565b9150611322600a86612364565b61132d906030612280565b60f81b81838151811061135057634e487b7160e01b600052603260045260246000fd5b60200101906001600160f81b031916908160001a905350611372600a86612298565b9450611304565b6000818152600c60205260408120805460609291906113979061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546113c39061230e565b80156114105780601f106113e557610100808354040283529160200191611410565b820191906000526020600020905b8154815290600101906020018083116113f357829003601f168201915b505050505090506000600d600085815260200190815260200160002080546114379061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546114639061230e565b80156114b05780601f10611485576101008083540402835291602001916114b0565b820191906000526020600020905b81548152906001019060200180831161149357829003601f168201915b505050505090506000600e600086815260200190815260200160002080546114d79061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546115039061230e565b80156115505780601f1061152557610100808354040283529160200191611550565b820191906000526020600020905b81548152906001019060200180831161153357829003601f168201915b505050505090506000600f600087815260200190815260200160002080546115779061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546115a39061230e565b80156115f05780601f106115c5576101008083540402835291602001916115f0565b820191906000526020600020905b8154815290600101906020018083116115d357829003601f168201915b50505050509050611611848484846040516020016112179493929190611ee9565b9695505050505050565b606081516000141561163b57505060408051602081019091526000815290565b60006040518060600160405280604081526020016123d1604091399050600060038451600261166a9190612280565b6116749190612298565b61167f9060046122ac565b9050600061168e826020612280565b67ffffffffffffffff8111156116b457634e487b7160e01b600052604160045260246000fd5b6040519080825280601f01601f1916602001820160405280156116de576020820181803683370190505b509050818152600183018586518101602084015b8183101561174c5760039283018051603f601282901c811687015160f890811b8552600c83901c8216880151811b6001860152600683901c8216880151811b60028601529116860151901b938201939093526004016116f2565b600389510660018114611766576002811461177757611783565b613d3d60f01b600119830152611783565b603d60f81b6000198301525b509398975050505050505050565b6002546001600160a01b0385166117ba57604051622e076360e81b815260040160405180910390fd5b836117d85760405163b562e8dd60e01b815260040160405180910390fd5b6001600160a01b038516600081815260086020908152604080832080546fffffffffffffffffffffffffffffffff19811667ffffffffffffffff8083168c0181169182176801000000000000000067ffffffffffffffff1990941690921783900481168c01811690920217909155858452600790925290912080546001600160e01b031916909217600160a01b42909216919091021790558080850183801561188e575061188e876001600160a01b03166110b4565b15611917575b60405182906001600160a01b038916906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a46118df60008884806001019550886110f0565b6118fc576040516368d2bf6b60e11b815260040160405180910390fd5b8082141561189457826002541461191257600080fd5b61195d565b5b6040516001830192906001600160a01b038916906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a480821415611918575b50600255610f84565b8280546119729061230e565b90600052602060002090601f01602090048101928261199457600085556119da565b82601f106119ad57805160ff19168380011785556119da565b828001600101855582156119da579182015b828111156119da5782518255916020019190600101906119bf565b506119e69291506119ea565b5090565b5b808211156119e657600081556001016119eb565b600067ffffffffffffffff80841115611a1a57611a1a6123a4565b604051601f8501601f19908116603f01168101908282118183101715611a4257611a426123a4565b81604052809350858152868686011115611a5b57600080fd5b858560208301376000602087830101525050509392505050565b80356001600160a01b0381168114611a8c57600080fd5b919050565b600082601f830112611aa1578081fd5b610d76838335602085016119ff565b600060208284031215611ac1578081fd5b610d7682611a75565b60008060408385031215611adc578081fd5b611ae583611a75565b9150611af360208401611a75565b90509250929050565b600080600060608486031215611b10578081fd5b611b1984611a75565b9250611b2760208501611a75565b9150604084013590509250925092565b60008060008060808587031215611b4c578081fd5b611b5585611a75565b9350611b6360208601611a75565b925060408501359150606085013567ffffffffffffffff811115611b85578182fd5b8501601f81018713611b95578182fd5b611ba4878235602084016119ff565b91505092959194509250565b60008060408385031215611bc2578182fd5b611bcb83611a75565b915060208301358015158114611bdf578182fd5b809150509250929050565b60008060408385031215611bfc578182fd5b611c0583611a75565b946020939093013593505050565b600060208284031215611c24578081fd5b8135610d76816123ba565b600060208284031215611c40578081fd5b8151610d76816123ba565b600060208284031215611c5c578081fd5b5035919050565b600080600080600060a08688031215611c7a578081fd5b85359450602086013567ffffffffffffffff80821115611c98578283fd5b611ca489838a01611a91565b95506040880135915080821115611cb9578283fd5b611cc589838a01611a91565b94506060880135915080821115611cda578283fd5b611ce689838a01611a91565b93506080880135915080821115611cfb578283fd5b50611d0888828901611a91565b9150509295509295909350565b60008151808452611d2d8160208601602086016122e2565b601f01601f19169290920160200192915050565b60008151611d538185602086016122e2565b9290920192915050565b683d913730b6b2911d1160b91b8152654c696e65202360d01b600982015283516000906020611d9282600f8601838a016122e2565b71111610113232b9b1b934b83a34b7b7111d1160711b600f9285019283015285546021908490600181811c9080831680611dcd57607f831692505b868310811415611deb57634e487b7160e01b89526022600452602489fd5b808015611dff5760018114611e1457611e44565b60ff1985168988015283890187019550611e44565b60008d8152602090208a5b85811015611e3a5781548b82018a0152908401908901611e1f565b505086848a010195505b5050505050611edc611ecf611ec1611ea4611e9e611e75866c1116101134b6b0b3b2911d101160991b8152600d0190565b7f646174613a696d6167652f7376672b786d6c3b6261736536342c0000000000008152601a0190565b8b611d41565b7001116101130ba3a3934b13aba32b9911d1607d1b815260110190565b615b5d60f01b815260020190565b607d60f81b815260010190565b9998505050505050505050565b7f3c7376672077696474683d223132303022206865696768743d2233303022207881527f6d6c6e733d22687474703a2f2f7777772e77332e6f72672f323030302f737667602082015261111f60f11b60408201527f3c72656374206865696768743d22333030222077696474683d2231323030222060428201527f66696c6c3d2268736c283332382c20313030252c203130302529222f3e00000060628201527f3c7465787420783d223530252220793d2234302522202066696c6c3d2268736c607f8201527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f72609f820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b60bf8201526000855161200c8160d8850160208a016122e2565b6121ea6121d86120bd6121d26121416120bd611e9e6120d06120bd6120b761204660d88c8f0101661e17ba32bc3a1f60c91b815260070190565b7f3c7465787420783d223530252220793d2235302522202066696c6c3d2268736c81527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f726020820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b604082015260590190565b8f611d41565b661e17ba32bc3a1f60c91b815260070190565b7f3c7465787420783d223530252220793d2236302522202066696c6c3d2268736c81527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f726020820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b604082015260590190565b7f3c7465787420783d223530252220793d223230252220646f6d696e616e742d6281527f6173656c696e653d226d6964646c65222066696c6c3d2268736c2872616e646f60208201527f6d2c20313030252c20383025292220746578742d616e63686f723d226d696464604082015272363291103337b73a16b9b4bd329e911a18911f60691b606082015260730190565b87611d41565b651e17b9bb339f60d11b815260060190565b979650505050505050565b7f646174613a6170706c69636174696f6e2f6a736f6e3b6261736536342c00000081526000825161222d81601d8501602087016122e2565b91909101601d0192915050565b6001600160a01b038581168252841660208201526040810183905260806060820181905260009061161190830184611d15565b602081526000610d766020830184611d15565b6000821982111561229357612293612378565b500190565b6000826122a7576122a761238e565b500490565b60008160001904831182151516156122c6576122c6612378565b500290565b6000828210156122dd576122dd612378565b500390565b60005b838110156122fd5781810151838201526020016122e5565b83811115610bb95750506000910152565b600181811c9082168061232257607f821691505b6020821081141561234357634e487b7160e01b600052602260045260246000fd5b50919050565b600060001982141561235d5761235d612378565b5060010190565b6000826123735761237361238e565b500690565b634e487b7160e01b600052601160045260246000fd5b634e487b7160e01b600052601260045260246000fd5b634e487b7160e01b600052604160045260246000fd5b6001600160e01b0319811681146107b057600080fdfe4142434445464748494a4b4c4d4e4f505152535455565758595a6162636465666768696a6b6c6d6e6f707172737475767778797a303132333435363738392b2fa2646970667358221220a254f1bf1132049008dc255143963394df7602cda125a662a32265ded41204f664736f6c63430008040033416e206f6e2d636861696e2068756d616e2d4149206c6f76652073746f72792e204120706c6179207772697474656e206279204b616c656e204977616d6f746f20616e642041492e
Deployed Bytecode
0x6080604052600436106101b75760003560e01c80637284e416116100ec578063b88d4fde1161008a578063e985e9c511610064578063e985e9c5146104d5578063ec4eb4421461051e578063f851a4401461053e578063fbfaf17e1461055e57600080fd5b8063b88d4fde14610475578063c87b56dd14610495578063e271a64a146104b557600080fd5b806395d89b41116100c657806395d89b4114610400578063a22cb46514610415578063a958327b14610435578063ae39c7b81461045557600080fd5b80637284e4161461039b5780638da5cb5b146103b0578063922753a2146103d057600080fd5b806318160ddd1161015957806342842e0e1161013357806342842e0e146103265780636352211e146103465780636c0360eb1461036657806370a082311461037b57600080fd5b806318160ddd146102b95780631e7be210146102d657806323b872dd1461030657600080fd5b8063095ea7b311610195578063095ea7b31461024b5780630ba133c51461026d5780631249c58b1461029157806313af40351461029957600080fd5b806301ffc9a7146101bc57806306fdde03146101f1578063081812fc14610213575b600080fd5b3480156101c857600080fd5b506101dc6101d7366004611c13565b61057e565b60405190151581526020015b60405180910390f35b3480156101fd57600080fd5b506102066105d9565b6040516101e8919061226d565b34801561021f57600080fd5b5061023361022e366004611c4b565b61066b565b6040516001600160a01b0390911681526020016101e8565b34801561025757600080fd5b5061026b610266366004611bea565b6106af565b005b34801561027957600080fd5b5061028360135481565b6040519081526020016101e8565b61026b61073d565b3480156102a557600080fd5b5061026b6102b4366004611ab0565b6107b3565b3480156102c557600080fd5b506003546002540360001901610283565b3480156102e257600080fd5b506101dc6102f1366004611ab0565b60016020526000908152604090205460ff1681565b34801561031257600080fd5b5061026b610321366004611afc565b61083e565b34801561033257600080fd5b5061026b610341366004611afc565b610849565b34801561035257600080fd5b50610233610361366004611c4b565b610864565b34801561037257600080fd5b50610206610876565b34801561038757600080fd5b50610283610396366004611ab0565b610885565b3480156103a757600080fd5b506102066108d4565b3480156103bc57600080fd5b50601154610233906001600160a01b031681565b3480156103dc57600080fd5b506101dc6103eb366004611c4b565b60106020526000908152604090205460ff1681565b34801561040c57600080fd5b50610206610962565b34801561042157600080fd5b5061026b610430366004611bb0565b610971565b34801561044157600080fd5b50610206610450366004611c4b565b610a07565b34801561046157600080fd5b5061026b610470366004611c63565b610a20565b34801561048157600080fd5b5061026b610490366004611b37565b610b69565b3480156104a157600080fd5b506102066104b0366004611c4b565b610bbf565b3480156104c157600080fd5b506102066104d0366004611c4b565b610c37565b3480156104e157600080fd5b506101dc6104f0366004611aca565b6001600160a01b039182166000908152600a6020908152604080832093909416825291909152205460ff1690565b34801561052a57600080fd5b50610206610539366004611c4b565b610c50565b34801561054a57600080fd5b50601254610233906001600160a01b031681565b34801561056a57600080fd5b50610206610579366004611c4b565b610c69565b60006001600160e01b031982166380ac58cd60e01b14806105af57506001600160e01b03198216635b5e139f60e01b145b806105d357506001600160e01b0319821660009081526020819052604090205460ff165b92915050565b6060600480546105e89061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546106149061230e565b80156106615780601f1061063657610100808354040283529160200191610661565b820191906000526020600020905b81548152906001019060200180831161064457829003601f168201915b5050505050905090565b600061067682610c82565b610693576040516333d1c03960e21b815260040160405180910390fd5b506000908152600960205260409020546001600160a01b031690565b60006106ba82610864565b9050806001600160a01b0316836001600160a01b031614156106ef5760405163250fdee360e21b815260040160405180910390fd5b336001600160a01b0382161480159061070f575061070d81336104f0565b155b1561072d576040516367d9dca160e11b815260040160405180910390fd5b610738838383610cbb565b505050565b60035460025460009190036000190160135490915061075d826001610d17565b11156107a55760405162461bcd60e51b815260206004820152601260248201527113585e081cdd5c1c1b1e481c995858da195960721b60448201526064015b60405180910390fd5b6107b03360cb610d7d565b50565b6011546001600160a01b0316331461081c5760405162461bcd60e51b815260206004820152602660248201527f4e6f6e46756e6769626c65546f6b656e3a206d75737420686176652061646d696044820152656e20726f6c6560d01b606482015260840161079c565b601180546001600160a01b0319166001600160a01b0392909216919091179055565b610738838383610d9b565b61073883838360405180602001604052806000815250610b69565b600061086f82610f8b565b5192915050565b6060600680546105e89061230e565b60006001600160a01b0382166108ae576040516323d3ad8160e21b815260040160405180910390fd5b506001600160a01b031660009081526008602052604090205467ffffffffffffffff1690565b600b80546108e19061230e565b80601f016020809104026020016040519081016040528092919081815260200182805461090d9061230e565b801561095a5780601f1061092f5761010080835404028352916020019161095a565b820191906000526020600020905b81548152906001019060200180831161093d57829003601f168201915b505050505081565b6060600580546105e89061230e565b6001600160a01b03821633141561099b5760405163b06307db60e01b815260040160405180910390fd5b336000818152600a602090815260408083206001600160a01b03871680855290835292819020805460ff191686151590811790915590519081529192917f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31910160405180910390a35050565b600d60205260009081526040902080546108e19061230e565b6011546001600160a01b0316331480610a4357506012546001600160a01b031633145b610a7d5760405162461bcd60e51b815260206004820152600b60248201526a139bdd08185b1b1bddd95960aa1b604482015260640161079c565b60008581526010602052604090205460ff1615610aca5760405162461bcd60e51b815260206004820152600b60248201526a105b1c9958591e481cd95d60aa1b604482015260640161079c565b6000858152600c602090815260409091208551610ae992870190611966565b506000858152600d602090815260409091208451610b0992860190611966565b506000858152600e602090815260409091208351610b2992850190611966565b506000858152600f602090815260409091208251610b4992840190611966565b50505060009283525050601060205260409020805460ff19166001179055565b610b74848484610d9b565b610b86836001600160a01b03166110b4565b8015610b9b5750610b99848484846110f0565b155b15610bb9576040516368d2bf6b60e11b815260040160405180910390fd5b50505050565b6060610bca82610c82565b610c2e5760405162461bcd60e51b815260206004820152602f60248201527f4552433732314d657461646174613a2055524920717565727920666f72206e6f60448201526e3732bc34b9ba32b73a103a37b5b2b760891b606482015260840161079c565b6105d3826111e7565b600e60205260009081526040902080546108e19061230e565b600f60205260009081526040902080546108e19061230e565b600c60205260009081526040902080546108e19061230e565b600081600111158015610c96575060025482105b80156105d3575050600090815260076020526040902054600160e01b900460ff161590565b60008281526009602052604080822080546001600160a01b0319166001600160a01b0387811691821790925591518593918516917f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591a4505050565b600080610d248385612280565b905083811015610d765760405162461bcd60e51b815260206004820152601b60248201527f536166654d6174683a206164646974696f6e206f766572666c6f770000000000604482015260640161079c565b9392505050565b610d97828260405180602001604052806000815250611252565b5050565b6000610da682610f8b565b9050836001600160a01b031681600001516001600160a01b031614610ddd5760405162a1148160e81b815260040160405180910390fd5b6000336001600160a01b0386161480610dfb5750610dfb85336104f0565b80610e16575033610e0b8461066b565b6001600160a01b0316145b905080610e3657604051632ce44b5f60e11b815260040160405180910390fd5b6001600160a01b038416610e5d57604051633a954ecd60e21b815260040160405180910390fd5b610e6960008487610cbb565b6001600160a01b038581166000908152600860209081526040808320805467ffffffffffffffff1980821667ffffffffffffffff92831660001901831617909255898616808652838620805493841693831660019081018416949094179055898652600790945282852080546001600160e01b031916909417600160a01b42909216919091021783558701808452922080549193909116610f3f576002548214610f3f578054602086015167ffffffffffffffff16600160a01b026001600160e01b03199091166001600160a01b038a16171781555b50505082846001600160a01b0316866001600160a01b03167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a45b5050505050565b60408051606081018252600080825260208201819052918101919091528180600111158015610fbb575060025481105b1561109b57600081815260076020908152604091829020825160608101845290546001600160a01b0381168252600160a01b810467ffffffffffffffff1692820192909252600160e01b90910460ff161515918101829052906110995780516001600160a01b03161561102f579392505050565b5060001901600081815260076020908152604091829020825160608101845290546001600160a01b038116808352600160a01b820467ffffffffffffffff1693830193909352600160e01b900460ff1615159281019290925215611094579392505050565b61102f565b505b604051636f96cda160e11b815260040160405180910390fd5b6000813f7fc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a47081158015906110e85750808214155b949350505050565b604051630a85bd0160e11b81526000906001600160a01b0385169063150b7a029061112590339089908890889060040161223a565b602060405180830381600087803b15801561113f57600080fd5b505af192505050801561116f575060408051601f3d908101601f1916820190925261116c91810190611c2f565b60015b6111ca573d80801561119d576040519150601f19603f3d011682016040523d82523d6000602084013e6111a2565b606091505b5080516111c2576040516368d2bf6b60e11b815260040160405180910390fd5b805181602001fd5b6001600160e01b031916630a85bd0160e11b149050949350505050565b606060006111f48361125f565b905061122b81600b61120586611379565b60405160200161121793929190611d5d565b60405160208183030381529060405261161b565b60405160200161123b91906121f5565b604051602081830303815290604052915050919050565b6107388383836001611791565b6060816112835750506040805180820190915260018152600360fc1b602082015290565b8160005b81156112ad578061129781612349565b91506112a69050600a83612298565b9150611287565b60008167ffffffffffffffff8111156112d657634e487b7160e01b600052604160045260246000fd5b6040519080825280601f01601f191660200182016040528015611300576020820181803683370190505b5090505b84156110e8576113156001836122cb565b9150611322600a86612364565b61132d906030612280565b60f81b81838151811061135057634e487b7160e01b600052603260045260246000fd5b60200101906001600160f81b031916908160001a905350611372600a86612298565b9450611304565b6000818152600c60205260408120805460609291906113979061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546113c39061230e565b80156114105780601f106113e557610100808354040283529160200191611410565b820191906000526020600020905b8154815290600101906020018083116113f357829003601f168201915b505050505090506000600d600085815260200190815260200160002080546114379061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546114639061230e565b80156114b05780601f10611485576101008083540402835291602001916114b0565b820191906000526020600020905b81548152906001019060200180831161149357829003601f168201915b505050505090506000600e600086815260200190815260200160002080546114d79061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546115039061230e565b80156115505780601f1061152557610100808354040283529160200191611550565b820191906000526020600020905b81548152906001019060200180831161153357829003601f168201915b505050505090506000600f600087815260200190815260200160002080546115779061230e565b80601f01602080910402602001604051908101604052809291908181526020018280546115a39061230e565b80156115f05780601f106115c5576101008083540402835291602001916115f0565b820191906000526020600020905b8154815290600101906020018083116115d357829003601f168201915b50505050509050611611848484846040516020016112179493929190611ee9565b9695505050505050565b606081516000141561163b57505060408051602081019091526000815290565b60006040518060600160405280604081526020016123d1604091399050600060038451600261166a9190612280565b6116749190612298565b61167f9060046122ac565b9050600061168e826020612280565b67ffffffffffffffff8111156116b457634e487b7160e01b600052604160045260246000fd5b6040519080825280601f01601f1916602001820160405280156116de576020820181803683370190505b509050818152600183018586518101602084015b8183101561174c5760039283018051603f601282901c811687015160f890811b8552600c83901c8216880151811b6001860152600683901c8216880151811b60028601529116860151901b938201939093526004016116f2565b600389510660018114611766576002811461177757611783565b613d3d60f01b600119830152611783565b603d60f81b6000198301525b509398975050505050505050565b6002546001600160a01b0385166117ba57604051622e076360e81b815260040160405180910390fd5b836117d85760405163b562e8dd60e01b815260040160405180910390fd5b6001600160a01b038516600081815260086020908152604080832080546fffffffffffffffffffffffffffffffff19811667ffffffffffffffff8083168c0181169182176801000000000000000067ffffffffffffffff1990941690921783900481168c01811690920217909155858452600790925290912080546001600160e01b031916909217600160a01b42909216919091021790558080850183801561188e575061188e876001600160a01b03166110b4565b15611917575b60405182906001600160a01b038916906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a46118df60008884806001019550886110f0565b6118fc576040516368d2bf6b60e11b815260040160405180910390fd5b8082141561189457826002541461191257600080fd5b61195d565b5b6040516001830192906001600160a01b038916906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a480821415611918575b50600255610f84565b8280546119729061230e565b90600052602060002090601f01602090048101928261199457600085556119da565b82601f106119ad57805160ff19168380011785556119da565b828001600101855582156119da579182015b828111156119da5782518255916020019190600101906119bf565b506119e69291506119ea565b5090565b5b808211156119e657600081556001016119eb565b600067ffffffffffffffff80841115611a1a57611a1a6123a4565b604051601f8501601f19908116603f01168101908282118183101715611a4257611a426123a4565b81604052809350858152868686011115611a5b57600080fd5b858560208301376000602087830101525050509392505050565b80356001600160a01b0381168114611a8c57600080fd5b919050565b600082601f830112611aa1578081fd5b610d76838335602085016119ff565b600060208284031215611ac1578081fd5b610d7682611a75565b60008060408385031215611adc578081fd5b611ae583611a75565b9150611af360208401611a75565b90509250929050565b600080600060608486031215611b10578081fd5b611b1984611a75565b9250611b2760208501611a75565b9150604084013590509250925092565b60008060008060808587031215611b4c578081fd5b611b5585611a75565b9350611b6360208601611a75565b925060408501359150606085013567ffffffffffffffff811115611b85578182fd5b8501601f81018713611b95578182fd5b611ba4878235602084016119ff565b91505092959194509250565b60008060408385031215611bc2578182fd5b611bcb83611a75565b915060208301358015158114611bdf578182fd5b809150509250929050565b60008060408385031215611bfc578182fd5b611c0583611a75565b946020939093013593505050565b600060208284031215611c24578081fd5b8135610d76816123ba565b600060208284031215611c40578081fd5b8151610d76816123ba565b600060208284031215611c5c578081fd5b5035919050565b600080600080600060a08688031215611c7a578081fd5b85359450602086013567ffffffffffffffff80821115611c98578283fd5b611ca489838a01611a91565b95506040880135915080821115611cb9578283fd5b611cc589838a01611a91565b94506060880135915080821115611cda578283fd5b611ce689838a01611a91565b93506080880135915080821115611cfb578283fd5b50611d0888828901611a91565b9150509295509295909350565b60008151808452611d2d8160208601602086016122e2565b601f01601f19169290920160200192915050565b60008151611d538185602086016122e2565b9290920192915050565b683d913730b6b2911d1160b91b8152654c696e65202360d01b600982015283516000906020611d9282600f8601838a016122e2565b71111610113232b9b1b934b83a34b7b7111d1160711b600f9285019283015285546021908490600181811c9080831680611dcd57607f831692505b868310811415611deb57634e487b7160e01b89526022600452602489fd5b808015611dff5760018114611e1457611e44565b60ff1985168988015283890187019550611e44565b60008d8152602090208a5b85811015611e3a5781548b82018a0152908401908901611e1f565b505086848a010195505b5050505050611edc611ecf611ec1611ea4611e9e611e75866c1116101134b6b0b3b2911d101160991b8152600d0190565b7f646174613a696d6167652f7376672b786d6c3b6261736536342c0000000000008152601a0190565b8b611d41565b7001116101130ba3a3934b13aba32b9911d1607d1b815260110190565b615b5d60f01b815260020190565b607d60f81b815260010190565b9998505050505050505050565b7f3c7376672077696474683d223132303022206865696768743d2233303022207881527f6d6c6e733d22687474703a2f2f7777772e77332e6f72672f323030302f737667602082015261111f60f11b60408201527f3c72656374206865696768743d22333030222077696474683d2231323030222060428201527f66696c6c3d2268736c283332382c20313030252c203130302529222f3e00000060628201527f3c7465787420783d223530252220793d2234302522202066696c6c3d2268736c607f8201527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f72609f820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b60bf8201526000855161200c8160d8850160208a016122e2565b6121ea6121d86120bd6121d26121416120bd611e9e6120d06120bd6120b761204660d88c8f0101661e17ba32bc3a1f60c91b815260070190565b7f3c7465787420783d223530252220793d2235302522202066696c6c3d2268736c81527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f726020820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b604082015260590190565b8f611d41565b661e17ba32bc3a1f60c91b815260070190565b7f3c7465787420783d223530252220793d2236302522202066696c6c3d2268736c81527f2872616e646f6d2c20313030252c20383025292220746578742d616e63686f726020820152781e9136b4b232363291103337b73a16b9b4bd329e911919911f60391b604082015260590190565b7f3c7465787420783d223530252220793d223230252220646f6d696e616e742d6281527f6173656c696e653d226d6964646c65222066696c6c3d2268736c2872616e646f60208201527f6d2c20313030252c20383025292220746578742d616e63686f723d226d696464604082015272363291103337b73a16b9b4bd329e911a18911f60691b606082015260730190565b87611d41565b651e17b9bb339f60d11b815260060190565b979650505050505050565b7f646174613a6170706c69636174696f6e2f6a736f6e3b6261736536342c00000081526000825161222d81601d8501602087016122e2565b91909101601d0192915050565b6001600160a01b038581168252841660208201526040810183905260806060820181905260009061161190830184611d15565b602081526000610d766020830184611d15565b6000821982111561229357612293612378565b500190565b6000826122a7576122a761238e565b500490565b60008160001904831182151516156122c6576122c6612378565b500290565b6000828210156122dd576122dd612378565b500390565b60005b838110156122fd5781810151838201526020016122e5565b83811115610bb95750506000910152565b600181811c9082168061232257607f821691505b6020821081141561234357634e487b7160e01b600052602260045260246000fd5b50919050565b600060001982141561235d5761235d612378565b5060010190565b6000826123735761237361238e565b500690565b634e487b7160e01b600052601160045260246000fd5b634e487b7160e01b600052601260045260246000fd5b634e487b7160e01b600052604160045260246000fd5b6001600160e01b0319811681146107b057600080fdfe4142434445464748494a4b4c4d4e4f505152535455565758595a6162636465666768696a6b6c6d6e6f707172737475767778797a303132333435363738392b2fa2646970667358221220a254f1bf1132049008dc255143963394df7602cda125a662a32265ded41204f664736f6c63430008040033
Deployed Bytecode Sourcemap
74112:4801:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;47470:305;;;;;;;;;;-1:-1:-1;47470:305:0;;;;;:::i;:::-;;:::i;:::-;;;14137:14:1;;14130:22;14112:41;;14100:2;14085:18;47470:305:0;;;;;;;;50583:100;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;51722:204::-;;;;;;;;;;-1:-1:-1;51722:204:0;;;;;:::i;:::-;;:::i;:::-;;;-1:-1:-1;;;;;13435:32:1;;;13417:51;;13405:2;13390:18;51722:204:0;13372:102:1;51285:371:0;;;;;;;;;;-1:-1:-1;51285:371:0;;;;;:::i;:::-;;:::i;:::-;;74642:27;;;;;;;;;;;;;;;;;;;16740:25:1;;;16728:2;16713:18;74642:27:0;16695:76:1;75314:211:0;;;:::i;75139:167::-;;;;;;;;;;-1:-1:-1;75139:167:0;;;;;:::i;:::-;;:::i;46719:303::-;;;;;;;;;;-1:-1:-1;46973:12:0;;46957:13;;:28;-1:-1:-1;;46957:46:0;46719:303;;43644:43;;;;;;;;;;-1:-1:-1;43644:43:0;;;;;:::i;:::-;;;;;;;;;;;;;;;;52587:170;;;;;;;;;;-1:-1:-1;52587:170:0;;;;;:::i;:::-;;:::i;52828:185::-;;;;;;;;;;-1:-1:-1;52828:185:0;;;;;:::i;:::-;;:::i;50391:125::-;;;;;;;;;;-1:-1:-1;50391:125:0;;;;;:::i;:::-;;:::i;45559:89::-;;;;;;;;;;;;;:::i;47839:206::-;;;;;;;;;;-1:-1:-1;47839:206:0;;;;;:::i;:::-;;:::i;74233:25::-;;;;;;;;;;;;;:::i;74539:20::-;;;;;;;;;;-1:-1:-1;74539:20:0;;;;-1:-1:-1;;;;;74539:20:0;;;74491:39;;;;;;;;;;-1:-1:-1;74491:39:0;;;;;:::i;:::-;;;;;;;;;;;;;;;;50752:104;;;;;;;;;;;;;:::i;51998:287::-;;;;;;;;;;-1:-1:-1;51998:287:0;;;;;:::i;:::-;;:::i;74326:49::-;;;;;;;;;;-1:-1:-1;74326:49:0;;;;;:::i;:::-;;:::i;75533:685::-;;;;;;;;;;-1:-1:-1;75533:685:0;;;;;:::i;:::-;;:::i;53084:369::-;;;;;;;;;;-1:-1:-1;53084:369:0;;;;;:::i;:::-;;:::i;78595:313::-;;;;;;;;;;-1:-1:-1;78595:313:0;;;;;:::i;:::-;;:::i;74384:49::-;;;;;;;;;;-1:-1:-1;74384:49:0;;;;;:::i;:::-;;:::i;52356:164::-;;;;;;;;;;-1:-1:-1;52356:164:0;;;;;:::i;:::-;-1:-1:-1;;;;;52477:25:0;;;52453:4;52477:25;;;:18;:25;;;;;;;;:35;;;;;;;;;;;;;;;52356:164;74442:40;;;;;;;;;;-1:-1:-1;74442:40:0;;;;;:::i;:::-;;:::i;74568:65::-;;;;;;;;;;-1:-1:-1;74568:65:0;;;;-1:-1:-1;;;;;74568:65:0;;;74269:48;;;;;;;;;;-1:-1:-1;74269:48:0;;;;;:::i;:::-;;:::i;47470:305::-;47572:4;-1:-1:-1;;;;;;47609:40:0;;-1:-1:-1;;;47609:40:0;;:105;;-1:-1:-1;;;;;;;47666:48:0;;-1:-1:-1;;;47666:48:0;47609:105;:158;;;-1:-1:-1;;;;;;;33446:33:0;;33422:4;33446:33;;;;;;;;;;;;;47731:36;47589:178;47470:305;-1:-1:-1;;47470:305:0:o;50583:100::-;50637:13;50670:5;50663:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;50583:100;:::o;51722:204::-;51790:7;51815:16;51823:7;51815;:16::i;:::-;51810:64;;51840:34;;-1:-1:-1;;;51840:34:0;;;;;;;;;;;51810:64;-1:-1:-1;51894:24:0;;;;:15;:24;;;;;;-1:-1:-1;;;;;51894:24:0;;51722:204::o;51285:371::-;51358:13;51374:24;51390:7;51374:15;:24::i;:::-;51358:40;;51419:5;-1:-1:-1;;;;;51413:11:0;:2;-1:-1:-1;;;;;51413:11:0;;51409:48;;;51433:24;;-1:-1:-1;;;51433:24:0;;;;;;;;;;;51409:48;3322:10;-1:-1:-1;;;;;51474:21:0;;;;;;:63;;-1:-1:-1;51500:37:0;51517:5;3322:10;52356:164;:::i;51500:37::-;51499:38;51474:63;51470:138;;;51561:35;;-1:-1:-1;;;51561:35:0;;;;;;;;;;;51470:138;51620:28;51629:2;51633:7;51642:5;51620:8;:28::i;:::-;51285:371;;;:::o;75314:211::-;46973:12;;46957:13;;75365:19;;46957:28;;-1:-1:-1;;46957:46:0;75444:9;;75365:35;;-1:-1:-1;75422:18:0;75365:35;75438:1;75422:15;:18::i;:::-;:31;;75413:63;;;;-1:-1:-1;;;75413:63:0;;16042:2:1;75413:63:0;;;16024:21:1;16081:2;16061:18;;;16054:30;-1:-1:-1;;;16100:18:1;;;16093:48;16158:18;;75413:63:0;;;;;;;;;75489:26;75499:10;75511:3;75489:9;:26::i;:::-;75314:211;:::o;75139:167::-;75208:5;;-1:-1:-1;;;;;75208:5:0;75217:10;75208:19;75199:72;;;;-1:-1:-1;;;75199:72:0;;16389:2:1;75199:72:0;;;16371:21:1;16428:2;16408:18;;;16401:30;16467:34;16447:18;;;16440:62;-1:-1:-1;;;16518:18:1;;;16511:36;16564:19;;75199:72:0;16361:228:1;75199:72:0;75284:5;:14;;-1:-1:-1;;;;;;75284:14:0;-1:-1:-1;;;;;75284:14:0;;;;;;;;;;75139:167::o;52587:170::-;52721:28;52731:4;52737:2;52741:7;52721:9;:28::i;52828:185::-;52966:39;52983:4;52989:2;52993:7;52966:39;;;;;;;;;;;;:16;:39::i;50391:125::-;50455:7;50482:21;50495:7;50482:12;:21::i;:::-;:26;;50391:125;-1:-1:-1;;50391:125:0:o;45559:89::-;45599:13;45632:8;45625:15;;;;;:::i;47839:206::-;47903:7;-1:-1:-1;;;;;47927:19:0;;47923:60;;47955:28;;-1:-1:-1;;;47955:28:0;;;;;;;;;;;47923:60;-1:-1:-1;;;;;;48009:19:0;;;;;:12;:19;;;;;:27;;;;47839:206::o;74233:25::-;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;50752:104::-;50808:13;50841:7;50834:14;;;;;:::i;51998:287::-;-1:-1:-1;;;;;52097:24:0;;3322:10;52097:24;52093:54;;;52130:17;;-1:-1:-1;;;52130:17:0;;;;;;;;;;;52093:54;3322:10;52160:32;;;;:18;:32;;;;;;;;-1:-1:-1;;;;;52160:42:0;;;;;;;;;;;;:53;;-1:-1:-1;;52160:53:0;;;;;;;;;;52229:48;;14112:41:1;;;52160:42:0;;3322:10;52229:48;;14085:18:1;52229:48:0;;;;;;;51998:287;;:::o;74326:49::-;;;;;;;;;;;;;;;;:::i;75533:685::-;75864:5;;-1:-1:-1;;;;;75864:5:0;75850:10;:19;;:42;;-1:-1:-1;75887:5:0;;-1:-1:-1;;;;;75887:5:0;75873:10;:19;75850:42;75842:66;;;;-1:-1:-1;;;75842:66:0;;15286:2:1;75842:66:0;;;15268:21:1;15325:2;15305:18;;;15298:30;-1:-1:-1;;;15344:18:1;;;15337:41;15395:18;;75842:66:0;15258:161:1;75842:66:0;75929:16;;;;:7;:16;;;;;;;;75927:18;75919:42;;;;-1:-1:-1;;;75919:42:0;;14946:2:1;75919:42:0;;;14928:21:1;14985:2;14965:18;;;14958:30;-1:-1:-1;;;15004:18:1;;;14997:41;15055:18;;75919:42:0;14918:161:1;75919:42:0;75974:23;;;;:14;:23;;;;;;;;:35;;;;;;;;:::i;:::-;-1:-1:-1;76051:24:0;;;;:15;:24;;;;;;;;:37;;;;;;;;:::i;:::-;-1:-1:-1;76099:24:0;;;;:15;:24;;;;;;;;:37;;;;;;;;:::i;:::-;-1:-1:-1;76147:15:0;;;;:6;:15;;;;;;;;:25;;;;;;;;:::i;:::-;-1:-1:-1;;;76185:16:0;;;;-1:-1:-1;;76185:7:0;:16;;;;;:23;;-1:-1:-1;;76185:23:0;76204:4;76185:23;;;75533:685::o;53084:369::-;53251:28;53261:4;53267:2;53271:7;53251:9;:28::i;:::-;53294:15;:2;-1:-1:-1;;;;;53294:13:0;;:15::i;:::-;:76;;;;;53314:56;53345:4;53351:2;53355:7;53364:5;53314:30;:56::i;:::-;53313:57;53294:76;53290:156;;;53394:40;;-1:-1:-1;;;53394:40:0;;;;;;;;;;;53290:156;53084:369;;;;:::o;78595:313::-;78714:13;78767:17;78775:8;78767:7;:17::i;:::-;78745:114;;;;-1:-1:-1;;;78745:114:0;;15626:2:1;78745:114:0;;;15608:21:1;15665:2;15645:18;;;15638:30;15704:34;15684:18;;;15677:62;-1:-1:-1;;;15755:18:1;;;15748:45;15810:19;;78745:114:0;15598:237:1;78745:114:0;78877:23;78891:8;78877:13;:23::i;74384:49::-;;;;;;;;;;;;;;;;:::i;74442:40::-;;;;;;;;;;;;;;;;:::i;74269:48::-;;;;;;;;;;;;;;;;:::i;53708:187::-;53765:4;53808:7;46576:1;53789:26;;:53;;;;;53829:13;;53819:7;:23;53789:53;:98;;;;-1:-1:-1;;53860:20:0;;;;:11;:20;;;;;:27;-1:-1:-1;;;53860:27:0;;;;53859:28;;53708:187::o;61878:196::-;61993:24;;;;:15;:24;;;;;;:29;;-1:-1:-1;;;;;;61993:29:0;-1:-1:-1;;;;;61993:29:0;;;;;;;;;62038:28;;61993:24;;62038:28;;;;;;;61878:196;;;:::o;68928:181::-;68986:7;;69018:5;69022:1;69018;:5;:::i;:::-;69006:17;;69047:1;69042;:6;;69034:46;;;;-1:-1:-1;;;69034:46:0;;14590:2:1;69034:46:0;;;14572:21:1;14629:2;14609:18;;;14602:30;14668:29;14648:18;;;14641:57;14715:18;;69034:46:0;14562:177:1;69034:46:0;69100:1;68928:181;-1:-1:-1;;;68928:181:0:o;53903:104::-;53972:27;53982:2;53986:8;53972:27;;;;;;;;;;;;:9;:27::i;:::-;53903:104;;:::o;56821:2130::-;56936:35;56974:21;56987:7;56974:12;:21::i;:::-;56936:59;;57034:4;-1:-1:-1;;;;;57012:26:0;:13;:18;;;-1:-1:-1;;;;;57012:26:0;;57008:67;;57047:28;;-1:-1:-1;;;57047:28:0;;;;;;;;;;;57008:67;57088:22;3322:10;-1:-1:-1;;;;;57114:20:0;;;;:73;;-1:-1:-1;57151:36:0;57168:4;3322:10;52356:164;:::i;57151:36::-;57114:126;;;-1:-1:-1;3322:10:0;57204:20;57216:7;57204:11;:20::i;:::-;-1:-1:-1;;;;;57204:36:0;;57114:126;57088:153;;57259:17;57254:66;;57285:35;;-1:-1:-1;;;57285:35:0;;;;;;;;;;;57254:66;-1:-1:-1;;;;;57335:16:0;;57331:52;;57360:23;;-1:-1:-1;;;57360:23:0;;;;;;;;;;;57331:52;57504:35;57521:1;57525:7;57534:4;57504:8;:35::i;:::-;-1:-1:-1;;;;;57835:18:0;;;;;;;:12;:18;;;;;;;;:31;;-1:-1:-1;;57835:31:0;;;;;;;-1:-1:-1;;57835:31:0;;;;;;;57881:16;;;;;;;;;:29;;;;;;;;-1:-1:-1;57881:29:0;;;;;;;;;;;57961:20;;;:11;:20;;;;;;57996:18;;-1:-1:-1;;;;;;58029:49:0;;;;-1:-1:-1;;;58062:15:0;58029:49;;;;;;;;;;58352:11;;58412:24;;;;;58455:13;;57961:20;;58412:24;;58455:13;58451:384;;58665:13;;58650:11;:28;58646:174;;58703:20;;58772:28;;;;58746:54;;-1:-1:-1;;;58746:54:0;-1:-1:-1;;;;;;58746:54:0;;;-1:-1:-1;;;;;58703:20:0;;58746:54;;;;58646:174;56821:2130;;;58882:7;58878:2;-1:-1:-1;;;;;58863:27:0;58872:4;-1:-1:-1;;;;;58863:27:0;;;;;;;;;;;58901:42;56821:2130;;;;;:::o;49220:1109::-;-1:-1:-1;;;;;;;;;;;;;;;;;;;;;;;;;49331:7:0;;46576:1;49380:23;;:47;;;;;49414:13;;49407:4;:20;49380:47;49376:886;;;49448:31;49482:17;;;:11;:17;;;;;;;;;49448:51;;;;;;;;;-1:-1:-1;;;;;49448:51:0;;;;-1:-1:-1;;;49448:51:0;;;;;;;;;;;-1:-1:-1;;;49448:51:0;;;;;;;;;;;;;;49518:729;;49568:14;;-1:-1:-1;;;;;49568:28:0;;49564:101;;49632:9;49220:1109;-1:-1:-1;;;49220:1109:0:o;49564:101::-;-1:-1:-1;;;50007:6:0;50052:17;;;;:11;:17;;;;;;;;;50040:29;;;;;;;;;-1:-1:-1;;;;;50040:29:0;;;;;-1:-1:-1;;;50040:29:0;;;;;;;;;;;-1:-1:-1;;;50040:29:0;;;;;;;;;;;;;50100:28;50096:109;;50168:9;49220:1109;-1:-1:-1;;;49220:1109:0:o;50096:109::-;49967:261;;;49376:886;;50290:31;;-1:-1:-1;;;50290:31:0;;;;;;;;;;;16223:755;16281:17;16863:18;;16767:66;16929:15;;;;;:42;;;16960:11;16948:8;:23;;16929:42;16913:59;16223:755;-1:-1:-1;;;;16223:755:0:o;62566:667::-;62750:72;;-1:-1:-1;;;62750:72:0;;62729:4;;-1:-1:-1;;;;;62750:36:0;;;;;:72;;3322:10;;62801:4;;62807:7;;62816:5;;62750:72;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;62750:72:0;;;;;;;;-1:-1:-1;;62750:72:0;;;;;;;;;;;;:::i;:::-;;;62746:480;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;62984:13:0;;62980:235;;63030:40;;-1:-1:-1;;;63030:40:0;;;;;;;;;;;62980:235;63173:6;63167:13;63158:6;63154:2;63150:15;63143:38;62746:480;-1:-1:-1;;;;;;62869:55:0;-1:-1:-1;;;62869:55:0;;-1:-1:-1;62566:667:0;;;;;;:::o;77529:1058::-;77619:13;77650:17;77670:26;77687:8;77670:16;:26::i;:::-;77650:46;;77845:700;78061:3;78154:11;78313:20;78324:8;78313:10;:20::i;:::-;77921:574;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;77845:13;:700::i;:::-;77752:812;;;;;;;;:::i;:::-;;;;;;;;;;;;;77707:872;;;77529:1058;;;:::o;54370:163::-;54493:32;54499:2;54503:8;54513:5;54520:4;54493:5;:32::i;40723:723::-;40779:13;41000:10;40996:53;;-1:-1:-1;;41027:10:0;;;;;;;;;;;;-1:-1:-1;;;41027:10:0;;;;;40723:723::o;40996:53::-;41074:5;41059:12;41115:78;41122:9;;41115:78;;41148:8;;;;:::i;:::-;;-1:-1:-1;41171:10:0;;-1:-1:-1;41179:2:0;41171:10;;:::i;:::-;;;41115:78;;;41203:19;41235:6;41225:17;;;;;;-1:-1:-1;;;41225:17:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;41225:17:0;;41203:39;;41253:154;41260:10;;41253:154;;41287:11;41297:1;41287:11;;:::i;:::-;;-1:-1:-1;41356:10:0;41364:2;41356:5;:10;:::i;:::-;41343:24;;:2;:24;:::i;:::-;41330:39;;41313:6;41320;41313:14;;;;;;-1:-1:-1;;;41313:14:0;;;;;;;;;;;;:56;-1:-1:-1;;;;;41313:56:0;;;;;;;;-1:-1:-1;41384:11:0;41393:2;41384:11;;:::i;:::-;;;41253:154;;76226:1295;76312:25;76340:24;;;:14;:24;;;;;76312:52;;76286:13;;76312:25;76340:24;76312:52;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;76375:26;76404:15;:25;76420:8;76404:25;;;;;;;;;;;76375:54;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;76440:26;76469:15;:25;76485:8;76469:25;;;;;;;;;;;76440:54;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;76505:21;76529:6;:16;76536:8;76529:16;;;;;;;;;;;76505:40;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;76576:937;76956:11;77096:12;77237;77404:7;76636:843;;;;;;;;;;;:::i;76576:937::-;76556:957;76226:1295;-1:-1:-1;;;;;;76226:1295:0:o;439:2256::-;497:13;527:4;:11;542:1;527:16;523:31;;;-1:-1:-1;;545:9:0;;;;;;;;;-1:-1:-1;545:9:0;;;439:2256::o;523:31::-;606:19;628:5;;;;;;;;;;;;;;;;;606:27;;685:18;731:1;712:4;:11;726:1;712:15;;;;:::i;:::-;711:21;;;;:::i;:::-;706:27;;:1;:27;:::i;:::-;685:48;-1:-1:-1;816:20:0;850:15;685:48;863:2;850:15;:::i;:::-;839:27;;;;;;-1:-1:-1;;;839:27:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;839:27:0;;816:50;;963:10;955:6;948:26;1058:1;1051:5;1047:13;1117:4;1168;1162:11;1153:7;1149:25;1264:2;1256:6;1252:15;1337:1045;1372:6;1363:7;1360:19;1337:1045;;;1442:1;1429:15;;;1510:14;;1693:4;1681:2;1677:14;;;1673:25;;1659:40;;1653:47;1648:3;1644:57;;;1583:137;;1884:2;1880:14;;;1876:25;;1862:40;;1856:47;1847:57;;1766:1;1751:17;;1786:137;2087:1;2083:13;;;2079:24;;2065:39;;2059:46;2050:56;;1954:17;;;1989:136;2281:16;;2267:31;;2261:38;2252:48;;2156:17;;;2191:128;;;;2350:17;;1337:1045;;;2455:1;2448:4;2442:11;2438:19;2476:1;2471:84;;;;2574:1;2569:82;;;;2431:220;;2471:84;-1:-1:-1;;;;;2504:17:0;;2497:43;2471:84;;2569:82;-1:-1:-1;;;;;2602:17:0;;2595:41;2431:220;-1:-1:-1;2681:6:0;;439:2256;-1:-1:-1;;;;;;;;439:2256:0:o;54792:1775::-;54954:13;;-1:-1:-1;;;;;54982:16:0;;54978:48;;55007:19;;-1:-1:-1;;;55007:19:0;;;;;;;;;;;54978:48;55041:13;55037:44;;55063:18;;-1:-1:-1;;;55063:18:0;;;;;;;;;;;55037:44;-1:-1:-1;;;;;55432:16:0;;;;;;:12;:16;;;;;;;;:44;;-1:-1:-1;;55491:49:0;;55432:44;;;;;;;;55491:49;;;;-1:-1:-1;;55432:44:0;;;;;;55491:49;;;;;;;;;;;;;;;;55557:25;;;:11;:25;;;;;;:35;;-1:-1:-1;;;;;;55607:66:0;;;;-1:-1:-1;;;55657:15:0;55607:66;;;;;;;;;;55557:25;55754:23;;;55798:4;:23;;;;;55806:15;:2;-1:-1:-1;;;;;55806:13:0;;:15::i;:::-;55794:641;;;55842:314;55873:38;;55898:12;;-1:-1:-1;;;;;55873:38:0;;;55890:1;;55873:38;;55890:1;;55873:38;55939:69;55978:1;55982:2;55986:14;;;;;;56002:5;55939:30;:69::i;:::-;55934:174;;56044:40;;-1:-1:-1;;;56044:40:0;;;;;;;;;;;55934:174;56151:3;56135:12;:19;;55842:314;;56237:12;56220:13;;:29;56216:43;;56251:8;;;56216:43;55794:641;;;56300:120;56331:40;;56356:14;;;;;-1:-1:-1;;;;;56331:40:0;;;56348:1;;56331:40;;56348:1;;56331:40;56415:3;56399:12;:19;;56300:120;;55794:641;-1:-1:-1;56449:13:0;:28;56499:60;53084:369;-1:-1:-1;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;:::o;:::-;;;;;;;;;;;;;;;14:631:1;78:5;108:18;149:2;141:6;138:14;135:2;;;155:18;;:::i;:::-;230:2;224:9;198:2;284:15;;-1:-1:-1;;280:24:1;;;306:2;276:33;272:42;260:55;;;330:18;;;350:22;;;327:46;324:2;;;376:18;;:::i;:::-;416:10;412:2;405:22;445:6;436:15;;475:6;467;460:22;515:3;506:6;501:3;497:16;494:25;491:2;;;532:1;529;522:12;491:2;582:6;577:3;570:4;562:6;558:17;545:44;637:1;630:4;621:6;613;609:19;605:30;598:41;;;;88:557;;;;;:::o;650:173::-;718:20;;-1:-1:-1;;;;;767:31:1;;757:42;;747:2;;813:1;810;803:12;747:2;699:124;;;:::o;828:229::-;871:5;924:3;917:4;909:6;905:17;901:27;891:2;;946:5;939;932:20;891:2;972:79;1047:3;1038:6;1025:20;1018:4;1010:6;1006:17;972:79;:::i;1062:196::-;1121:6;1174:2;1162:9;1153:7;1149:23;1145:32;1142:2;;;1195:6;1187;1180:22;1142:2;1223:29;1242:9;1223:29;:::i;1263:270::-;1331:6;1339;1392:2;1380:9;1371:7;1367:23;1363:32;1360:2;;;1413:6;1405;1398:22;1360:2;1441:29;1460:9;1441:29;:::i;:::-;1431:39;;1489:38;1523:2;1512:9;1508:18;1489:38;:::i;:::-;1479:48;;1350:183;;;;;:::o;1538:338::-;1615:6;1623;1631;1684:2;1672:9;1663:7;1659:23;1655:32;1652:2;;;1705:6;1697;1690:22;1652:2;1733:29;1752:9;1733:29;:::i;:::-;1723:39;;1781:38;1815:2;1804:9;1800:18;1781:38;:::i;:::-;1771:48;;1866:2;1855:9;1851:18;1838:32;1828:42;;1642:234;;;;;:::o;1881:696::-;1976:6;1984;1992;2000;2053:3;2041:9;2032:7;2028:23;2024:33;2021:2;;;2075:6;2067;2060:22;2021:2;2103:29;2122:9;2103:29;:::i;:::-;2093:39;;2151:38;2185:2;2174:9;2170:18;2151:38;:::i;:::-;2141:48;;2236:2;2225:9;2221:18;2208:32;2198:42;;2291:2;2280:9;2276:18;2263:32;2318:18;2310:6;2307:30;2304:2;;;2355:6;2347;2340:22;2304:2;2383:22;;2436:4;2428:13;;2424:27;-1:-1:-1;2414:2:1;;2470:6;2462;2455:22;2414:2;2498:73;2563:7;2558:2;2545:16;2540:2;2536;2532:11;2498:73;:::i;:::-;2488:83;;;2011:566;;;;;;;:::o;2582:367::-;2647:6;2655;2708:2;2696:9;2687:7;2683:23;2679:32;2676:2;;;2729:6;2721;2714:22;2676:2;2757:29;2776:9;2757:29;:::i;:::-;2747:39;;2836:2;2825:9;2821:18;2808:32;2883:5;2876:13;2869:21;2862:5;2859:32;2849:2;;2910:6;2902;2895:22;2849:2;2938:5;2928:15;;;2666:283;;;;;:::o;2954:264::-;3022:6;3030;3083:2;3071:9;3062:7;3058:23;3054:32;3051:2;;;3104:6;3096;3089:22;3051:2;3132:29;3151:9;3132:29;:::i;:::-;3122:39;3208:2;3193:18;;;;3180:32;;-1:-1:-1;;;3041:177:1:o;3223:255::-;3281:6;3334:2;3322:9;3313:7;3309:23;3305:32;3302:2;;;3355:6;3347;3340:22;3302:2;3399:9;3386:23;3418:30;3442:5;3418:30;:::i;3483:259::-;3552:6;3605:2;3593:9;3584:7;3580:23;3576:32;3573:2;;;3626:6;3618;3611:22;3573:2;3663:9;3657:16;3682:30;3706:5;3682:30;:::i;3747:190::-;3806:6;3859:2;3847:9;3838:7;3834:23;3830:32;3827:2;;;3880:6;3872;3865:22;3827:2;-1:-1:-1;3908:23:1;;3817:120;-1:-1:-1;3817:120:1:o;3942:1063::-;4077:6;4085;4093;4101;4109;4162:3;4150:9;4141:7;4137:23;4133:33;4130:2;;;4184:6;4176;4169:22;4130:2;4225:9;4212:23;4202:33;;4286:2;4275:9;4271:18;4258:32;4309:18;4350:2;4342:6;4339:14;4336:2;;;4371:6;4363;4356:22;4336:2;4399:50;4441:7;4432:6;4421:9;4417:22;4399:50;:::i;:::-;4389:60;;4502:2;4491:9;4487:18;4474:32;4458:48;;4531:2;4521:8;4518:16;4515:2;;;4552:6;4544;4537:22;4515:2;4580:52;4624:7;4613:8;4602:9;4598:24;4580:52;:::i;:::-;4570:62;;4685:2;4674:9;4670:18;4657:32;4641:48;;4714:2;4704:8;4701:16;4698:2;;;4735:6;4727;4720:22;4698:2;4763:52;4807:7;4796:8;4785:9;4781:24;4763:52;:::i;:::-;4753:62;;4868:3;4857:9;4853:19;4840:33;4824:49;;4898:2;4888:8;4885:16;4882:2;;;4919:6;4911;4904:22;4882:2;;4947:52;4991:7;4980:8;4969:9;4965:24;4947:52;:::i;:::-;4937:62;;;4120:885;;;;;;;;:::o;5010:257::-;5051:3;5089:5;5083:12;5116:6;5111:3;5104:19;5132:63;5188:6;5181:4;5176:3;5172:14;5165:4;5158:5;5154:16;5132:63;:::i;:::-;5249:2;5228:15;-1:-1:-1;;5224:29:1;5215:39;;;;5256:4;5211:50;;5059:208;-1:-1:-1;;5059:208:1:o;5272:185::-;5314:3;5352:5;5346:12;5367:52;5412:6;5407:3;5400:4;5393:5;5389:16;5367:52;:::i;:::-;5435:16;;;;;5322:135;-1:-1:-1;;5322:135:1:o;7621:2591::-;-1:-1:-1;;;8671:43:1;;-1:-1:-1;;;8739:1:1;8730:11;;8723:29;8775:13;;-1:-1:-1;;8807:4:1;8820:60;8775:13;8868:2;8859:12;;8842:15;;;8820:60;:::i;:::-;-1:-1:-1;;;8939:2:1;8899:16;;;8931:11;;;8924:69;9063:13;;9012:2;;9034:3;;9123:1;9145:18;;;;9198;;;;9225:2;;9303:4;9293:8;9289:19;9277:31;;9225:2;9366;9356:8;9353:16;9333:18;9330:40;9327:2;;;-1:-1:-1;;;9393:33:1;;9449:4;9446:1;9439:15;9479:4;9400:3;9467:17;9327:2;9510:18;9537:122;;;;9673:1;9668:342;;;;9503:507;;9537:122;-1:-1:-1;;9578:24:1;;9565:11;;;9558:45;9627:17;;;9623:26;;;-1:-1:-1;9537:122:1;;9668:342;16823:4;16842:17;;;16892:4;16876:21;;9763:3;9779:175;9793:8;9790:1;9787:15;9779:175;;;9881:14;;9864:10;;;9860:19;;9853:43;9924:16;;;;9810:10;;9779:175;;;9783:3;;9997:2;9986:8;9982:2;9978:17;9974:26;9967:33;;9503:507;;;;;;10026:180;10056:149;10081:123;10111:92;10137:65;10167:34;10197:3;-1:-1:-1;;;6766:51:1;;6842:2;6833:12;;6756:95;10167:34;7553:28;7541:41;;7607:2;7598:12;;7531:85;10137:65;10129:6;10111:92;:::i;:::-;-1:-1:-1;;;5527:59:1;;5611:2;5602:12;;5517:103;10081:123;-1:-1:-1;;;6062:17:1;;6104:1;6095:11;;6052:60;10056:149;-1:-1:-1;;;6921:16:1;;6962:1;6953:11;;6911:59;10026:180;10019:187;8661:1551;-1:-1:-1;;;;;;;;;8661:1551:1:o;10217:2596::-;11633:66;11628:3;11621:79;11730:66;11725:2;11720:3;11716:12;11709:88;11836:4;11831:3;11827:14;11822:2;11817:3;11813:12;11806:36;11872:66;11867:2;11862:3;11858:12;11851:88;11969:66;11964:2;11959:3;11955:12;11948:88;12067:66;12061:3;12056;12052:13;12045:89;12165:66;12159:3;12154;12150:13;12143:89;-1:-1:-1;;;12257:3:1;12252;12248:13;12241:89;11603:3;12359:6;12353:13;12375:61;12429:6;12423:3;12418;12414:13;12409:2;12401:6;12397:15;12375:61;:::i;:::-;12452:355;12482:324;12512:293;12538:266;12568:235;12598:204;12624:177;12654:146;12684:115;12710:88;12740:57;12792:3;12783:6;12778:3;12774:16;12770:26;-1:-1:-1;;;6641:22:1;;6688:1;6679:11;;6631:65;12740:57;5702:66;5690:79;;5799:66;5794:2;5785:12;;5778:88;-1:-1:-1;;;5891:2:1;5882:12;;5875:88;5988:2;5979:12;;5680:317;12710:88;12702:6;12684:115;:::i;:::-;-1:-1:-1;;;6641:22:1;;6688:1;6679:11;;6631:65;12654:146;7052:66;7040:79;;7149:66;7144:2;7135:12;;7128:88;-1:-1:-1;;;7241:2:1;7232:12;;7225:88;7338:2;7329:12;;7030:317;12568:235;6194:66;6182:79;;6291:66;6286:2;6277:12;;6270:88;6388:66;6383:2;6374:12;;6367:88;-1:-1:-1;;;6480:2:1;6471:12;;6464:72;6561:3;6552:13;;6172:399;12538:266;12530:6;12512:293;:::i;12482:324::-;-1:-1:-1;;;7417:21:1;;7463:1;7454:11;;7407:64;12452:355;12445:362;11611:1202;-1:-1:-1;;;;;;;11611:1202:1:o;12818:448::-;13080:31;13075:3;13068:44;13050:3;13141:6;13135:13;13157:62;13212:6;13207:2;13202:3;13198:12;13191:4;13183:6;13179:17;13157:62;:::i;:::-;13239:16;;;;13257:2;13235:25;;13058:208;-1:-1:-1;;13058:208:1:o;13479:488::-;-1:-1:-1;;;;;13748:15:1;;;13730:34;;13800:15;;13795:2;13780:18;;13773:43;13847:2;13832:18;;13825:34;;;13895:3;13890:2;13875:18;;13868:31;;;13673:4;;13916:45;;13941:19;;13933:6;13916:45;:::i;14164:219::-;14313:2;14302:9;14295:21;14276:4;14333:44;14373:2;14362:9;14358:18;14350:6;14333:44;:::i;16908:128::-;16948:3;16979:1;16975:6;16972:1;16969:13;16966:2;;;16985:18;;:::i;:::-;-1:-1:-1;17021:9:1;;16956:80::o;17041:120::-;17081:1;17107;17097:2;;17112:18;;:::i;:::-;-1:-1:-1;17146:9:1;;17087:74::o;17166:168::-;17206:7;17272:1;17268;17264:6;17260:14;17257:1;17254:21;17249:1;17242:9;17235:17;17231:45;17228:2;;;17279:18;;:::i;:::-;-1:-1:-1;17319:9:1;;17218:116::o;17339:125::-;17379:4;17407:1;17404;17401:8;17398:2;;;17412:18;;:::i;:::-;-1:-1:-1;17449:9:1;;17388:76::o;17469:258::-;17541:1;17551:113;17565:6;17562:1;17559:13;17551:113;;;17641:11;;;17635:18;17622:11;;;17615:39;17587:2;17580:10;17551:113;;;17682:6;17679:1;17676:13;17673:2;;;-1:-1:-1;;17717:1:1;17699:16;;17692:27;17522:205::o;17732:380::-;17811:1;17807:12;;;;17854;;;17875:2;;17929:4;17921:6;17917:17;17907:27;;17875:2;17982;17974:6;17971:14;17951:18;17948:38;17945:2;;;18028:10;18023:3;18019:20;18016:1;18009:31;18063:4;18060:1;18053:15;18091:4;18088:1;18081:15;17945:2;;17787:325;;;:::o;18117:135::-;18156:3;-1:-1:-1;;18177:17:1;;18174:2;;;18197:18;;:::i;:::-;-1:-1:-1;18244:1:1;18233:13;;18164:88::o;18257:112::-;18289:1;18315;18305:2;;18320:18;;:::i;:::-;-1:-1:-1;18354:9:1;;18295:74::o;18374:127::-;18435:10;18430:3;18426:20;18423:1;18416:31;18466:4;18463:1;18456:15;18490:4;18487:1;18480:15;18506:127;18567:10;18562:3;18558:20;18555:1;18548:31;18598:4;18595:1;18588:15;18622:4;18619:1;18612:15;18638:127;18699:10;18694:3;18690:20;18687:1;18680:31;18730:4;18727:1;18720:15;18754:4;18751:1;18744:15;18770:131;-1:-1:-1;;;;;;18844:32:1;;18834:43;;18824:2;;18891:1;18888;18881:12
Swarm Source
ipfs://a254f1bf1132049008dc255143963394df7602cda125a662a32265ded41204f6
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 30 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|
Loading...
Loading
[ Download: CSV Export ]
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.