Overview
CRO Balance
0 CRO
CRO Value
$0.00More Info
Private Name Tags
ContractCreator
TokenTracker
Latest 25 from a total of 266 transactions
Transaction Hash |
Method
|
Block
|
From
|
To
|
|||||
---|---|---|---|---|---|---|---|---|---|
Set Approval For... | 16577533 | 39 days ago | IN | 0 CRO | 0.23607235 | ||||
Safe Transfer Fr... | 16577085 | 39 days ago | IN | 0 CRO | 0.970408 | ||||
Safe Transfer Fr... | 14242844 | 192 days ago | IN | 0 CRO | 0.3295731 | ||||
Safe Transfer Fr... | 14241866 | 192 days ago | IN | 0 CRO | 1.128776 | ||||
Set Approval For... | 13973390 | 209 days ago | IN | 0 CRO | 0.23607235 | ||||
Safe Transfer Fr... | 13748097 | 224 days ago | IN | 0 CRO | 0.9024754 | ||||
Transfer From | 13198638 | 260 days ago | IN | 0 CRO | 0.505 | ||||
Safe Transfer Fr... | 12805198 | 286 days ago | IN | 0 CRO | 0.6106662 | ||||
Transfer From | 12660325 | 295 days ago | IN | 0 CRO | 1.01 | ||||
Transfer From | 12660314 | 295 days ago | IN | 0 CRO | 1.01 | ||||
Transfer From | 12660096 | 295 days ago | IN | 0 CRO | 1.01 | ||||
Set Approval For... | 12170239 | 327 days ago | IN | 0 CRO | 0.4721447 | ||||
Safe Transfer Fr... | 12125902 | 330 days ago | IN | 0 CRO | 1.420464 | ||||
Transfer From | 12034972 | 336 days ago | IN | 0 CRO | 0.57664648 | ||||
Safe Transfer Fr... | 12013536 | 337 days ago | IN | 0 CRO | 3.9542308 | ||||
Safe Transfer Fr... | 11845525 | 348 days ago | IN | 0 CRO | 1.940816 | ||||
Safe Transfer Fr... | 11604429 | 364 days ago | IN | 0 CRO | 5.2952 | ||||
Transfer From | 11571825 | 366 days ago | IN | 0 CRO | 0.46021847 | ||||
Set Approval For... | 11464827 | 373 days ago | IN | 0 CRO | 0.21535815 | ||||
Safe Transfer Fr... | 11464675 | 373 days ago | IN | 0 CRO | 0.6584 | ||||
Safe Transfer Fr... | 11453288 | 374 days ago | IN | 0 CRO | 0.19978599 | ||||
Safe Transfer Fr... | 11453282 | 374 days ago | IN | 0 CRO | 0.22190152 | ||||
Safe Transfer Fr... | 11453276 | 374 days ago | IN | 0 CRO | 0.30068804 | ||||
Safe Transfer Fr... | 11453241 | 374 days ago | IN | 0 CRO | 1.1441 | ||||
Safe Transfer Fr... | 11453209 | 374 days ago | IN | 0 CRO | 0.6177 |
Loading...
Loading
Contract Name:
BasicERC721A
Compiler Version
v0.8.4+commit.c7e474f2
Contract Source Code (Solidity)
/** *Submitted for verification at cronoscan.com on 2022-11-21 */ // Sources flattened with hardhat v2.9.3 https://hardhat.org // File erc721a/contracts/[email protected] // SPDX-License-Identifier: MIT // ERC721A Contracts v4.2.2 // Creator: Chiru Labs pragma solidity ^0.8.4; /** * @dev Interface of ERC721A. */ interface IERC721A { /** * The caller must own the token or be an approved operator. */ error ApprovalCallerNotOwnerNorApproved(); /** * The token does not exist. */ error ApprovalQueryForNonexistentToken(); /** * The caller cannot approve to their own address. */ error ApproveToCaller(); /** * Cannot query the balance for the zero address. */ error BalanceQueryForZeroAddress(); /** * Cannot mint to the zero address. */ error MintToZeroAddress(); /** * The quantity of tokens minted must be more than zero. */ error MintZeroQuantity(); /** * The token does not exist. */ error OwnerQueryForNonexistentToken(); /** * The caller must own the token or be an approved operator. */ error TransferCallerNotOwnerNorApproved(); /** * The token must be owned by `from`. */ error TransferFromIncorrectOwner(); /** * Cannot safely transfer to a contract that does not implement the * ERC721Receiver interface. */ error TransferToNonERC721ReceiverImplementer(); /** * Cannot transfer to the zero address. */ error TransferToZeroAddress(); /** * The token does not exist. */ error URIQueryForNonexistentToken(); /** * The `quantity` minted with ERC2309 exceeds the safety limit. */ error MintERC2309QuantityExceedsLimit(); /** * The `extraData` cannot be set on an unintialized ownership slot. */ error OwnershipNotInitializedForExtraData(); // ============================================================= // STRUCTS // ============================================================= struct TokenOwnership { // The address of the owner. address addr; // Stores the start time of ownership with minimal overhead for tokenomics. uint64 startTimestamp; // Whether the token has been burned. bool burned; // Arbitrary data similar to `startTimestamp` that can be set via {_extraData}. uint24 extraData; } // ============================================================= // TOKEN COUNTERS // ============================================================= /** * @dev Returns the total number of tokens in existence. * Burned tokens will reduce the count. * To get the total number of tokens minted, please see {_totalMinted}. */ function totalSupply() external view returns (uint256); // ============================================================= // IERC165 // ============================================================= /** * @dev Returns true if this contract implements the interface defined by * `interfaceId`. See the corresponding * [EIP section](https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified) * to learn more about how these ids are created. * * This function call must use less than 30000 gas. */ function supportsInterface(bytes4 interfaceId) external view returns (bool); // ============================================================= // IERC721 // ============================================================= /** * @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, bytes calldata data ) external; /** * @dev Equivalent to `safeTransferFrom(from, to, tokenId, '')`. */ function safeTransferFrom( address from, address to, uint256 tokenId ) external; /** * @dev Transfers `tokenId` from `from` to `to`. * * WARNING: Usage of this method is discouraged, use {safeTransferFrom} * whenever possible. * * Requirements: * * - `from` cannot be the zero address. * - `to` cannot be the zero address. * - `tokenId` token must be owned by `from`. * - If the caller is not `from`, it must be approved to move this token * by either {approve} or {setApprovalForAll}. * * Emits a {Transfer} event. */ function transferFrom( address from, address to, uint256 tokenId ) external; /** * @dev Gives permission to `to` to transfer `tokenId` token to another account. * The approval is cleared when the token is transferred. * * Only a single account can be approved at a time, so approving the * zero address clears previous approvals. * * Requirements: * * - The caller must own the token or be an approved operator. * - `tokenId` must exist. * * Emits an {Approval} event. */ function approve(address to, uint256 tokenId) external; /** * @dev Approve or remove `operator` as an operator for the caller. * Operators can call {transferFrom} or {safeTransferFrom} * for any token owned by the caller. * * Requirements: * * - The `operator` cannot be the caller. * * Emits an {ApprovalForAll} event. */ function setApprovalForAll(address operator, bool _approved) external; /** * @dev Returns the account approved for `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function getApproved(uint256 tokenId) external view returns (address operator); /** * @dev Returns if the `operator` is allowed to manage all of the assets of `owner`. * * See {setApprovalForAll}. */ function isApprovedForAll(address owner, address operator) external view returns (bool); // ============================================================= // IERC721Metadata // ============================================================= /** * @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); // ============================================================= // IERC2309 // ============================================================= /** * @dev Emitted when tokens in `fromTokenId` to `toTokenId` * (inclusive) is transferred from `from` to `to`, as defined in the * [ERC2309](https://eips.ethereum.org/EIPS/eip-2309) standard. * * See {_mintERC2309} for more details. */ event ConsecutiveTransfer(uint256 indexed fromTokenId, uint256 toTokenId, address indexed from, address indexed to); } // File erc721a/contracts/[email protected] // ERC721A Contracts v4.2.2 // Creator: Chiru Labs pragma solidity ^0.8.4; /** * @dev Interface of ERC721 token receiver. */ interface ERC721A__IERC721Receiver { function onERC721Received( address operator, address from, uint256 tokenId, bytes calldata data ) external returns (bytes4); } /** * @title ERC721A * * @dev Implementation of the [ERC721](https://eips.ethereum.org/EIPS/eip-721) * Non-Fungible Token Standard, including the Metadata extension. * Optimized for lower gas during batch mints. * * Token IDs are minted in sequential order (e.g. 0, 1, 2, 3, ...) * starting from `_startTokenId()`. * * Assumptions: * * - An owner cannot have more than 2**64 - 1 (max value of uint64) of supply. * - The maximum token ID cannot exceed 2**256 - 1 (max value of uint256). */ contract ERC721A is IERC721A { // Reference type for token approval. struct TokenApprovalRef { address value; } // ============================================================= // CONSTANTS // ============================================================= // Mask of an entry in packed address data. uint256 private constant _BITMASK_ADDRESS_DATA_ENTRY = (1 << 64) - 1; // The bit position of `numberMinted` in packed address data. uint256 private constant _BITPOS_NUMBER_MINTED = 64; // The bit position of `numberBurned` in packed address data. uint256 private constant _BITPOS_NUMBER_BURNED = 128; // The bit position of `aux` in packed address data. uint256 private constant _BITPOS_AUX = 192; // Mask of all 256 bits in packed address data except the 64 bits for `aux`. uint256 private constant _BITMASK_AUX_COMPLEMENT = (1 << 192) - 1; // The bit position of `startTimestamp` in packed ownership. uint256 private constant _BITPOS_START_TIMESTAMP = 160; // The bit mask of the `burned` bit in packed ownership. uint256 private constant _BITMASK_BURNED = 1 << 224; // The bit position of the `nextInitialized` bit in packed ownership. uint256 private constant _BITPOS_NEXT_INITIALIZED = 225; // The bit mask of the `nextInitialized` bit in packed ownership. uint256 private constant _BITMASK_NEXT_INITIALIZED = 1 << 225; // The bit position of `extraData` in packed ownership. uint256 private constant _BITPOS_EXTRA_DATA = 232; // Mask of all 256 bits in a packed ownership except the 24 bits for `extraData`. uint256 private constant _BITMASK_EXTRA_DATA_COMPLEMENT = (1 << 232) - 1; // The mask of the lower 160 bits for addresses. uint256 private constant _BITMASK_ADDRESS = (1 << 160) - 1; // The maximum `quantity` that can be minted with {_mintERC2309}. // This limit is to prevent overflows on the address data entries. // For a limit of 5000, a total of 3.689e15 calls to {_mintERC2309} // is required to cause an overflow, which is unrealistic. uint256 private constant _MAX_MINT_ERC2309_QUANTITY_LIMIT = 5000; // The `Transfer` event signature is given by: // `keccak256(bytes("Transfer(address,address,uint256)"))`. bytes32 private constant _TRANSFER_EVENT_SIGNATURE = 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef; // ============================================================= // STORAGE // ============================================================= // The next token ID to be minted. uint256 private _currentIndex; // The number of tokens burned. uint256 private _burnCounter; // Token name string private _name; // Token symbol string private _symbol; // Mapping from token ID to ownership details // An empty struct value does not necessarily mean the token is unowned. // See {_packedOwnershipOf} implementation for details. // // Bits Layout: // - [0..159] `addr` // - [160..223] `startTimestamp` // - [224] `burned` // - [225] `nextInitialized` // - [232..255] `extraData` mapping(uint256 => uint256) private _packedOwnerships; // Mapping owner address to address data. // // Bits Layout: // - [0..63] `balance` // - [64..127] `numberMinted` // - [128..191] `numberBurned` // - [192..255] `aux` mapping(address => uint256) private _packedAddressData; // Mapping from token ID to approved address. mapping(uint256 => TokenApprovalRef) private _tokenApprovals; // Mapping from owner to operator approvals mapping(address => mapping(address => bool)) private _operatorApprovals; // ============================================================= // CONSTRUCTOR // ============================================================= constructor(string memory name_, string memory symbol_) { _name = name_; _symbol = symbol_; _currentIndex = _startTokenId(); } // ============================================================= // TOKEN COUNTING OPERATIONS // ============================================================= /** * @dev Returns the starting token ID. * To change the starting token ID, please override this function. */ function _startTokenId() internal view virtual returns (uint256) { return 0; } /** * @dev Returns the next token ID to be minted. */ function _nextTokenId() internal view virtual returns (uint256) { return _currentIndex; } /** * @dev Returns the total number of tokens in existence. * Burned tokens will reduce the count. * To get the total number of tokens minted, please see {_totalMinted}. */ function totalSupply() public view virtual override returns (uint256) { // Counter underflow is impossible as _burnCounter cannot be incremented // more than `_currentIndex - _startTokenId()` times. unchecked { return _currentIndex - _burnCounter - _startTokenId(); } } /** * @dev Returns the total amount of tokens minted in the contract. */ function _totalMinted() internal view virtual returns (uint256) { // Counter underflow is impossible as `_currentIndex` does not decrement, // and it is initialized to `_startTokenId()`. unchecked { return _currentIndex - _startTokenId(); } } /** * @dev Returns the total number of tokens burned. */ function _totalBurned() internal view virtual returns (uint256) { return _burnCounter; } // ============================================================= // ADDRESS DATA OPERATIONS // ============================================================= /** * @dev Returns the number of tokens in `owner`'s account. */ function balanceOf(address owner) public view virtual override returns (uint256) { if (owner == address(0)) revert BalanceQueryForZeroAddress(); return _packedAddressData[owner] & _BITMASK_ADDRESS_DATA_ENTRY; } /** * Returns the number of tokens minted by `owner`. */ function _numberMinted(address owner) internal view returns (uint256) { return (_packedAddressData[owner] >> _BITPOS_NUMBER_MINTED) & _BITMASK_ADDRESS_DATA_ENTRY; } /** * Returns the number of tokens burned by or on behalf of `owner`. */ function _numberBurned(address owner) internal view returns (uint256) { return (_packedAddressData[owner] >> _BITPOS_NUMBER_BURNED) & _BITMASK_ADDRESS_DATA_ENTRY; } /** * Returns the auxiliary data for `owner`. (e.g. number of whitelist mint slots used). */ function _getAux(address owner) internal view returns (uint64) { return uint64(_packedAddressData[owner] >> _BITPOS_AUX); } /** * Sets the auxiliary 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 virtual { uint256 packed = _packedAddressData[owner]; uint256 auxCasted; // Cast `aux` with assembly to avoid redundant masking. assembly { auxCasted := aux } packed = (packed & _BITMASK_AUX_COMPLEMENT) | (auxCasted << _BITPOS_AUX); _packedAddressData[owner] = packed; } // ============================================================= // IERC165 // ============================================================= /** * @dev Returns true if this contract implements the interface defined by * `interfaceId`. See the corresponding * [EIP section](https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified) * to learn more about how these ids are created. * * This function call must use less than 30000 gas. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { // The interface IDs are constants representing the first 4 bytes // of the XOR of all function selectors in the interface. // See: [ERC165](https://eips.ethereum.org/EIPS/eip-165) // (e.g. `bytes4(i.functionA.selector ^ i.functionB.selector ^ ...)`) return interfaceId == 0x01ffc9a7 || // ERC165 interface ID for ERC165. interfaceId == 0x80ac58cd || // ERC165 interface ID for ERC721. interfaceId == 0x5b5e139f; // ERC165 interface ID for ERC721Metadata. } // ============================================================= // IERC721Metadata // ============================================================= /** * @dev Returns the token collection name. */ function name() public view virtual override returns (string memory) { return _name; } /** * @dev Returns the token collection symbol. */ function symbol() public view virtual override returns (string memory) { return _symbol; } /** * @dev Returns the Uniform Resource Identifier (URI) for `tokenId` token. */ function tokenURI(uint256 tokenId) public view virtual override returns (string memory) { if (!_exists(tokenId)) revert URIQueryForNonexistentToken(); string memory baseURI = _baseURI(); return bytes(baseURI).length != 0 ? string(abi.encodePacked(baseURI, _toString(tokenId))) : ''; } /** * @dev Base URI for computing {tokenURI}. If set, the resulting URI for each * token will be the concatenation of the `baseURI` and the `tokenId`. Empty * by default, it can be overridden in child contracts. */ function _baseURI() internal view virtual returns (string memory) { return ''; } // ============================================================= // OWNERSHIPS OPERATIONS // ============================================================= /** * @dev Returns the owner of the `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function ownerOf(uint256 tokenId) public view virtual override returns (address) { return address(uint160(_packedOwnershipOf(tokenId))); } /** * @dev Gas spent here starts off proportional to the maximum mint batch size. * It gradually moves to O(1) as tokens get transferred around over time. */ function _ownershipOf(uint256 tokenId) internal view virtual returns (TokenOwnership memory) { return _unpackedOwnership(_packedOwnershipOf(tokenId)); } /** * @dev Returns the unpacked `TokenOwnership` struct at `index`. */ function _ownershipAt(uint256 index) internal view virtual returns (TokenOwnership memory) { return _unpackedOwnership(_packedOwnerships[index]); } /** * @dev Initializes the ownership slot minted at `index` for efficiency purposes. */ function _initializeOwnershipAt(uint256 index) internal virtual { if (_packedOwnerships[index] == 0) { _packedOwnerships[index] = _packedOwnershipOf(index); } } /** * Returns the packed ownership data of `tokenId`. */ function _packedOwnershipOf(uint256 tokenId) private view returns (uint256) { uint256 curr = tokenId; unchecked { if (_startTokenId() <= curr) if (curr < _currentIndex) { uint256 packed = _packedOwnerships[curr]; // If not burned. if (packed & _BITMASK_BURNED == 0) { // Invariant: // There will always be an initialized ownership slot // (i.e. `ownership.addr != address(0) && ownership.burned == false`) // before an unintialized ownership slot // (i.e. `ownership.addr == address(0) && ownership.burned == false`) // Hence, `curr` will not underflow. // // We can directly compare the packed value. // If the address is zero, packed will be zero. while (packed == 0) { packed = _packedOwnerships[--curr]; } return packed; } } } revert OwnerQueryForNonexistentToken(); } /** * @dev Returns the unpacked `TokenOwnership` struct from `packed`. */ function _unpackedOwnership(uint256 packed) private pure returns (TokenOwnership memory ownership) { ownership.addr = address(uint160(packed)); ownership.startTimestamp = uint64(packed >> _BITPOS_START_TIMESTAMP); ownership.burned = packed & _BITMASK_BURNED != 0; ownership.extraData = uint24(packed >> _BITPOS_EXTRA_DATA); } /** * @dev Packs ownership data into a single uint256. */ function _packOwnershipData(address owner, uint256 flags) private view returns (uint256 result) { assembly { // Mask `owner` to the lower 160 bits, in case the upper bits somehow aren't clean. owner := and(owner, _BITMASK_ADDRESS) // `owner | (block.timestamp << _BITPOS_START_TIMESTAMP) | flags`. result := or(owner, or(shl(_BITPOS_START_TIMESTAMP, timestamp()), flags)) } } /** * @dev Returns the `nextInitialized` flag set if `quantity` equals 1. */ function _nextInitializedFlag(uint256 quantity) private pure returns (uint256 result) { // For branchless setting of the `nextInitialized` flag. assembly { // `(quantity == 1) << _BITPOS_NEXT_INITIALIZED`. result := shl(_BITPOS_NEXT_INITIALIZED, eq(quantity, 1)) } } // ============================================================= // APPROVAL OPERATIONS // ============================================================= /** * @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) public virtual override { address owner = ownerOf(tokenId); if (_msgSenderERC721A() != owner) if (!isApprovedForAll(owner, _msgSenderERC721A())) { revert ApprovalCallerNotOwnerNorApproved(); } _tokenApprovals[tokenId].value = to; emit Approval(owner, to, tokenId); } /** * @dev Returns the account approved for `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function getApproved(uint256 tokenId) public view virtual override returns (address) { if (!_exists(tokenId)) revert ApprovalQueryForNonexistentToken(); return _tokenApprovals[tokenId].value; } /** * @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) public virtual override { if (operator == _msgSenderERC721A()) revert ApproveToCaller(); _operatorApprovals[_msgSenderERC721A()][operator] = approved; emit ApprovalForAll(_msgSenderERC721A(), operator, approved); } /** * @dev Returns if the `operator` is allowed to manage all of the assets of `owner`. * * See {setApprovalForAll}. */ function isApprovedForAll(address owner, address operator) public view virtual override returns (bool) { return _operatorApprovals[owner][operator]; } /** * @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. See {_mint}. */ function _exists(uint256 tokenId) internal view virtual returns (bool) { return _startTokenId() <= tokenId && tokenId < _currentIndex && // If within bounds, _packedOwnerships[tokenId] & _BITMASK_BURNED == 0; // and not burned. } /** * @dev Returns whether `msgSender` is equal to `approvedAddress` or `owner`. */ function _isSenderApprovedOrOwner( address approvedAddress, address owner, address msgSender ) private pure returns (bool result) { assembly { // Mask `owner` to the lower 160 bits, in case the upper bits somehow aren't clean. owner := and(owner, _BITMASK_ADDRESS) // Mask `msgSender` to the lower 160 bits, in case the upper bits somehow aren't clean. msgSender := and(msgSender, _BITMASK_ADDRESS) // `msgSender == owner || msgSender == approvedAddress`. result := or(eq(msgSender, owner), eq(msgSender, approvedAddress)) } } /** * @dev Returns the storage slot and value for the approved address of `tokenId`. */ function _getApprovedSlotAndAddress(uint256 tokenId) private view returns (uint256 approvedAddressSlot, address approvedAddress) { TokenApprovalRef storage tokenApproval = _tokenApprovals[tokenId]; // The following is equivalent to `approvedAddress = _tokenApprovals[tokenId]`. assembly { approvedAddressSlot := tokenApproval.slot approvedAddress := sload(approvedAddressSlot) } } // ============================================================= // TRANSFER OPERATIONS // ============================================================= /** * @dev Transfers `tokenId` from `from` to `to`. * * 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 ) public virtual override { uint256 prevOwnershipPacked = _packedOwnershipOf(tokenId); if (address(uint160(prevOwnershipPacked)) != from) revert TransferFromIncorrectOwner(); (uint256 approvedAddressSlot, address approvedAddress) = _getApprovedSlotAndAddress(tokenId); // The nested ifs save around 20+ gas over a compound boolean condition. if (!_isSenderApprovedOrOwner(approvedAddress, from, _msgSenderERC721A())) if (!isApprovedForAll(from, _msgSenderERC721A())) revert TransferCallerNotOwnerNorApproved(); if (to == address(0)) revert TransferToZeroAddress(); _beforeTokenTransfers(from, to, tokenId, 1); // Clear approvals from the previous owner. assembly { if approvedAddress { // This is equivalent to `delete _tokenApprovals[tokenId]`. sstore(approvedAddressSlot, 0) } } // 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 { // We can directly increment and decrement the balances. --_packedAddressData[from]; // Updates: `balance -= 1`. ++_packedAddressData[to]; // Updates: `balance += 1`. // Updates: // - `address` to the next owner. // - `startTimestamp` to the timestamp of transfering. // - `burned` to `false`. // - `nextInitialized` to `true`. _packedOwnerships[tokenId] = _packOwnershipData( to, _BITMASK_NEXT_INITIALIZED | _nextExtraData(from, to, prevOwnershipPacked) ); // If the next slot may not have been initialized (i.e. `nextInitialized == false`) . if (prevOwnershipPacked & _BITMASK_NEXT_INITIALIZED == 0) { uint256 nextTokenId = tokenId + 1; // If the next slot's address is zero and not burned (i.e. packed value is zero). if (_packedOwnerships[nextTokenId] == 0) { // If the next slot is within bounds. if (nextTokenId != _currentIndex) { // Initialize the next slot to maintain correctness for `ownerOf(tokenId + 1)`. _packedOwnerships[nextTokenId] = prevOwnershipPacked; } } } } emit Transfer(from, to, tokenId); _afterTokenTransfers(from, to, tokenId, 1); } /** * @dev Equivalent to `safeTransferFrom(from, to, tokenId, '')`. */ function safeTransferFrom( address from, address to, uint256 tokenId ) public virtual override { safeTransferFrom(from, to, tokenId, ''); } /** * @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 memory _data ) public virtual override { transferFrom(from, to, tokenId); if (to.code.length != 0) if (!_checkContractOnERC721Received(from, to, tokenId, _data)) { revert TransferToNonERC721ReceiverImplementer(); } } /** * @dev Hook that is called before a set of serially-ordered token IDs * are about to be transferred. This includes minting. * And also called before burning one token. * * `startTokenId` - the first token ID to be transferred. * `quantity` - the amount to be transferred. * * Calling conditions: * * - When `from` and `to` are both non-zero, `from`'s `tokenId` will be * transferred to `to`. * - When `from` is zero, `tokenId` will be minted for `to`. * - When `to` is zero, `tokenId` will be burned by `from`. * - `from` and `to` are never both zero. */ function _beforeTokenTransfers( address from, address to, uint256 startTokenId, uint256 quantity ) internal virtual {} /** * @dev Hook that is called after a set of serially-ordered token IDs * have been transferred. This includes minting. * And also called after one token has been burned. * * `startTokenId` - the first token ID to be transferred. * `quantity` - the amount to be transferred. * * Calling conditions: * * - When `from` and `to` are both non-zero, `from`'s `tokenId` has been * transferred to `to`. * - When `from` is zero, `tokenId` has been minted for `to`. * - When `to` is zero, `tokenId` has been burned by `from`. * - `from` and `to` are never both zero. */ function _afterTokenTransfers( address from, address to, uint256 startTokenId, uint256 quantity ) internal virtual {} /** * @dev Private function to invoke {IERC721Receiver-onERC721Received} on a target contract. * * `from` - Previous owner of the given token ID. * `to` - Target address that will receive the token. * `tokenId` - Token ID to be transferred. * `_data` - Optional data to send along with the call. * * Returns whether the call correctly returned the expected magic value. */ function _checkContractOnERC721Received( address from, address to, uint256 tokenId, bytes memory _data ) private returns (bool) { try ERC721A__IERC721Receiver(to).onERC721Received(_msgSenderERC721A(), from, tokenId, _data) returns ( bytes4 retval ) { return retval == ERC721A__IERC721Receiver(to).onERC721Received.selector; } catch (bytes memory reason) { if (reason.length == 0) { revert TransferToNonERC721ReceiverImplementer(); } else { assembly { revert(add(32, reason), mload(reason)) } } } } // ============================================================= // MINT OPERATIONS // ============================================================= /** * @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 for each mint. */ function _mint(address to, uint256 quantity) internal virtual { uint256 startTokenId = _currentIndex; if (quantity == 0) revert MintZeroQuantity(); _beforeTokenTransfers(address(0), to, startTokenId, quantity); // Overflows are incredibly unrealistic. // `balance` and `numberMinted` have a maximum limit of 2**64. // `tokenId` has a maximum limit of 2**256. unchecked { // Updates: // - `balance += quantity`. // - `numberMinted += quantity`. // // We can directly add to the `balance` and `numberMinted`. _packedAddressData[to] += quantity * ((1 << _BITPOS_NUMBER_MINTED) | 1); // Updates: // - `address` to the owner. // - `startTimestamp` to the timestamp of minting. // - `burned` to `false`. // - `nextInitialized` to `quantity == 1`. _packedOwnerships[startTokenId] = _packOwnershipData( to, _nextInitializedFlag(quantity) | _nextExtraData(address(0), to, 0) ); uint256 toMasked; uint256 end = startTokenId + quantity; // Use assembly to loop and emit the `Transfer` event for gas savings. assembly { // Mask `to` to the lower 160 bits, in case the upper bits somehow aren't clean. toMasked := and(to, _BITMASK_ADDRESS) // Emit the `Transfer` event. log4( 0, // Start of data (0, since no data). 0, // End of data (0, since no data). _TRANSFER_EVENT_SIGNATURE, // Signature. 0, // `address(0)`. toMasked, // `to`. startTokenId // `tokenId`. ) for { let tokenId := add(startTokenId, 1) } iszero(eq(tokenId, end)) { tokenId := add(tokenId, 1) } { // Emit the `Transfer` event. Similar to above. log4(0, 0, _TRANSFER_EVENT_SIGNATURE, 0, toMasked, tokenId) } } if (toMasked == 0) revert MintToZeroAddress(); _currentIndex = end; } _afterTokenTransfers(address(0), to, startTokenId, quantity); } /** * @dev Mints `quantity` tokens and transfers them to `to`. * * This function is intended for efficient minting only during contract creation. * * It emits only one {ConsecutiveTransfer} as defined in * [ERC2309](https://eips.ethereum.org/EIPS/eip-2309), * instead of a sequence of {Transfer} event(s). * * Calling this function outside of contract creation WILL make your contract * non-compliant with the ERC721 standard. * For full ERC721 compliance, substituting ERC721 {Transfer} event(s) with the ERC2309 * {ConsecutiveTransfer} event is only permissible during contract creation. * * Requirements: * * - `to` cannot be the zero address. * - `quantity` must be greater than 0. * * Emits a {ConsecutiveTransfer} event. */ function _mintERC2309(address to, uint256 quantity) internal virtual { uint256 startTokenId = _currentIndex; if (to == address(0)) revert MintToZeroAddress(); if (quantity == 0) revert MintZeroQuantity(); if (quantity > _MAX_MINT_ERC2309_QUANTITY_LIMIT) revert MintERC2309QuantityExceedsLimit(); _beforeTokenTransfers(address(0), to, startTokenId, quantity); // Overflows are unrealistic due to the above check for `quantity` to be below the limit. unchecked { // Updates: // - `balance += quantity`. // - `numberMinted += quantity`. // // We can directly add to the `balance` and `numberMinted`. _packedAddressData[to] += quantity * ((1 << _BITPOS_NUMBER_MINTED) | 1); // Updates: // - `address` to the owner. // - `startTimestamp` to the timestamp of minting. // - `burned` to `false`. // - `nextInitialized` to `quantity == 1`. _packedOwnerships[startTokenId] = _packOwnershipData( to, _nextInitializedFlag(quantity) | _nextExtraData(address(0), to, 0) ); emit ConsecutiveTransfer(startTokenId, startTokenId + quantity - 1, address(0), to); _currentIndex = startTokenId + quantity; } _afterTokenTransfers(address(0), to, startTokenId, 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. * * See {_mint}. * * Emits a {Transfer} event for each mint. */ function _safeMint( address to, uint256 quantity, bytes memory _data ) internal virtual { _mint(to, quantity); unchecked { if (to.code.length != 0) { uint256 end = _currentIndex; uint256 index = end - quantity; do { if (!_checkContractOnERC721Received(address(0), to, index++, _data)) { revert TransferToNonERC721ReceiverImplementer(); } } while (index < end); // Reentrancy protection. if (_currentIndex != end) revert(); } } } /** * @dev Equivalent to `_safeMint(to, quantity, '')`. */ function _safeMint(address to, uint256 quantity) internal virtual { _safeMint(to, quantity, ''); } // ============================================================= // BURN OPERATIONS // ============================================================= /** * @dev Equivalent to `_burn(tokenId, false)`. */ function _burn(uint256 tokenId) internal virtual { _burn(tokenId, false); } /** * @dev Destroys `tokenId`. * The approval is cleared when the token is burned. * * Requirements: * * - `tokenId` must exist. * * Emits a {Transfer} event. */ function _burn(uint256 tokenId, bool approvalCheck) internal virtual { uint256 prevOwnershipPacked = _packedOwnershipOf(tokenId); address from = address(uint160(prevOwnershipPacked)); (uint256 approvedAddressSlot, address approvedAddress) = _getApprovedSlotAndAddress(tokenId); if (approvalCheck) { // The nested ifs save around 20+ gas over a compound boolean condition. if (!_isSenderApprovedOrOwner(approvedAddress, from, _msgSenderERC721A())) if (!isApprovedForAll(from, _msgSenderERC721A())) revert TransferCallerNotOwnerNorApproved(); } _beforeTokenTransfers(from, address(0), tokenId, 1); // Clear approvals from the previous owner. assembly { if approvedAddress { // This is equivalent to `delete _tokenApprovals[tokenId]`. sstore(approvedAddressSlot, 0) } } // 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 { // Updates: // - `balance -= 1`. // - `numberBurned += 1`. // // We can directly decrement the balance, and increment the number burned. // This is equivalent to `packed -= 1; packed += 1 << _BITPOS_NUMBER_BURNED;`. _packedAddressData[from] += (1 << _BITPOS_NUMBER_BURNED) - 1; // Updates: // - `address` to the last owner. // - `startTimestamp` to the timestamp of burning. // - `burned` to `true`. // - `nextInitialized` to `true`. _packedOwnerships[tokenId] = _packOwnershipData( from, (_BITMASK_BURNED | _BITMASK_NEXT_INITIALIZED) | _nextExtraData(from, address(0), prevOwnershipPacked) ); // If the next slot may not have been initialized (i.e. `nextInitialized == false`) . if (prevOwnershipPacked & _BITMASK_NEXT_INITIALIZED == 0) { uint256 nextTokenId = tokenId + 1; // If the next slot's address is zero and not burned (i.e. packed value is zero). if (_packedOwnerships[nextTokenId] == 0) { // If the next slot is within bounds. if (nextTokenId != _currentIndex) { // Initialize the next slot to maintain correctness for `ownerOf(tokenId + 1)`. _packedOwnerships[nextTokenId] = prevOwnershipPacked; } } } } emit Transfer(from, address(0), tokenId); _afterTokenTransfers(from, address(0), tokenId, 1); // Overflow not possible, as _burnCounter cannot be exceed _currentIndex times. unchecked { _burnCounter++; } } // ============================================================= // EXTRA DATA OPERATIONS // ============================================================= /** * @dev Directly sets the extra data for the ownership data `index`. */ function _setExtraDataAt(uint256 index, uint24 extraData) internal virtual { uint256 packed = _packedOwnerships[index]; if (packed == 0) revert OwnershipNotInitializedForExtraData(); uint256 extraDataCasted; // Cast `extraData` with assembly to avoid redundant masking. assembly { extraDataCasted := extraData } packed = (packed & _BITMASK_EXTRA_DATA_COMPLEMENT) | (extraDataCasted << _BITPOS_EXTRA_DATA); _packedOwnerships[index] = packed; } /** * @dev Called during each token transfer to set the 24bit `extraData` field. * Intended to be overridden by the cosumer contract. * * `previousExtraData` - the value of `extraData` before transfer. * * 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 _extraData( address from, address to, uint24 previousExtraData ) internal view virtual returns (uint24) {} /** * @dev Returns the next extra data for the packed ownership data. * The returned result is shifted into position. */ function _nextExtraData( address from, address to, uint256 prevOwnershipPacked ) private view returns (uint256) { uint24 extraData = uint24(prevOwnershipPacked >> _BITPOS_EXTRA_DATA); return uint256(_extraData(from, to, extraData)) << _BITPOS_EXTRA_DATA; } // ============================================================= // OTHER OPERATIONS // ============================================================= /** * @dev Returns the message sender (defaults to `msg.sender`). * * If you are writing GSN compatible contracts, you need to override this function. */ function _msgSenderERC721A() internal view virtual returns (address) { return msg.sender; } /** * @dev Converts a uint256 to its ASCII string decimal representation. */ function _toString(uint256 value) internal pure virtual returns (string memory str) { assembly { // The maximum value of a uint256 contains 78 digits (1 byte per digit), // but we allocate 0x80 bytes to keep the free memory pointer 32-byte word aliged. // We will need 1 32-byte word to store the length, // and 3 32-byte words to store a maximum of 78 digits. Total: 0x20 + 3 * 0x20 = 0x80. str := add(mload(0x40), 0x80) // Update the free memory pointer to allocate. mstore(0x40, str) // Cache the end of the memory to calculate the length later. let end := str // We write the string from rightmost digit to leftmost digit. // The following is essentially a do-while loop that also handles the zero case. // prettier-ignore for { let temp := value } 1 {} { str := sub(str, 1) // Write the character to the pointer. // The ASCII index of the '0' character is 48. mstore8(str, add(48, mod(temp, 10))) // Keep dividing `temp` until zero. temp := div(temp, 10) // prettier-ignore if iszero(temp) { break } } let length := sub(end, str) // Move the pointer 32 bytes leftwards to make room for the length. str := sub(str, 0x20) // Store the length. mstore(str, length) } } } // File @openzeppelin/contracts/utils/introspection/[email protected] // OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol) pragma solidity ^0.8.0; /** * @dev Interface of the ERC165 standard, as defined in the * https://eips.ethereum.org/EIPS/eip-165[EIP]. * * Implementers can declare support of contract interfaces, which can then be * queried by others ({ERC165Checker}). * * For an implementation, see {ERC165}. */ interface IERC165 { /** * @dev Returns true if this contract implements the interface defined by * `interfaceId`. See the corresponding * https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section] * to learn more about how these ids are created. * * This function call must use less than 30 000 gas. */ function supportsInterface(bytes4 interfaceId) external view returns (bool); } // File @openzeppelin/contracts/utils/introspection/[email protected] // OpenZeppelin Contracts v4.4.1 (utils/introspection/ERC165.sol) pragma solidity ^0.8.0; /** * @dev Implementation of the {IERC165} interface. * * Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check * for the additional interface id that will be supported. For example: * * ```solidity * function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { * return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId); * } * ``` * * Alternatively, {ERC165Storage} provides an easier to use but more expensive implementation. */ abstract contract ERC165 is IERC165 { /** * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return interfaceId == type(IERC165).interfaceId; } } // File @openzeppelin/contracts/access/[email protected] // OpenZeppelin Contracts v4.4.1 (access/IAccessControl.sol) pragma solidity ^0.8.0; /** * @dev External interface of AccessControl declared to support ERC165 detection. */ interface IAccessControl { /** * @dev Emitted when `newAdminRole` is set as ``role``'s admin role, replacing `previousAdminRole` * * `DEFAULT_ADMIN_ROLE` is the starting admin for all roles, despite * {RoleAdminChanged} not being emitted signaling this. * * _Available since v3.1._ */ event RoleAdminChanged(bytes32 indexed role, bytes32 indexed previousAdminRole, bytes32 indexed newAdminRole); /** * @dev Emitted when `account` is granted `role`. * * `sender` is the account that originated the contract call, an admin role * bearer except when using {AccessControl-_setupRole}. */ event RoleGranted(bytes32 indexed role, address indexed account, address indexed sender); /** * @dev Emitted when `account` is revoked `role`. * * `sender` is the account that originated the contract call: * - if using `revokeRole`, it is the admin role bearer * - if using `renounceRole`, it is the role bearer (i.e. `account`) */ event RoleRevoked(bytes32 indexed role, address indexed account, address indexed sender); /** * @dev Returns `true` if `account` has been granted `role`. */ function hasRole(bytes32 role, address account) external view returns (bool); /** * @dev Returns the admin role that controls `role`. See {grantRole} and * {revokeRole}. * * To change a role's admin, use {AccessControl-_setRoleAdmin}. */ function getRoleAdmin(bytes32 role) external view returns (bytes32); /** * @dev Grants `role` to `account`. * * If `account` had not been already granted `role`, emits a {RoleGranted} * event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function grantRole(bytes32 role, address account) external; /** * @dev Revokes `role` from `account`. * * If `account` had been granted `role`, emits a {RoleRevoked} event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function revokeRole(bytes32 role, address account) external; /** * @dev Revokes `role` from the calling account. * * Roles are often managed via {grantRole} and {revokeRole}: this function's * purpose is to provide a mechanism for accounts to lose their privileges * if they are compromised (such as when a trusted device is misplaced). * * If the calling account had been granted `role`, emits a {RoleRevoked} * event. * * Requirements: * * - the caller must be `account`. */ function renounceRole(bytes32 role, address account) external; } // File @openzeppelin/contracts/access/[email protected] // OpenZeppelin Contracts v4.4.1 (access/IAccessControlEnumerable.sol) pragma solidity ^0.8.0; /** * @dev External interface of AccessControlEnumerable declared to support ERC165 detection. */ interface IAccessControlEnumerable is IAccessControl { /** * @dev Returns one of the accounts that have `role`. `index` must be a * value between 0 and {getRoleMemberCount}, non-inclusive. * * Role bearers are not sorted in any particular way, and their ordering may * change at any point. * * WARNING: When using {getRoleMember} and {getRoleMemberCount}, make sure * you perform all queries on the same block. See the following * https://forum.openzeppelin.com/t/iterating-over-elements-on-enumerableset-in-openzeppelin-contracts/2296[forum post] * for more information. */ function getRoleMember(bytes32 role, uint256 index) external view returns (address); /** * @dev Returns the number of accounts that have `role`. Can be used * together with {getRoleMember} to enumerate all bearers of a role. */ function getRoleMemberCount(bytes32 role) external view returns (uint256); } // File @openzeppelin/contracts/utils/[email protected] // OpenZeppelin Contracts v4.4.1 (utils/Context.sol) pragma solidity ^0.8.0; /** * @dev Provides information about the current execution context, including the * sender of the transaction and its data. While these are generally available * via msg.sender and msg.data, they should not be accessed in such a direct * manner, since when dealing with meta-transactions the account sending and * paying for execution may not be the actual sender (as far as an application * is concerned). * * This contract is only required for intermediate, library-like contracts. */ abstract contract Context { function _msgSender() internal view virtual returns (address) { return msg.sender; } function _msgData() internal view virtual returns (bytes calldata) { return msg.data; } } // File @openzeppelin/contracts/utils/[email protected] // OpenZeppelin Contracts v4.4.1 (utils/Strings.sol) pragma solidity ^0.8.0; /** * @dev String operations. */ library Strings { bytes16 private constant _HEX_SYMBOLS = "0123456789abcdef"; /** * @dev Converts a `uint256` to its ASCII `string` decimal representation. */ function toString(uint256 value) internal pure returns (string memory) { // Inspired by OraclizeAPI's implementation - MIT licence // https://github.com/oraclize/ethereum-api/blob/b42146b063c7d6ee1358846c198246239e9360e8/oraclizeAPI_0.4.25.sol if (value == 0) { return "0"; } uint256 temp = value; uint256 digits; while (temp != 0) { digits++; temp /= 10; } bytes memory buffer = new bytes(digits); while (value != 0) { digits -= 1; buffer[digits] = bytes1(uint8(48 + uint256(value % 10))); value /= 10; } return string(buffer); } /** * @dev Converts a `uint256` to its ASCII `string` hexadecimal representation. */ function toHexString(uint256 value) internal pure returns (string memory) { if (value == 0) { return "0x00"; } uint256 temp = value; uint256 length = 0; while (temp != 0) { length++; temp >>= 8; } return toHexString(value, length); } /** * @dev Converts a `uint256` to its ASCII `string` hexadecimal representation with fixed length. */ function toHexString(uint256 value, uint256 length) internal pure returns (string memory) { bytes memory buffer = new bytes(2 * length + 2); buffer[0] = "0"; buffer[1] = "x"; for (uint256 i = 2 * length + 1; i > 1; --i) { buffer[i] = _HEX_SYMBOLS[value & 0xf]; value >>= 4; } require(value == 0, "Strings: hex length insufficient"); return string(buffer); } } // File @openzeppelin/contracts/access/[email protected] // OpenZeppelin Contracts (last updated v4.5.0) (access/AccessControl.sol) pragma solidity ^0.8.0; /** * @dev Contract module that allows children to implement role-based access * control mechanisms. This is a lightweight version that doesn't allow enumerating role * members except through off-chain means by accessing the contract event logs. Some * applications may benefit from on-chain enumerability, for those cases see * {AccessControlEnumerable}. * * Roles are referred to by their `bytes32` identifier. These should be exposed * in the external API and be unique. The best way to achieve this is by * using `public constant` hash digests: * * ``` * bytes32 public constant MY_ROLE = keccak256("MY_ROLE"); * ``` * * Roles can be used to represent a set of permissions. To restrict access to a * function call, use {hasRole}: * * ``` * function foo() public { * require(hasRole(MY_ROLE, msg.sender)); * ... * } * ``` * * Roles can be granted and revoked dynamically via the {grantRole} and * {revokeRole} functions. Each role has an associated admin role, and only * accounts that have a role's admin role can call {grantRole} and {revokeRole}. * * By default, the admin role for all roles is `DEFAULT_ADMIN_ROLE`, which means * that only accounts with this role will be able to grant or revoke other * roles. More complex role relationships can be created by using * {_setRoleAdmin}. * * WARNING: The `DEFAULT_ADMIN_ROLE` is also its own admin: it has permission to * grant and revoke this role. Extra precautions should be taken to secure * accounts that have been granted it. */ abstract contract AccessControl is Context, IAccessControl, ERC165 { struct RoleData { mapping(address => bool) members; bytes32 adminRole; } mapping(bytes32 => RoleData) private _roles; bytes32 public constant DEFAULT_ADMIN_ROLE = 0x00; /** * @dev Modifier that checks that an account has a specific role. Reverts * with a standardized message including the required role. * * The format of the revert reason is given by the following regular expression: * * /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/ * * _Available since v4.1._ */ modifier onlyRole(bytes32 role) { _checkRole(role, _msgSender()); _; } /** * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return interfaceId == type(IAccessControl).interfaceId || super.supportsInterface(interfaceId); } /** * @dev Returns `true` if `account` has been granted `role`. */ function hasRole(bytes32 role, address account) public view virtual override returns (bool) { return _roles[role].members[account]; } /** * @dev Revert with a standard message if `account` is missing `role`. * * The format of the revert reason is given by the following regular expression: * * /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/ */ function _checkRole(bytes32 role, address account) internal view virtual { if (!hasRole(role, account)) { revert( string( abi.encodePacked( "AccessControl: account ", Strings.toHexString(uint160(account), 20), " is missing role ", Strings.toHexString(uint256(role), 32) ) ) ); } } /** * @dev Returns the admin role that controls `role`. See {grantRole} and * {revokeRole}. * * To change a role's admin, use {_setRoleAdmin}. */ function getRoleAdmin(bytes32 role) public view virtual override returns (bytes32) { return _roles[role].adminRole; } /** * @dev Grants `role` to `account`. * * If `account` had not been already granted `role`, emits a {RoleGranted} * event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function grantRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) { _grantRole(role, account); } /** * @dev Revokes `role` from `account`. * * If `account` had been granted `role`, emits a {RoleRevoked} event. * * Requirements: * * - the caller must have ``role``'s admin role. */ function revokeRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) { _revokeRole(role, account); } /** * @dev Revokes `role` from the calling account. * * Roles are often managed via {grantRole} and {revokeRole}: this function's * purpose is to provide a mechanism for accounts to lose their privileges * if they are compromised (such as when a trusted device is misplaced). * * If the calling account had been revoked `role`, emits a {RoleRevoked} * event. * * Requirements: * * - the caller must be `account`. */ function renounceRole(bytes32 role, address account) public virtual override { require(account == _msgSender(), "AccessControl: can only renounce roles for self"); _revokeRole(role, account); } /** * @dev Grants `role` to `account`. * * If `account` had not been already granted `role`, emits a {RoleGranted} * event. Note that unlike {grantRole}, this function doesn't perform any * checks on the calling account. * * [WARNING] * ==== * This function should only be called from the constructor when setting * up the initial roles for the system. * * Using this function in any other way is effectively circumventing the admin * system imposed by {AccessControl}. * ==== * * NOTE: This function is deprecated in favor of {_grantRole}. */ function _setupRole(bytes32 role, address account) internal virtual { _grantRole(role, account); } /** * @dev Sets `adminRole` as ``role``'s admin role. * * Emits a {RoleAdminChanged} event. */ function _setRoleAdmin(bytes32 role, bytes32 adminRole) internal virtual { bytes32 previousAdminRole = getRoleAdmin(role); _roles[role].adminRole = adminRole; emit RoleAdminChanged(role, previousAdminRole, adminRole); } /** * @dev Grants `role` to `account`. * * Internal function without access restriction. */ function _grantRole(bytes32 role, address account) internal virtual { if (!hasRole(role, account)) { _roles[role].members[account] = true; emit RoleGranted(role, account, _msgSender()); } } /** * @dev Revokes `role` from `account`. * * Internal function without access restriction. */ function _revokeRole(bytes32 role, address account) internal virtual { if (hasRole(role, account)) { _roles[role].members[account] = false; emit RoleRevoked(role, account, _msgSender()); } } } // File @openzeppelin/contracts/utils/structs/[email protected] // OpenZeppelin Contracts v4.4.1 (utils/structs/EnumerableSet.sol) pragma solidity ^0.8.0; /** * @dev Library for managing * https://en.wikipedia.org/wiki/Set_(abstract_data_type)[sets] of primitive * types. * * Sets have the following properties: * * - Elements are added, removed, and checked for existence in constant time * (O(1)). * - Elements are enumerated in O(n). No guarantees are made on the ordering. * * ``` * contract Example { * // Add the library methods * using EnumerableSet for EnumerableSet.AddressSet; * * // Declare a set state variable * EnumerableSet.AddressSet private mySet; * } * ``` * * As of v3.3.0, sets of type `bytes32` (`Bytes32Set`), `address` (`AddressSet`) * and `uint256` (`UintSet`) are supported. */ library 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 @openzeppelin/contracts/access/[email protected] // OpenZeppelin Contracts (last updated v4.5.0) (access/AccessControlEnumerable.sol) pragma solidity ^0.8.0; /** * @dev Extension of {AccessControl} that allows enumerating the members of each role. */ abstract contract AccessControlEnumerable is IAccessControlEnumerable, AccessControl { using EnumerableSet for EnumerableSet.AddressSet; mapping(bytes32 => EnumerableSet.AddressSet) private _roleMembers; /** * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return interfaceId == type(IAccessControlEnumerable).interfaceId || super.supportsInterface(interfaceId); } /** * @dev Returns one of the accounts that have `role`. `index` must be a * value between 0 and {getRoleMemberCount}, non-inclusive. * * Role bearers are not sorted in any particular way, and their ordering may * change at any point. * * WARNING: When using {getRoleMember} and {getRoleMemberCount}, make sure * you perform all queries on the same block. See the following * https://forum.openzeppelin.com/t/iterating-over-elements-on-enumerableset-in-openzeppelin-contracts/2296[forum post] * for more information. */ function getRoleMember(bytes32 role, uint256 index) public view virtual override returns (address) { return _roleMembers[role].at(index); } /** * @dev Returns the number of accounts that have `role`. Can be used * together with {getRoleMember} to enumerate all bearers of a role. */ function getRoleMemberCount(bytes32 role) public view virtual override returns (uint256) { return _roleMembers[role].length(); } /** * @dev Overload {_grantRole} to track enumerable memberships */ function _grantRole(bytes32 role, address account) internal virtual override { super._grantRole(role, account); _roleMembers[role].add(account); } /** * @dev Overload {_revokeRole} to track enumerable memberships */ function _revokeRole(bytes32 role, address account) internal virtual override { super._revokeRole(role, account); _roleMembers[role].remove(account); } } // File @openzeppelin/contracts/interfaces/[email protected] // OpenZeppelin Contracts v4.4.1 (interfaces/IERC165.sol) pragma solidity ^0.8.0; // File @openzeppelin/contracts/interfaces/[email protected] // OpenZeppelin Contracts (last updated v4.5.0) (interfaces/IERC2981.sol) pragma solidity ^0.8.0; /** * @dev Interface for the NFT Royalty Standard. * * A standardized way to retrieve royalty payment information for non-fungible tokens (NFTs) to enable universal * support for royalty payments across all NFT marketplaces and ecosystem participants. * * _Available since v4.5._ */ interface IERC2981 is IERC165 { /** * @dev Returns how much royalty is owed and to whom, based on a sale price that may be denominated in any unit of * exchange. The royalty amount is denominated and should be payed in that same unit of exchange. */ function royaltyInfo(uint256 tokenId, uint256 salePrice) external view returns (address receiver, uint256 royaltyAmount); } // File @openzeppelin/contracts/token/common/[email protected] // OpenZeppelin Contracts (last updated v4.5.0) (token/common/ERC2981.sol) pragma solidity ^0.8.0; /** * @dev Implementation of the NFT Royalty Standard, a standardized way to retrieve royalty payment information. * * Royalty information can be specified globally for all token ids via {_setDefaultRoyalty}, and/or individually for * specific token ids via {_setTokenRoyalty}. The latter takes precedence over the first. * * Royalty is specified as a fraction of sale price. {_feeDenominator} is overridable but defaults to 10000, meaning the * fee is specified in basis points by default. * * IMPORTANT: ERC-2981 only specifies a way to signal royalty information and does not enforce its payment. See * https://eips.ethereum.org/EIPS/eip-2981#optional-royalty-payments[Rationale] in the EIP. Marketplaces are expected to * voluntarily pay royalties together with sales, but note that this standard is not yet widely supported. * * _Available since v4.5._ */ abstract contract ERC2981 is IERC2981, ERC165 { struct RoyaltyInfo { address receiver; uint96 royaltyFraction; } RoyaltyInfo private _defaultRoyaltyInfo; mapping(uint256 => RoyaltyInfo) private _tokenRoyaltyInfo; /** * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override(IERC165, ERC165) returns (bool) { return interfaceId == type(IERC2981).interfaceId || super.supportsInterface(interfaceId); } /** * @inheritdoc IERC2981 */ function royaltyInfo(uint256 _tokenId, uint256 _salePrice) external view virtual override returns (address, uint256) { RoyaltyInfo memory royalty = _tokenRoyaltyInfo[_tokenId]; if (royalty.receiver == address(0)) { royalty = _defaultRoyaltyInfo; } uint256 royaltyAmount = (_salePrice * royalty.royaltyFraction) / _feeDenominator(); return (royalty.receiver, royaltyAmount); } /** * @dev The denominator with which to interpret the fee set in {_setTokenRoyalty} and {_setDefaultRoyalty} as a * fraction of the sale price. Defaults to 10000 so fees are expressed in basis points, but may be customized by an * override. */ function _feeDenominator() internal pure virtual returns (uint96) { return 10000; } /** * @dev Sets the royalty information that all ids in this contract will default to. * * Requirements: * * - `receiver` cannot be the zero address. * - `feeNumerator` cannot be greater than the fee denominator. */ function _setDefaultRoyalty(address receiver, uint96 feeNumerator) internal virtual { require(feeNumerator <= _feeDenominator(), "ERC2981: royalty fee will exceed salePrice"); require(receiver != address(0), "ERC2981: invalid receiver"); _defaultRoyaltyInfo = RoyaltyInfo(receiver, feeNumerator); } /** * @dev Removes default royalty information. */ function _deleteDefaultRoyalty() internal virtual { delete _defaultRoyaltyInfo; } /** * @dev Sets the royalty information for a specific token id, overriding the global default. * * Requirements: * * - `tokenId` must be already minted. * - `receiver` cannot be the zero address. * - `feeNumerator` cannot be greater than the fee denominator. */ function _setTokenRoyalty( uint256 tokenId, address receiver, uint96 feeNumerator ) internal virtual { require(feeNumerator <= _feeDenominator(), "ERC2981: royalty fee will exceed salePrice"); require(receiver != address(0), "ERC2981: Invalid parameters"); _tokenRoyaltyInfo[tokenId] = RoyaltyInfo(receiver, feeNumerator); } /** * @dev Resets royalty information for the token id back to the global default. */ function _resetTokenRoyalty(uint256 tokenId) internal virtual { delete _tokenRoyaltyInfo[tokenId]; } } // File erc721a/contracts/extensions/[email protected] // ERC721A Contracts v4.2.2 // Creator: Chiru Labs pragma solidity ^0.8.4; /** * @dev Interface of ERC721AQueryable. */ interface IERC721AQueryable is IERC721A { /** * Invalid query range (`start` >= `stop`). */ error InvalidQueryRange(); /** * @dev Returns the `TokenOwnership` struct at `tokenId` without reverting. * * If the `tokenId` is out of bounds: * * - `addr = address(0)` * - `startTimestamp = 0` * - `burned = false` * - `extraData = 0` * * If the `tokenId` is burned: * * - `addr = <Address of owner before token was burned>` * - `startTimestamp = <Timestamp when token was burned>` * - `burned = true` * - `extraData = <Extra data when token was burned>` * * Otherwise: * * - `addr = <Address of owner>` * - `startTimestamp = <Timestamp of start of ownership>` * - `burned = false` * - `extraData = <Extra data at start of ownership>` */ function explicitOwnershipOf(uint256 tokenId) external view returns (TokenOwnership memory); /** * @dev Returns an array of `TokenOwnership` structs at `tokenIds` in order. * See {ERC721AQueryable-explicitOwnershipOf} */ function explicitOwnershipsOf(uint256[] memory tokenIds) external view returns (TokenOwnership[] memory); /** * @dev Returns an array of token IDs owned by `owner`, * in the range [`start`, `stop`) * (i.e. `start <= tokenId < stop`). * * This function allows for tokens to be queried if the collection * grows too big for a single call of {ERC721AQueryable-tokensOfOwner}. * * Requirements: * * - `start < stop` */ function tokensOfOwnerIn( address owner, uint256 start, uint256 stop ) external view returns (uint256[] memory); /** * @dev Returns an array of token IDs owned by `owner`. * * This function scans the ownership mapping and is O(`totalSupply`) in complexity. * It is meant to be called off-chain. * * See {ERC721AQueryable-tokensOfOwnerIn} for splitting the scan into * multiple smaller scans if the collection is large enough to cause * an out-of-gas error (10K collections should be fine). */ function tokensOfOwner(address owner) external view returns (uint256[] memory); } // File erc721a/contracts/extensions/[email protected] // ERC721A Contracts v4.2.2 // Creator: Chiru Labs pragma solidity ^0.8.4; /** * @title ERC721AQueryable. * * @dev ERC721A subclass with convenience query functions. */ abstract contract ERC721AQueryable is ERC721A, IERC721AQueryable { /** * @dev Returns the `TokenOwnership` struct at `tokenId` without reverting. * * If the `tokenId` is out of bounds: * * - `addr = address(0)` * - `startTimestamp = 0` * - `burned = false` * - `extraData = 0` * * If the `tokenId` is burned: * * - `addr = <Address of owner before token was burned>` * - `startTimestamp = <Timestamp when token was burned>` * - `burned = true` * - `extraData = <Extra data when token was burned>` * * Otherwise: * * - `addr = <Address of owner>` * - `startTimestamp = <Timestamp of start of ownership>` * - `burned = false` * - `extraData = <Extra data at start of ownership>` */ function explicitOwnershipOf(uint256 tokenId) public view virtual override returns (TokenOwnership memory) { TokenOwnership memory ownership; if (tokenId < _startTokenId() || tokenId >= _nextTokenId()) { return ownership; } ownership = _ownershipAt(tokenId); if (ownership.burned) { return ownership; } return _ownershipOf(tokenId); } /** * @dev Returns an array of `TokenOwnership` structs at `tokenIds` in order. * See {ERC721AQueryable-explicitOwnershipOf} */ function explicitOwnershipsOf(uint256[] calldata tokenIds) external view virtual override returns (TokenOwnership[] memory) { unchecked { uint256 tokenIdsLength = tokenIds.length; TokenOwnership[] memory ownerships = new TokenOwnership[](tokenIdsLength); for (uint256 i; i != tokenIdsLength; ++i) { ownerships[i] = explicitOwnershipOf(tokenIds[i]); } return ownerships; } } /** * @dev Returns an array of token IDs owned by `owner`, * in the range [`start`, `stop`) * (i.e. `start <= tokenId < stop`). * * This function allows for tokens to be queried if the collection * grows too big for a single call of {ERC721AQueryable-tokensOfOwner}. * * Requirements: * * - `start < stop` */ function tokensOfOwnerIn( address owner, uint256 start, uint256 stop ) external view virtual override returns (uint256[] memory) { unchecked { if (start >= stop) revert InvalidQueryRange(); uint256 tokenIdsIdx; uint256 stopLimit = _nextTokenId(); // Set `start = max(start, _startTokenId())`. if (start < _startTokenId()) { start = _startTokenId(); } // Set `stop = min(stop, stopLimit)`. if (stop > stopLimit) { stop = stopLimit; } uint256 tokenIdsMaxLength = balanceOf(owner); // Set `tokenIdsMaxLength = min(balanceOf(owner), stop - start)`, // to cater for cases where `balanceOf(owner)` is too big. if (start < stop) { uint256 rangeLength = stop - start; if (rangeLength < tokenIdsMaxLength) { tokenIdsMaxLength = rangeLength; } } else { tokenIdsMaxLength = 0; } uint256[] memory tokenIds = new uint256[](tokenIdsMaxLength); if (tokenIdsMaxLength == 0) { return tokenIds; } // We need to call `explicitOwnershipOf(start)`, // because the slot at `start` may not be initialized. TokenOwnership memory ownership = explicitOwnershipOf(start); address currOwnershipAddr; // If the starting slot exists (i.e. not burned), initialize `currOwnershipAddr`. // `ownership.address` will not be zero, as `start` is clamped to the valid token ID range. if (!ownership.burned) { currOwnershipAddr = ownership.addr; } for (uint256 i = start; i != stop && tokenIdsIdx != tokenIdsMaxLength; ++i) { ownership = _ownershipAt(i); if (ownership.burned) { continue; } if (ownership.addr != address(0)) { currOwnershipAddr = ownership.addr; } if (currOwnershipAddr == owner) { tokenIds[tokenIdsIdx++] = i; } } // Downsize the array to fit. assembly { mstore(tokenIds, tokenIdsIdx) } return tokenIds; } } /** * @dev Returns an array of token IDs owned by `owner`. * * This function scans the ownership mapping and is O(`totalSupply`) in complexity. * It is meant to be called off-chain. * * See {ERC721AQueryable-tokensOfOwnerIn} for splitting the scan into * multiple smaller scans if the collection is large enough to cause * an out-of-gas error (10K collections should be fine). */ function tokensOfOwner(address owner) external view virtual override returns (uint256[] memory) { unchecked { uint256 tokenIdsIdx; address currOwnershipAddr; uint256 tokenIdsLength = balanceOf(owner); uint256[] memory tokenIds = new uint256[](tokenIdsLength); TokenOwnership memory ownership; for (uint256 i = _startTokenId(); tokenIdsIdx != tokenIdsLength; ++i) { ownership = _ownershipAt(i); if (ownership.burned) { continue; } if (ownership.addr != address(0)) { currOwnershipAddr = ownership.addr; } if (currOwnershipAddr == owner) { tokenIds[tokenIdsIdx++] = i; } } return tokenIds; } } } // File contracts/BasicErc721A.sol pragma solidity 0.8.4; // import "@openzeppelin/contracts/utils/introspection/ERC165.sol"; contract BasicERC721A is ERC165, ERC721A, ERC2981, ERC721AQueryable, AccessControlEnumerable { string private _baseTokenURI; uint256 public maxSupply; uint256 public constant startIndex = 1; bytes32 public constant MINTER_ROLE = keccak256("MINTER_ROLE"); event UpdateRoyalty(address indexed _royaltyReceiver, uint96 _royaltyFee); event UpdateTokenRoyalty(uint256 indexed _tokenId, address indexed _royaltyReceiver, uint96 _royaltyFee); event ResetTokenRoyalty(uint256 indexed _tokenId); event DeleteDefaultRoyalty(); event UpdateMaxSupply(uint256 oldMaxSupply, uint256 newMaxSupply); constructor( string memory name_, string memory symbol_, uint256 _maxSupply, address _minter, address _royaltyReceiver, uint96 _royaltyFee // 100 = 1% ) ERC721A(name_, symbol_) { require(_maxSupply > 0, "maxSupply is 0"); maxSupply = _maxSupply; _grantRole(DEFAULT_ADMIN_ROLE, msg.sender); require(hasRole(DEFAULT_ADMIN_ROLE, msg.sender), "__grantRole failed for DEFAULT_ADMIN_ROLE"); // Minter is not required. If minter address is specified, then give the minter role if (_minter != address(0)) { _grantRole(MINTER_ROLE, _minter); require(hasRole(MINTER_ROLE, _minter), "__grantRole failed for MINTER_ROLE"); } // set royalty information if (_royaltyReceiver != address(0)) { _setDefaultRoyalty(_royaltyReceiver, _royaltyFee); } } function _startTokenId() internal view virtual override returns (uint256) { return startIndex; } function updateMaxSupply(uint256 _newMaxSupply) public { require(_newMaxSupply >= totalSupply(), "invalid maxSupply"); emit UpdateMaxSupply(maxSupply, _newMaxSupply); maxSupply = _newMaxSupply; } function totalMinted() public view returns (uint256) { return _totalMinted(); } function safeMint(address to) external { require( hasRole(DEFAULT_ADMIN_ROLE, msg.sender) || hasRole(MINTER_ROLE, msg.sender), "no permission to call" ); require(totalSupply() < maxSupply, "max supply reached"); _mint(to, 1); } function batchMint(address to, uint256 quantity) external { require( hasRole(DEFAULT_ADMIN_ROLE, msg.sender) || hasRole(MINTER_ROLE, msg.sender), "no permission to call" ); require(totalSupply() + quantity <= maxSupply, "max supply reached"); _mint(to, quantity); } function _baseURI() internal view virtual override returns (string memory) { return _baseTokenURI; } function baseURI() public view returns (string memory) { return _baseURI(); } function setBaseURI(string calldata _newBaseURI) public onlyRole(DEFAULT_ADMIN_ROLE) { _baseTokenURI = _newBaseURI; } function supportsInterface(bytes4 interfaceId) public view override(ERC165, ERC721A, ERC2981, AccessControlEnumerable) returns (bool) { return super.supportsInterface(interfaceId); } // royalty function updateRoyalty(address _royaltyReceiver, uint96 _royaltyFee) external onlyRole(DEFAULT_ADMIN_ROLE) { _setDefaultRoyalty(_royaltyReceiver, _royaltyFee); emit UpdateRoyalty(_royaltyReceiver, _royaltyFee); } function deleteDefaultRoyalty() external onlyRole(DEFAULT_ADMIN_ROLE) { _deleteDefaultRoyalty(); emit DeleteDefaultRoyalty(); } function updateTokenRoyalty( uint256 _tokenId, address _royaltyReceiver, uint96 _royaltyFee ) external onlyRole(DEFAULT_ADMIN_ROLE) { _setTokenRoyalty(_tokenId, _royaltyReceiver, _royaltyFee); emit UpdateTokenRoyalty(_tokenId, _royaltyReceiver, _royaltyFee); } function resetTokenRoyalty(uint256 _tokenId) external onlyRole(DEFAULT_ADMIN_ROLE) { _resetTokenRoyalty(_tokenId); emit ResetTokenRoyalty(_tokenId); } }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
[{"inputs":[{"internalType":"string","name":"name_","type":"string"},{"internalType":"string","name":"symbol_","type":"string"},{"internalType":"uint256","name":"_maxSupply","type":"uint256"},{"internalType":"address","name":"_minter","type":"address"},{"internalType":"address","name":"_royaltyReceiver","type":"address"},{"internalType":"uint96","name":"_royaltyFee","type":"uint96"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ApprovalCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"ApprovalQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"ApproveToCaller","type":"error"},{"inputs":[],"name":"BalanceQueryForZeroAddress","type":"error"},{"inputs":[],"name":"InvalidQueryRange","type":"error"},{"inputs":[],"name":"MintERC2309QuantityExceedsLimit","type":"error"},{"inputs":[],"name":"MintToZeroAddress","type":"error"},{"inputs":[],"name":"MintZeroQuantity","type":"error"},{"inputs":[],"name":"OwnerQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"OwnershipNotInitializedForExtraData","type":"error"},{"inputs":[],"name":"TransferCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"TransferFromIncorrectOwner","type":"error"},{"inputs":[],"name":"TransferToNonERC721ReceiverImplementer","type":"error"},{"inputs":[],"name":"TransferToZeroAddress","type":"error"},{"inputs":[],"name":"URIQueryForNonexistentToken","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":"uint256","name":"fromTokenId","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"toTokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"}],"name":"ConsecutiveTransfer","type":"event"},{"anonymous":false,"inputs":[],"name":"DeleteDefaultRoyalty","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"_tokenId","type":"uint256"}],"name":"ResetTokenRoyalty","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"previousAdminRole","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"newAdminRole","type":"bytes32"}],"name":"RoleAdminChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleGranted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleRevoked","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"oldMaxSupply","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"newMaxSupply","type":"uint256"}],"name":"UpdateMaxSupply","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"_royaltyReceiver","type":"address"},{"indexed":false,"internalType":"uint96","name":"_royaltyFee","type":"uint96"}],"name":"UpdateRoyalty","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"_tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"_royaltyReceiver","type":"address"},{"indexed":false,"internalType":"uint96","name":"_royaltyFee","type":"uint96"}],"name":"UpdateTokenRoyalty","type":"event"},{"inputs":[],"name":"DEFAULT_ADMIN_ROLE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"MINTER_ROLE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"baseURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"quantity","type":"uint256"}],"name":"batchMint","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"deleteDefaultRoyalty","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"explicitOwnershipOf","outputs":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint64","name":"startTimestamp","type":"uint64"},{"internalType":"bool","name":"burned","type":"bool"},{"internalType":"uint24","name":"extraData","type":"uint24"}],"internalType":"struct IERC721A.TokenOwnership","name":"","type":"tuple"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"}],"name":"explicitOwnershipsOf","outputs":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint64","name":"startTimestamp","type":"uint64"},{"internalType":"bool","name":"burned","type":"bool"},{"internalType":"uint24","name":"extraData","type":"uint24"}],"internalType":"struct IERC721A.TokenOwnership[]","name":"","type":"tuple[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"getRoleAdmin","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"uint256","name":"index","type":"uint256"}],"name":"getRoleMember","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"getRoleMemberCount","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"grantRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"hasRole","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maxSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"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":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"renounceRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"}],"name":"resetTokenRoyalty","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"revokeRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"},{"internalType":"uint256","name":"_salePrice","type":"uint256"}],"name":"royaltyInfo","outputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"}],"name":"safeMint","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"_data","type":"bytes"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"_newBaseURI","type":"string"}],"name":"setBaseURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"startIndex","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"tokensOfOwner","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"uint256","name":"start","type":"uint256"},{"internalType":"uint256","name":"stop","type":"uint256"}],"name":"tokensOfOwnerIn","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalMinted","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_newMaxSupply","type":"uint256"}],"name":"updateMaxSupply","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_royaltyReceiver","type":"address"},{"internalType":"uint96","name":"_royaltyFee","type":"uint96"}],"name":"updateRoyalty","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"},{"internalType":"address","name":"_royaltyReceiver","type":"address"},{"internalType":"uint96","name":"_royaltyFee","type":"uint96"}],"name":"updateTokenRoyalty","outputs":[],"stateMutability":"nonpayable","type":"function"}]
Contract Creation Code
60806040523480156200001157600080fd5b506040516200587e3803806200587e83398181016040528101906200003791906200080c565b8585816002908051906020019062000051929190620006a5565b5080600390805190602001906200006a929190620006a5565b506200007b6200026c60201b60201c565b600081905550505060008411620000c9576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401620000c09062000997565b60405180910390fd5b83600d81905550620000e56000801b336200027560201b60201c565b620000fa6000801b33620002bd60201b60201c565b6200013c576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016200013390620009b9565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff16146200021857620001a37f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6846200027560201b60201c565b620001d57f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a684620002bd60201b60201c565b62000217576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016200020e90620009db565b60405180910390fd5b5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161462000260576200025f82826200032860201b60201c565b5b50505050505062000da5565b60006001905090565b6200028c8282620004cc60201b62001f941760201c565b620002b881600b6000858152602001908152602001600020620005be60201b620020751790919060201c565b505050565b6000600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b62000338620005f660201b60201c565b6bffffffffffffffffffffffff16816bffffffffffffffffffffffff16111562000399576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016200039090620009fd565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614156200040c576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401620004039062000a1f565b60405180910390fd5b60405180604001604052808373ffffffffffffffffffffffffffffffffffffffff168152602001826bffffffffffffffffffffffff16815250600860008201518160000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060208201518160000160146101000a8154816bffffffffffffffffffffffff02191690836bffffffffffffffffffffffff1602179055509050505050565b620004de8282620002bd60201b60201c565b620005ba576001600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506200055f6200060060201b60201c565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45b5050565b6000620005ee836000018373ffffffffffffffffffffffffffffffffffffffff1660001b6200060860201b60201c565b905092915050565b6000612710905090565b600033905090565b60006200061c83836200068260201b60201c565b620006775782600001829080600181540180825580915050600190039060005260206000200160009091909190915055826000018054905083600101600084815260200190815260200160002081905550600190506200067c565b600090505b92915050565b600080836001016000848152602001908152602001600020541415905092915050565b828054620006b39062000b3d565b90600052602060002090601f016020900481019282620006d7576000855562000723565b82601f10620006f257805160ff191683800117855562000723565b8280016001018555821562000723579182015b828111156200072257825182559160200191906001019062000705565b5b50905062000732919062000736565b5090565b5b808211156200075157600081600090555060010162000737565b5090565b60006200076c620007668462000a6a565b62000a41565b9050828152602081018484840111156200078557600080fd5b6200079284828562000b07565b509392505050565b600081519050620007ab8162000d57565b92915050565b600082601f830112620007c357600080fd5b8151620007d584826020860162000755565b91505092915050565b600081519050620007ef8162000d71565b92915050565b600081519050620008068162000d8b565b92915050565b60008060008060008060c087890312156200082657600080fd5b600087015167ffffffffffffffff8111156200084157600080fd5b6200084f89828a01620007b1565b965050602087015167ffffffffffffffff8111156200086d57600080fd5b6200087b89828a01620007b1565b95505060406200088e89828a01620007de565b9450506060620008a189828a016200079a565b9350506080620008b489828a016200079a565b92505060a0620008c789828a01620007f5565b9150509295509295509295565b6000620008e3600e8362000aa0565b9150620008f08262000c18565b602082019050919050565b60006200090a60298362000aa0565b9150620009178262000c41565b604082019050919050565b60006200093160228362000aa0565b91506200093e8262000c90565b604082019050919050565b600062000958602a8362000aa0565b9150620009658262000cdf565b604082019050919050565b60006200097f60198362000aa0565b91506200098c8262000d2e565b602082019050919050565b60006020820190508181036000830152620009b281620008d4565b9050919050565b60006020820190508181036000830152620009d481620008fb565b9050919050565b60006020820190508181036000830152620009f68162000922565b9050919050565b6000602082019050818103600083015262000a188162000949565b9050919050565b6000602082019050818103600083015262000a3a8162000970565b9050919050565b600062000a4d62000a60565b905062000a5b828262000b73565b919050565b6000604051905090565b600067ffffffffffffffff82111562000a885762000a8762000bd8565b5b62000a938262000c07565b9050602081019050919050565b600082825260208201905092915050565b600062000abe8262000ac5565b9050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b60006bffffffffffffffffffffffff82169050919050565b60005b8381101562000b2757808201518184015260208101905062000b0a565b8381111562000b37576000848401525b50505050565b6000600282049050600182168062000b5657607f821691505b6020821081141562000b6d5762000b6c62000ba9565b5b50919050565b62000b7e8262000c07565b810181811067ffffffffffffffff8211171562000ba05762000b9f62000bd8565b5b80604052505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6000601f19601f8301169050919050565b7f6d6178537570706c792069732030000000000000000000000000000000000000600082015250565b7f5f5f6772616e74526f6c65206661696c656420666f722044454641554c545f4160008201527f444d494e5f524f4c450000000000000000000000000000000000000000000000602082015250565b7f5f5f6772616e74526f6c65206661696c656420666f72204d494e5445525f524f60008201527f4c45000000000000000000000000000000000000000000000000000000000000602082015250565b7f455243323938313a20726f79616c7479206665652077696c6c2065786365656460008201527f2073616c65507269636500000000000000000000000000000000000000000000602082015250565b7f455243323938313a20696e76616c696420726563656976657200000000000000600082015250565b62000d628162000ab1565b811462000d6e57600080fd5b50565b62000d7c8162000ae5565b811462000d8857600080fd5b50565b62000d968162000aef565b811462000da257600080fd5b50565b614ac98062000db56000396000f3fe608060405234801561001057600080fd5b50600436106102485760003560e01c806386e228d51161013b578063b88d4fde116100b8578063d547741f1161007c578063d547741f14610738578063d5abeb0114610754578063daa83c6d14610772578063e985e9c51461078e578063f103b433146107be57610248565b8063b88d4fde1461066e578063c23dc68f1461068a578063c87b56dd146106ba578063ca15c873146106ea578063d53913931461071a57610248565b806399a2557a116100ff57806399a2557a146105dc578063a217fddf1461060c578063a22cb4651461062a578063a2309ff814610646578063aa1b103f1461066457610248565b806386e228d5146105265780638a616bc0146105425780639010d07c1461055e57806391d148541461058e57806395d89b41146105be57610248565b80633e0e828b116101c95780635bbb21771161018d5780635bbb2177146104485780636352211e146104785780636c0360eb146104a857806370a08231146104c65780638462151c146104f657610248565b80633e0e828b146103ba57806340d097c3146103d857806342842e0e146103f457806343508b051461041057806355f804b31461042c57610248565b806323b872dd1161021057806323b872dd14610305578063248a9ca3146103215780632a55205a146103515780632f2ff15d1461038257806336568abe1461039e57610248565b806301ffc9a71461024d57806306fdde031461027d578063081812fc1461029b578063095ea7b3146102cb57806318160ddd146102e7575b600080fd5b61026760048036038101906102629190613b32565b6107da565b60405161027491906141dc565b60405180910390f35b6102856107ec565b6040516102929190614212565b60405180910390f35b6102b560048036038101906102b09190613bc9565b61087e565b6040516102c29190614108565b60405180910390f35b6102e560048036038101906102e09190613985565b6108fd565b005b6102ef610a41565b6040516102fc919061434f565b60405180910390f35b61031f600480360381019061031a919061387f565b610a58565b005b61033b60048036038101906103369190613a91565b610d7d565b60405161034891906141f7565b60405180910390f35b61036b60048036038101906103669190613c41565b610d9d565b60405161037992919061416f565b60405180910390f35b61039c60048036038101906103979190613aba565b610f88565b005b6103b860048036038101906103b39190613aba565b610fb1565b005b6103c2611034565b6040516103cf919061434f565b60405180910390f35b6103f260048036038101906103ed919061381a565b611039565b005b61040e6004803603810190610409919061387f565b61110f565b005b61042a60048036038101906104259190613985565b61112f565b005b61044660048036038101906104419190613b84565b611211565b005b610462600480360381019061045d9190613a4c565b61123d565b60405161046f9190614198565b60405180910390f35b610492600480360381019061048d9190613bc9565b611372565b60405161049f9190614108565b60405180910390f35b6104b0611384565b6040516104bd9190614212565b60405180910390f35b6104e060048036038101906104db919061381a565b611393565b6040516104ed919061434f565b60405180910390f35b610510600480360381019061050b919061381a565b61144c565b60405161051d91906141ba565b60405180910390f35b610540600480360381019061053b9190613bf2565b6115e2565b005b61055c60048036038101906105579190613bc9565b611657565b005b61057860048036038101906105739190613af6565b6116a6565b6040516105859190614108565b60405180910390f35b6105a860048036038101906105a39190613aba565b6116d5565b6040516105b591906141dc565b60405180910390f35b6105c6611740565b6040516105d39190614212565b60405180910390f35b6105f660048036038101906105f191906139c1565b6117d2565b60405161060391906141ba565b60405180910390f35b610614611a32565b60405161062191906141f7565b60405180910390f35b610644600480360381019061063f9190613949565b611a39565b005b61064e611bb1565b60405161065b919061434f565b60405180910390f35b61066c611bc0565b005b610688600480360381019061068391906138ce565b611c0c565b005b6106a4600480360381019061069f9190613bc9565b611c7f565b6040516106b19190614334565b60405180910390f35b6106d460048036038101906106cf9190613bc9565b611ce9565b6040516106e19190614212565b60405180910390f35b61070460048036038101906106ff9190613a91565b611d88565b604051610711919061434f565b60405180910390f35b610722611dac565b60405161072f91906141f7565b60405180910390f35b610752600480360381019061074d9190613aba565b611dd0565b005b61075c611df9565b604051610769919061434f565b60405180910390f35b61078c60048036038101906107879190613a10565b611dff565b005b6107a860048036038101906107a39190613843565b611e71565b6040516107b591906141dc565b60405180910390f35b6107d860048036038101906107d39190613bc9565b611f05565b005b60006107e5826120a5565b9050919050565b6060600280546107fb906146f3565b80601f0160208091040260200160405190810160405280929190818152602001828054610827906146f3565b80156108745780601f1061084957610100808354040283529160200191610874565b820191906000526020600020905b81548152906001019060200180831161085757829003601f168201915b5050505050905090565b60006108898261211f565b6108bf576040517fcf4700e400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6006600083815260200190815260200160002060000160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff169050919050565b600061090882611372565b90508073ffffffffffffffffffffffffffffffffffffffff1661092961217e565b73ffffffffffffffffffffffffffffffffffffffff161461098c576109558161095061217e565b611e71565b61098b576040517fcfb3b94200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b826006600084815260200190815260200160002060000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550818373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a4505050565b6000610a4b612186565b6001546000540303905090565b6000610a638261218f565b90508373ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614610aca576040517fa114810000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b600080610ad68461225d565b91509150610aec8187610ae761217e565b612284565b610b3857610b0186610afc61217e565b611e71565b610b37576040517f59c896be00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415610b9f576040517fea553b3400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610bac86868660016122c8565b8015610bb757600082555b600560008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600081546001900391905081905550600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000815460010191905081905550610c8585610c618888876122ce565b7c0200000000000000000000000000000000000000000000000000000000176122f6565b600460008681526020019081526020016000208190555060007c020000000000000000000000000000000000000000000000000000000084161415610d0d576000600185019050600060046000838152602001908152602001600020541415610d0b576000548114610d0a578360046000838152602001908152602001600020819055505b5b505b838573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4610d758686866001612321565b505050505050565b6000600a6000838152602001908152602001600020600101549050919050565b6000806000600960008681526020019081526020016000206040518060400160405290816000820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020016000820160149054906101000a90046bffffffffffffffffffffffff166bffffffffffffffffffffffff166bffffffffffffffffffffffff16815250509050600073ffffffffffffffffffffffffffffffffffffffff16816000015173ffffffffffffffffffffffffffffffffffffffff161415610f335760086040518060400160405290816000820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020016000820160149054906101000a90046bffffffffffffffffffffffff166bffffffffffffffffffffffff166bffffffffffffffffffffffff168152505090505b6000610f3d612327565b6bffffffffffffffffffffffff1682602001516bffffffffffffffffffffffff1686610f699190614540565b610f73919061450f565b90508160000151819350935050509250929050565b610f9182610d7d565b610fa281610f9d612331565b612339565b610fac83836123d6565b505050565b610fb9612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614611026576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161101d90614314565b60405180910390fd5b611030828261240a565b5050565b600181565b6110466000801b336116d5565b8061107757506110767f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6336116d5565b5b6110b6576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016110ad90614274565b60405180910390fd5b600d546110c1610a41565b10611101576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016110f890614294565b60405180910390fd5b61110c81600161243e565b50565b61112a83838360405180602001604052806000815250611c0c565b505050565b61113c6000801b336116d5565b8061116d575061116c7f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6336116d5565b5b6111ac576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016111a390614274565b60405180910390fd5b600d54816111b8610a41565b6111c291906144b9565b1115611203576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016111fa90614294565b60405180910390fd5b61120d828261243e565b5050565b6000801b61122681611221612331565b612339565b8282600c9190611237929190613599565b50505050565b6060600083839050905060008167ffffffffffffffff811115611289577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156112c257816020015b6112af61361f565b8152602001906001900390816112a75790505b50905060005b8281146113665761131786868381811061130b577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90506020020135611c7f565b828281518110611350577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200260200101819052508060010190506112c8565b50809250505092915050565b600061137d8261218f565b9050919050565b606061138e6125fb565b905090565b60008073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614156113fb576040517f8f4eb60400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b67ffffffffffffffff600560008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054169050919050565b6060600080600061145c85611393565b905060008167ffffffffffffffff8111156114a0577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156114ce5781602001602082028036833780820191505090505b5090506114d961361f565b60006114e3612186565b90505b8386146115d4576114f68161268d565b9150816040015115611507576115c9565b600073ffffffffffffffffffffffffffffffffffffffff16826000015173ffffffffffffffffffffffffffffffffffffffff161461154757816000015194505b8773ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff1614156115c857808387806001019850815181106115bb577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b6020026020010181815250505b5b8060010190506114e6565b508195505050505050919050565b6000801b6115f7816115f2612331565b612339565b6116028484846126b8565b8273ffffffffffffffffffffffffffffffffffffffff16847f8219bae90c1815288c07ea441a930eb14c911bcee209d79219ff8098e9b243a2846040516116499190614393565b60405180910390a350505050565b6000801b61166c81611667612331565b612339565b61167582612860565b817f2d0c64cb223c165096aa5260f0c4f12caf09469f917f6139ff17e1795a01225d60405160405180910390a25050565b60006116cd82600b60008681526020019081526020016000206128bf90919063ffffffff16565b905092915050565b6000600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b60606003805461174f906146f3565b80601f016020809104026020016040519081016040528092919081815260200182805461177b906146f3565b80156117c85780601f1061179d576101008083540402835291602001916117c8565b820191906000526020600020905b8154815290600101906020018083116117ab57829003601f168201915b5050505050905090565b606081831061180d576040517f32c1995a00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000806118186128d9565b9050611822612186565b85101561183457611831612186565b94505b80841115611840578093505b600061184b87611393565b90508486101561186e576000868603905081811015611868578091505b50611873565b600090505b60008167ffffffffffffffff8111156118b5577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156118e35781602001602082028036833780820191505090505b50905060008214156118fb5780945050505050611a2b565b600061190688611c7f565b90506000816040015161191b57816000015190505b60008990505b8881141580156119315750848714155b15611a1d5761193f8161268d565b925082604001511561195057611a12565b600073ffffffffffffffffffffffffffffffffffffffff16836000015173ffffffffffffffffffffffffffffffffffffffff161461199057826000015191505b8a73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611a115780848880600101995081518110611a04577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b6020026020010181815250505b5b806001019050611921565b508583528296505050505050505b9392505050565b6000801b81565b611a4161217e565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611aa6576040517fb06307db00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060076000611ab361217e565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055508173ffffffffffffffffffffffffffffffffffffffff16611b6061217e565b73ffffffffffffffffffffffffffffffffffffffff167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c3183604051611ba591906141dc565b60405180910390a35050565b6000611bbb6128e2565b905090565b6000801b611bd581611bd0612331565b612339565b611bdd6128f5565b7f4a5f27b6a26c1d168b49c56a68ba4bb0aff57144387eb6bd10db8831e9cafdd960405160405180910390a150565b611c17848484610a58565b60008373ffffffffffffffffffffffffffffffffffffffff163b14611c7957611c4284848484612942565b611c78576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b50505050565b611c8761361f565b611c8f61361f565b611c97612186565b831080611cab5750611ca76128d9565b8310155b15611cb95780915050611ce4565b611cc28361268d565b9050806040015115611cd75780915050611ce4565b611ce083612aa2565b9150505b919050565b6060611cf48261211f565b611d2a576040517fa14c4b5000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000611d346125fb565b9050600081511415611d555760405180602001604052806000815250611d80565b80611d5f84612ac2565b604051602001611d709291906140aa565b6040516020818303038152906040525b915050919050565b6000611da5600b6000848152602001908152602001600020612b12565b9050919050565b7f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a681565b611dd982610d7d565b611dea81611de5612331565b612339565b611df4838361240a565b505050565b600d5481565b6000801b611e1481611e0f612331565b612339565b611e1e8383612b27565b8273ffffffffffffffffffffffffffffffffffffffff167f3e91409a02926290c65d2e6b1c28957f255d42cb904b947d566829981d0fc8f183604051611e649190614393565b60405180910390a2505050565b6000600760008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b611f0d610a41565b811015611f4f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611f4690614254565b60405180910390fd5b7f6a84334bf6663b783f2bbfcaf459b2cbc73570cf346a46d9e6a0f290fcf3ebfc600d5482604051611f8292919061436a565b60405180910390a180600d8190555050565b611f9e82826116d5565b612071576001600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff021916908315150217905550612016612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45b5050565b600061209d836000018373ffffffffffffffffffffffffffffffffffffffff1660001b612cbd565b905092915050565b60007f5a05180f000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff19161480612118575061211782612d2d565b5b9050919050565b60008161212a612186565b11158015612139575060005482105b8015612177575060007c0100000000000000000000000000000000000000000000000000000000600460008581526020019081526020016000205416145b9050919050565b600033905090565b60006001905090565b6000808290508061219e612186565b11612226576000548110156122255760006004600083815260200190815260200160002054905060007c010000000000000000000000000000000000000000000000000000000082161415612223575b60008114156122195760046000836001900393508381526020019081526020016000205490506121ee565b8092505050612258565b505b5b6040517fdf2d9b4200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b919050565b60008060006006600085815260200190815260200160002090508092508254915050915091565b600073ffffffffffffffffffffffffffffffffffffffff8316925073ffffffffffffffffffffffffffffffffffffffff821691508382148383141790509392505050565b50505050565b60008060e883901c905060e86122e5868684612da7565b62ffffff16901b9150509392505050565b600073ffffffffffffffffffffffffffffffffffffffff83169250814260a01b178317905092915050565b50505050565b6000612710905090565b600033905090565b61234382826116d5565b6123d2576123688173ffffffffffffffffffffffffffffffffffffffff166014612db0565b6123768360001c6020612db0565b6040516020016123879291906140ce565b6040516020818303038152906040526040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016123c99190614212565b60405180910390fd5b5050565b6123e08282611f94565b61240581600b600085815260200190815260200160002061207590919063ffffffff16565b505050565b61241482826130aa565b61243981600b600085815260200190815260200160002061318c90919063ffffffff16565b505050565b600080549050600082141561247f576040517fb562e8dd00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b61248c60008483856122c8565b600160406001901b178202600560008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008282540192505081905550612503836124f460008660006122ce565b6124fd856131bc565b176122f6565b6004600083815260200190815260200160002081905550600080838301905073ffffffffffffffffffffffffffffffffffffffff85169150828260007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600183015b8181146125a457808360007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600181019050612569565b5060008214156125e0576040517f2e07630000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060008190555050506125f66000848385612321565b505050565b6060600c805461260a906146f3565b80601f0160208091040260200160405190810160405280929190818152602001828054612636906146f3565b80156126835780601f1061265857610100808354040283529160200191612683565b820191906000526020600020905b81548152906001019060200180831161266657829003601f168201915b5050505050905090565b61269561361f565b6126b160046000848152602001908152602001600020546131cc565b9050919050565b6126c0612327565b6bffffffffffffffffffffffff16816bffffffffffffffffffffffff16111561271e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612715906142d4565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141561278e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612785906142b4565b60405180910390fd5b60405180604001604052808373ffffffffffffffffffffffffffffffffffffffff168152602001826bffffffffffffffffffffffff168152506009600085815260200190815260200160002060008201518160000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060208201518160000160146101000a8154816bffffffffffffffffffffffff02191690836bffffffffffffffffffffffff160217905550905050505050565b60096000828152602001908152602001600020600080820160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690556000820160146101000a8154906bffffffffffffffffffffffff0219169055505050565b60006128ce8360000183613282565b60001c905092915050565b60008054905090565b60006128ec612186565b60005403905090565b6008600080820160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690556000820160146101000a8154906bffffffffffffffffffffffff02191690555050565b60008373ffffffffffffffffffffffffffffffffffffffff1663150b7a0261296861217e565b8786866040518563ffffffff1660e01b815260040161298a9493929190614123565b602060405180830381600087803b1580156129a457600080fd5b505af19250505080156129d557506040513d601f19601f820116820180604052508101906129d29190613b5b565b60015b612a4f573d8060008114612a05576040519150601f19603f3d011682016040523d82523d6000602084013e612a0a565b606091505b50600081511415612a47576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805181602001fd5b63150b7a0260e01b7bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916817bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614915050949350505050565b612aaa61361f565b612abb612ab68361218f565b6131cc565b9050919050565b606060806040510190508060405280825b600115612afe57600183039250600a81066030018353600a8104905080612af957612afe565b612ad3565b508181036020830392508083525050919050565b6000612b20826000016132d3565b9050919050565b612b2f612327565b6bffffffffffffffffffffffff16816bffffffffffffffffffffffff161115612b8d576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612b84906142d4565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415612bfd576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612bf4906142f4565b60405180910390fd5b60405180604001604052808373ffffffffffffffffffffffffffffffffffffffff168152602001826bffffffffffffffffffffffff16815250600860008201518160000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060208201518160000160146101000a8154816bffffffffffffffffffffffff02191690836bffffffffffffffffffffffff1602179055509050505050565b6000612cc983836132e4565b612d22578260000182908060018154018082558091505060019003906000526020600020016000909190919091505582600001805490508360010160008481526020019081526020016000208190555060019050612d27565b600090505b92915050565b60007f7965db0b000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff19161480612da05750612d9f82613307565b5b9050919050565b60009392505050565b606060006002836002612dc39190614540565b612dcd91906144b9565b67ffffffffffffffff811115612e0c577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280601f01601f191660200182016040528015612e3e5781602001600182028036833780820191505090505b5090507f300000000000000000000000000000000000000000000000000000000000000081600081518110612e9c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053507f780000000000000000000000000000000000000000000000000000000000000081600181518110612f26577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a90535060006001846002612f669190614540565b612f7091906144b9565b90505b600181111561305c577f3031323334353637383961626364656600000000000000000000000000000000600f861660108110612fd8577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b1a60f81b828281518110613015577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a905350600485901c945080613055906146c9565b9050612f73565b50600084146130a0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161309790614234565b60405180910390fd5b8091505092915050565b6130b482826116d5565b15613188576000600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff02191690831515021790555061312d612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16837ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b60405160405180910390a45b5050565b60006131b4836000018373ffffffffffffffffffffffffffffffffffffffff1660001b613381565b905092915050565b60006001821460e11b9050919050565b6131d461361f565b81816000019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff168152505060a082901c816020019067ffffffffffffffff16908167ffffffffffffffff168152505060007c01000000000000000000000000000000000000000000000000000000008316141581604001901515908115158152505060e882901c816060019062ffffff16908162ffffff1681525050919050565b60008260000182815481106132c0577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200154905092915050565b600081600001805490509050919050565b600080836001016000848152602001908152602001600020541415905092915050565b60007f2a55205a000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916148061337a575061337982613507565b5b9050919050565b600080836001016000848152602001908152602001600020549050600081146134fb5760006001826133b3919061459a565b90506000600186600001805490506133cb919061459a565b9050818114613486576000866000018281548110613412577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b906000526020600020015490508087600001848154811061345c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90600052602060002001819055508387600101600083815260200190815260200160002081905550505b856000018054806134c0577f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fd5b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050613501565b60009150505b92915050565b60006301ffc9a760e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916148061356257506380ac58cd60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b806135925750635b5e139f60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b9050919050565b8280546135a5906146f3565b90600052602060002090601f0160209004810192826135c7576000855561360e565b82601f106135e057803560ff191683800117855561360e565b8280016001018555821561360e579182015b8281111561360d5782358255916020019190600101906135f2565b5b50905061361b919061366e565b5090565b6040518060800160405280600073ffffffffffffffffffffffffffffffffffffffff168152602001600067ffffffffffffffff168152602001600015158152602001600062ffffff1681525090565b5b8082111561368757600081600090555060010161366f565b5090565b600061369e613699846143d3565b6143ae565b9050828152602081018484840111156136b657600080fd5b6136c1848285614687565b509392505050565b6000813590506136d881614a09565b92915050565b60008083601f8401126136f057600080fd5b8235905067ffffffffffffffff81111561370957600080fd5b60208301915083602082028301111561372157600080fd5b9250929050565b60008135905061373781614a20565b92915050565b60008135905061374c81614a37565b92915050565b60008135905061376181614a4e565b92915050565b60008151905061377681614a4e565b92915050565b600082601f83011261378d57600080fd5b813561379d84826020860161368b565b91505092915050565b60008083601f8401126137b857600080fd5b8235905067ffffffffffffffff8111156137d157600080fd5b6020830191508360018202830111156137e957600080fd5b9250929050565b6000813590506137ff81614a65565b92915050565b60008135905061381481614a7c565b92915050565b60006020828403121561382c57600080fd5b600061383a848285016136c9565b91505092915050565b6000806040838503121561385657600080fd5b6000613864858286016136c9565b9250506020613875858286016136c9565b9150509250929050565b60008060006060848603121561389457600080fd5b60006138a2868287016136c9565b93505060206138b3868287016136c9565b92505060406138c4868287016137f0565b9150509250925092565b600080600080608085870312156138e457600080fd5b60006138f2878288016136c9565b9450506020613903878288016136c9565b9350506040613914878288016137f0565b925050606085013567ffffffffffffffff81111561393157600080fd5b61393d8782880161377c565b91505092959194509250565b6000806040838503121561395c57600080fd5b600061396a858286016136c9565b925050602061397b85828601613728565b9150509250929050565b6000806040838503121561399857600080fd5b60006139a6858286016136c9565b92505060206139b7858286016137f0565b9150509250929050565b6000806000606084860312156139d657600080fd5b60006139e4868287016136c9565b93505060206139f5868287016137f0565b9250506040613a06868287016137f0565b9150509250925092565b60008060408385031215613a2357600080fd5b6000613a31858286016136c9565b9250506020613a4285828601613805565b9150509250929050565b60008060208385031215613a5f57600080fd5b600083013567ffffffffffffffff811115613a7957600080fd5b613a85858286016136de565b92509250509250929050565b600060208284031215613aa357600080fd5b6000613ab18482850161373d565b91505092915050565b60008060408385031215613acd57600080fd5b6000613adb8582860161373d565b9250506020613aec858286016136c9565b9150509250929050565b60008060408385031215613b0957600080fd5b6000613b178582860161373d565b9250506020613b28858286016137f0565b9150509250929050565b600060208284031215613b4457600080fd5b6000613b5284828501613752565b91505092915050565b600060208284031215613b6d57600080fd5b6000613b7b84828501613767565b91505092915050565b60008060208385031215613b9757600080fd5b600083013567ffffffffffffffff811115613bb157600080fd5b613bbd858286016137a6565b92509250509250929050565b600060208284031215613bdb57600080fd5b6000613be9848285016137f0565b91505092915050565b600080600060608486031215613c0757600080fd5b6000613c15868287016137f0565b9350506020613c26868287016136c9565b9250506040613c3786828701613805565b9150509250925092565b60008060408385031215613c5457600080fd5b6000613c62858286016137f0565b9250506020613c73858286016137f0565b9150509250929050565b6000613c898383613fb5565b60808301905092915050565b6000613ca1838361406e565b60208301905092915050565b613cb6816145ce565b82525050565b613cc5816145ce565b82525050565b6000613cd682614424565b613ce0818561446a565b9350613ceb83614404565b8060005b83811015613d1c578151613d038882613c7d565b9750613d0e83614450565b925050600181019050613cef565b5085935050505092915050565b6000613d348261442f565b613d3e818561447b565b9350613d4983614414565b8060005b83811015613d7a578151613d618882613c95565b9750613d6c8361445d565b925050600181019050613d4d565b5085935050505092915050565b613d90816145e0565b82525050565b613d9f816145e0565b82525050565b613dae816145ec565b82525050565b6000613dbf8261443a565b613dc9818561448c565b9350613dd9818560208601614696565b613de281614812565b840191505092915050565b6000613df882614445565b613e02818561449d565b9350613e12818560208601614696565b613e1b81614812565b840191505092915050565b6000613e3182614445565b613e3b81856144ae565b9350613e4b818560208601614696565b80840191505092915050565b6000613e6460208361449d565b9150613e6f82614823565b602082019050919050565b6000613e8760118361449d565b9150613e928261484c565b602082019050919050565b6000613eaa60158361449d565b9150613eb582614875565b602082019050919050565b6000613ecd60128361449d565b9150613ed88261489e565b602082019050919050565b6000613ef0601b8361449d565b9150613efb826148c7565b602082019050919050565b6000613f136017836144ae565b9150613f1e826148f0565b601782019050919050565b6000613f36602a8361449d565b9150613f4182614919565b604082019050919050565b6000613f5960198361449d565b9150613f6482614968565b602082019050919050565b6000613f7c6011836144ae565b9150613f8782614991565b601182019050919050565b6000613f9f602f8361449d565b9150613faa826149ba565b604082019050919050565b608082016000820151613fcb6000850182613cad565b506020820151613fde602085018261408c565b506040820151613ff16040850182613d87565b506060820151614004606085018261405f565b50505050565b6080820160008201516140206000850182613cad565b506020820151614033602085018261408c565b5060408201516140466040850182613d87565b506060820151614059606085018261405f565b50505050565b61406881614642565b82525050565b61407781614651565b82525050565b61408681614651565b82525050565b6140958161465b565b82525050565b6140a48161466f565b82525050565b60006140b68285613e26565b91506140c28284613e26565b91508190509392505050565b60006140d982613f06565b91506140e58285613e26565b91506140f082613f6f565b91506140fc8284613e26565b91508190509392505050565b600060208201905061411d6000830184613cbc565b92915050565b60006080820190506141386000830187613cbc565b6141456020830186613cbc565b614152604083018561407d565b81810360608301526141648184613db4565b905095945050505050565b60006040820190506141846000830185613cbc565b614191602083018461407d565b9392505050565b600060208201905081810360008301526141b28184613ccb565b905092915050565b600060208201905081810360008301526141d48184613d29565b905092915050565b60006020820190506141f16000830184613d96565b92915050565b600060208201905061420c6000830184613da5565b92915050565b6000602082019050818103600083015261422c8184613ded565b905092915050565b6000602082019050818103600083015261424d81613e57565b9050919050565b6000602082019050818103600083015261426d81613e7a565b9050919050565b6000602082019050818103600083015261428d81613e9d565b9050919050565b600060208201905081810360008301526142ad81613ec0565b9050919050565b600060208201905081810360008301526142cd81613ee3565b9050919050565b600060208201905081810360008301526142ed81613f29565b9050919050565b6000602082019050818103600083015261430d81613f4c565b9050919050565b6000602082019050818103600083015261432d81613f92565b9050919050565b6000608082019050614349600083018461400a565b92915050565b6000602082019050614364600083018461407d565b92915050565b600060408201905061437f600083018561407d565b61438c602083018461407d565b9392505050565b60006020820190506143a8600083018461409b565b92915050565b60006143b86143c9565b90506143c48282614725565b919050565b6000604051905090565b600067ffffffffffffffff8211156143ee576143ed6147e3565b5b6143f782614812565b9050602081019050919050565b6000819050602082019050919050565b6000819050602082019050919050565b600081519050919050565b600081519050919050565b600081519050919050565b600081519050919050565b6000602082019050919050565b6000602082019050919050565b600082825260208201905092915050565b600082825260208201905092915050565b600082825260208201905092915050565b600082825260208201905092915050565b600081905092915050565b60006144c482614651565b91506144cf83614651565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561450457614503614756565b5b828201905092915050565b600061451a82614651565b915061452583614651565b92508261453557614534614785565b5b828204905092915050565b600061454b82614651565b915061455683614651565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff048311821515161561458f5761458e614756565b5b828202905092915050565b60006145a582614651565b91506145b083614651565b9250828210156145c3576145c2614756565b5b828203905092915050565b60006145d982614622565b9050919050565b60008115159050919050565b6000819050919050565b60007fffffffff0000000000000000000000000000000000000000000000000000000082169050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b600062ffffff82169050919050565b6000819050919050565b600067ffffffffffffffff82169050919050565b60006bffffffffffffffffffffffff82169050919050565b82818337600083830152505050565b60005b838110156146b4578082015181840152602081019050614699565b838111156146c3576000848401525b50505050565b60006146d482614651565b915060008214156146e8576146e7614756565b5b600182039050919050565b6000600282049050600182168061470b57607f821691505b6020821081141561471f5761471e6147b4565b5b50919050565b61472e82614812565b810181811067ffffffffffffffff8211171561474d5761474c6147e3565b5b80604052505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6000601f19601f8301169050919050565b7f537472696e67733a20686578206c656e67746820696e73756666696369656e74600082015250565b7f696e76616c6964206d6178537570706c79000000000000000000000000000000600082015250565b7f6e6f207065726d697373696f6e20746f2063616c6c0000000000000000000000600082015250565b7f6d617820737570706c7920726561636865640000000000000000000000000000600082015250565b7f455243323938313a20496e76616c696420706172616d65746572730000000000600082015250565b7f416363657373436f6e74726f6c3a206163636f756e7420000000000000000000600082015250565b7f455243323938313a20726f79616c7479206665652077696c6c2065786365656460008201527f2073616c65507269636500000000000000000000000000000000000000000000602082015250565b7f455243323938313a20696e76616c696420726563656976657200000000000000600082015250565b7f206973206d697373696e6720726f6c6520000000000000000000000000000000600082015250565b7f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560008201527f20726f6c657320666f722073656c660000000000000000000000000000000000602082015250565b614a12816145ce565b8114614a1d57600080fd5b50565b614a29816145e0565b8114614a3457600080fd5b50565b614a40816145ec565b8114614a4b57600080fd5b50565b614a57816145f6565b8114614a6257600080fd5b50565b614a6e81614651565b8114614a7957600080fd5b50565b614a858161466f565b8114614a9057600080fd5b5056fea26469706673582212207c755d20770f722879594472df615ea301b913f4ff5e739aa17e030bf0789cca64736f6c6343000804003300000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002710000000000000000000000000083bbe83c1b91e1caeaf277335bd1a82f593d8430000000000000000000000005607ee6014b0ecdb649216bc93dbbe687143a85400000000000000000000000000000000000000000000000000000000000001f400000000000000000000000000000000000000000000000000000000000000114d61746368205265616479204c696f6e7300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000114d61746368205265616479204c696f6e73000000000000000000000000000000
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106102485760003560e01c806386e228d51161013b578063b88d4fde116100b8578063d547741f1161007c578063d547741f14610738578063d5abeb0114610754578063daa83c6d14610772578063e985e9c51461078e578063f103b433146107be57610248565b8063b88d4fde1461066e578063c23dc68f1461068a578063c87b56dd146106ba578063ca15c873146106ea578063d53913931461071a57610248565b806399a2557a116100ff57806399a2557a146105dc578063a217fddf1461060c578063a22cb4651461062a578063a2309ff814610646578063aa1b103f1461066457610248565b806386e228d5146105265780638a616bc0146105425780639010d07c1461055e57806391d148541461058e57806395d89b41146105be57610248565b80633e0e828b116101c95780635bbb21771161018d5780635bbb2177146104485780636352211e146104785780636c0360eb146104a857806370a08231146104c65780638462151c146104f657610248565b80633e0e828b146103ba57806340d097c3146103d857806342842e0e146103f457806343508b051461041057806355f804b31461042c57610248565b806323b872dd1161021057806323b872dd14610305578063248a9ca3146103215780632a55205a146103515780632f2ff15d1461038257806336568abe1461039e57610248565b806301ffc9a71461024d57806306fdde031461027d578063081812fc1461029b578063095ea7b3146102cb57806318160ddd146102e7575b600080fd5b61026760048036038101906102629190613b32565b6107da565b60405161027491906141dc565b60405180910390f35b6102856107ec565b6040516102929190614212565b60405180910390f35b6102b560048036038101906102b09190613bc9565b61087e565b6040516102c29190614108565b60405180910390f35b6102e560048036038101906102e09190613985565b6108fd565b005b6102ef610a41565b6040516102fc919061434f565b60405180910390f35b61031f600480360381019061031a919061387f565b610a58565b005b61033b60048036038101906103369190613a91565b610d7d565b60405161034891906141f7565b60405180910390f35b61036b60048036038101906103669190613c41565b610d9d565b60405161037992919061416f565b60405180910390f35b61039c60048036038101906103979190613aba565b610f88565b005b6103b860048036038101906103b39190613aba565b610fb1565b005b6103c2611034565b6040516103cf919061434f565b60405180910390f35b6103f260048036038101906103ed919061381a565b611039565b005b61040e6004803603810190610409919061387f565b61110f565b005b61042a60048036038101906104259190613985565b61112f565b005b61044660048036038101906104419190613b84565b611211565b005b610462600480360381019061045d9190613a4c565b61123d565b60405161046f9190614198565b60405180910390f35b610492600480360381019061048d9190613bc9565b611372565b60405161049f9190614108565b60405180910390f35b6104b0611384565b6040516104bd9190614212565b60405180910390f35b6104e060048036038101906104db919061381a565b611393565b6040516104ed919061434f565b60405180910390f35b610510600480360381019061050b919061381a565b61144c565b60405161051d91906141ba565b60405180910390f35b610540600480360381019061053b9190613bf2565b6115e2565b005b61055c60048036038101906105579190613bc9565b611657565b005b61057860048036038101906105739190613af6565b6116a6565b6040516105859190614108565b60405180910390f35b6105a860048036038101906105a39190613aba565b6116d5565b6040516105b591906141dc565b60405180910390f35b6105c6611740565b6040516105d39190614212565b60405180910390f35b6105f660048036038101906105f191906139c1565b6117d2565b60405161060391906141ba565b60405180910390f35b610614611a32565b60405161062191906141f7565b60405180910390f35b610644600480360381019061063f9190613949565b611a39565b005b61064e611bb1565b60405161065b919061434f565b60405180910390f35b61066c611bc0565b005b610688600480360381019061068391906138ce565b611c0c565b005b6106a4600480360381019061069f9190613bc9565b611c7f565b6040516106b19190614334565b60405180910390f35b6106d460048036038101906106cf9190613bc9565b611ce9565b6040516106e19190614212565b60405180910390f35b61070460048036038101906106ff9190613a91565b611d88565b604051610711919061434f565b60405180910390f35b610722611dac565b60405161072f91906141f7565b60405180910390f35b610752600480360381019061074d9190613aba565b611dd0565b005b61075c611df9565b604051610769919061434f565b60405180910390f35b61078c60048036038101906107879190613a10565b611dff565b005b6107a860048036038101906107a39190613843565b611e71565b6040516107b591906141dc565b60405180910390f35b6107d860048036038101906107d39190613bc9565b611f05565b005b60006107e5826120a5565b9050919050565b6060600280546107fb906146f3565b80601f0160208091040260200160405190810160405280929190818152602001828054610827906146f3565b80156108745780601f1061084957610100808354040283529160200191610874565b820191906000526020600020905b81548152906001019060200180831161085757829003601f168201915b5050505050905090565b60006108898261211f565b6108bf576040517fcf4700e400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6006600083815260200190815260200160002060000160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff169050919050565b600061090882611372565b90508073ffffffffffffffffffffffffffffffffffffffff1661092961217e565b73ffffffffffffffffffffffffffffffffffffffff161461098c576109558161095061217e565b611e71565b61098b576040517fcfb3b94200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b826006600084815260200190815260200160002060000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550818373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a4505050565b6000610a4b612186565b6001546000540303905090565b6000610a638261218f565b90508373ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614610aca576040517fa114810000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b600080610ad68461225d565b91509150610aec8187610ae761217e565b612284565b610b3857610b0186610afc61217e565b611e71565b610b37576040517f59c896be00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415610b9f576040517fea553b3400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610bac86868660016122c8565b8015610bb757600082555b600560008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600081546001900391905081905550600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000815460010191905081905550610c8585610c618888876122ce565b7c0200000000000000000000000000000000000000000000000000000000176122f6565b600460008681526020019081526020016000208190555060007c020000000000000000000000000000000000000000000000000000000084161415610d0d576000600185019050600060046000838152602001908152602001600020541415610d0b576000548114610d0a578360046000838152602001908152602001600020819055505b5b505b838573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4610d758686866001612321565b505050505050565b6000600a6000838152602001908152602001600020600101549050919050565b6000806000600960008681526020019081526020016000206040518060400160405290816000820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020016000820160149054906101000a90046bffffffffffffffffffffffff166bffffffffffffffffffffffff166bffffffffffffffffffffffff16815250509050600073ffffffffffffffffffffffffffffffffffffffff16816000015173ffffffffffffffffffffffffffffffffffffffff161415610f335760086040518060400160405290816000820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020016000820160149054906101000a90046bffffffffffffffffffffffff166bffffffffffffffffffffffff166bffffffffffffffffffffffff168152505090505b6000610f3d612327565b6bffffffffffffffffffffffff1682602001516bffffffffffffffffffffffff1686610f699190614540565b610f73919061450f565b90508160000151819350935050509250929050565b610f9182610d7d565b610fa281610f9d612331565b612339565b610fac83836123d6565b505050565b610fb9612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614611026576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161101d90614314565b60405180910390fd5b611030828261240a565b5050565b600181565b6110466000801b336116d5565b8061107757506110767f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6336116d5565b5b6110b6576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016110ad90614274565b60405180910390fd5b600d546110c1610a41565b10611101576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016110f890614294565b60405180910390fd5b61110c81600161243e565b50565b61112a83838360405180602001604052806000815250611c0c565b505050565b61113c6000801b336116d5565b8061116d575061116c7f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a6336116d5565b5b6111ac576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016111a390614274565b60405180910390fd5b600d54816111b8610a41565b6111c291906144b9565b1115611203576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016111fa90614294565b60405180910390fd5b61120d828261243e565b5050565b6000801b61122681611221612331565b612339565b8282600c9190611237929190613599565b50505050565b6060600083839050905060008167ffffffffffffffff811115611289577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156112c257816020015b6112af61361f565b8152602001906001900390816112a75790505b50905060005b8281146113665761131786868381811061130b577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90506020020135611c7f565b828281518110611350577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200260200101819052508060010190506112c8565b50809250505092915050565b600061137d8261218f565b9050919050565b606061138e6125fb565b905090565b60008073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614156113fb576040517f8f4eb60400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b67ffffffffffffffff600560008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054169050919050565b6060600080600061145c85611393565b905060008167ffffffffffffffff8111156114a0577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156114ce5781602001602082028036833780820191505090505b5090506114d961361f565b60006114e3612186565b90505b8386146115d4576114f68161268d565b9150816040015115611507576115c9565b600073ffffffffffffffffffffffffffffffffffffffff16826000015173ffffffffffffffffffffffffffffffffffffffff161461154757816000015194505b8773ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff1614156115c857808387806001019850815181106115bb577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b6020026020010181815250505b5b8060010190506114e6565b508195505050505050919050565b6000801b6115f7816115f2612331565b612339565b6116028484846126b8565b8273ffffffffffffffffffffffffffffffffffffffff16847f8219bae90c1815288c07ea441a930eb14c911bcee209d79219ff8098e9b243a2846040516116499190614393565b60405180910390a350505050565b6000801b61166c81611667612331565b612339565b61167582612860565b817f2d0c64cb223c165096aa5260f0c4f12caf09469f917f6139ff17e1795a01225d60405160405180910390a25050565b60006116cd82600b60008681526020019081526020016000206128bf90919063ffffffff16565b905092915050565b6000600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b60606003805461174f906146f3565b80601f016020809104026020016040519081016040528092919081815260200182805461177b906146f3565b80156117c85780601f1061179d576101008083540402835291602001916117c8565b820191906000526020600020905b8154815290600101906020018083116117ab57829003601f168201915b5050505050905090565b606081831061180d576040517f32c1995a00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000806118186128d9565b9050611822612186565b85101561183457611831612186565b94505b80841115611840578093505b600061184b87611393565b90508486101561186e576000868603905081811015611868578091505b50611873565b600090505b60008167ffffffffffffffff8111156118b5577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280602002602001820160405280156118e35781602001602082028036833780820191505090505b50905060008214156118fb5780945050505050611a2b565b600061190688611c7f565b90506000816040015161191b57816000015190505b60008990505b8881141580156119315750848714155b15611a1d5761193f8161268d565b925082604001511561195057611a12565b600073ffffffffffffffffffffffffffffffffffffffff16836000015173ffffffffffffffffffffffffffffffffffffffff161461199057826000015191505b8a73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611a115780848880600101995081518110611a04577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b6020026020010181815250505b5b806001019050611921565b508583528296505050505050505b9392505050565b6000801b81565b611a4161217e565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611aa6576040517fb06307db00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060076000611ab361217e565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055508173ffffffffffffffffffffffffffffffffffffffff16611b6061217e565b73ffffffffffffffffffffffffffffffffffffffff167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c3183604051611ba591906141dc565b60405180910390a35050565b6000611bbb6128e2565b905090565b6000801b611bd581611bd0612331565b612339565b611bdd6128f5565b7f4a5f27b6a26c1d168b49c56a68ba4bb0aff57144387eb6bd10db8831e9cafdd960405160405180910390a150565b611c17848484610a58565b60008373ffffffffffffffffffffffffffffffffffffffff163b14611c7957611c4284848484612942565b611c78576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b50505050565b611c8761361f565b611c8f61361f565b611c97612186565b831080611cab5750611ca76128d9565b8310155b15611cb95780915050611ce4565b611cc28361268d565b9050806040015115611cd75780915050611ce4565b611ce083612aa2565b9150505b919050565b6060611cf48261211f565b611d2a576040517fa14c4b5000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000611d346125fb565b9050600081511415611d555760405180602001604052806000815250611d80565b80611d5f84612ac2565b604051602001611d709291906140aa565b6040516020818303038152906040525b915050919050565b6000611da5600b6000848152602001908152602001600020612b12565b9050919050565b7f9f2df0fed2c77648de5860a4cc508cd0818c85b8b8a1ab4ceeef8d981c8956a681565b611dd982610d7d565b611dea81611de5612331565b612339565b611df4838361240a565b505050565b600d5481565b6000801b611e1481611e0f612331565b612339565b611e1e8383612b27565b8273ffffffffffffffffffffffffffffffffffffffff167f3e91409a02926290c65d2e6b1c28957f255d42cb904b947d566829981d0fc8f183604051611e649190614393565b60405180910390a2505050565b6000600760008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b611f0d610a41565b811015611f4f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611f4690614254565b60405180910390fd5b7f6a84334bf6663b783f2bbfcaf459b2cbc73570cf346a46d9e6a0f290fcf3ebfc600d5482604051611f8292919061436a565b60405180910390a180600d8190555050565b611f9e82826116d5565b612071576001600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff021916908315150217905550612016612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45b5050565b600061209d836000018373ffffffffffffffffffffffffffffffffffffffff1660001b612cbd565b905092915050565b60007f5a05180f000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff19161480612118575061211782612d2d565b5b9050919050565b60008161212a612186565b11158015612139575060005482105b8015612177575060007c0100000000000000000000000000000000000000000000000000000000600460008581526020019081526020016000205416145b9050919050565b600033905090565b60006001905090565b6000808290508061219e612186565b11612226576000548110156122255760006004600083815260200190815260200160002054905060007c010000000000000000000000000000000000000000000000000000000082161415612223575b60008114156122195760046000836001900393508381526020019081526020016000205490506121ee565b8092505050612258565b505b5b6040517fdf2d9b4200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b919050565b60008060006006600085815260200190815260200160002090508092508254915050915091565b600073ffffffffffffffffffffffffffffffffffffffff8316925073ffffffffffffffffffffffffffffffffffffffff821691508382148383141790509392505050565b50505050565b60008060e883901c905060e86122e5868684612da7565b62ffffff16901b9150509392505050565b600073ffffffffffffffffffffffffffffffffffffffff83169250814260a01b178317905092915050565b50505050565b6000612710905090565b600033905090565b61234382826116d5565b6123d2576123688173ffffffffffffffffffffffffffffffffffffffff166014612db0565b6123768360001c6020612db0565b6040516020016123879291906140ce565b6040516020818303038152906040526040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016123c99190614212565b60405180910390fd5b5050565b6123e08282611f94565b61240581600b600085815260200190815260200160002061207590919063ffffffff16565b505050565b61241482826130aa565b61243981600b600085815260200190815260200160002061318c90919063ffffffff16565b505050565b600080549050600082141561247f576040517fb562e8dd00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b61248c60008483856122c8565b600160406001901b178202600560008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008282540192505081905550612503836124f460008660006122ce565b6124fd856131bc565b176122f6565b6004600083815260200190815260200160002081905550600080838301905073ffffffffffffffffffffffffffffffffffffffff85169150828260007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600183015b8181146125a457808360007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600181019050612569565b5060008214156125e0576040517f2e07630000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060008190555050506125f66000848385612321565b505050565b6060600c805461260a906146f3565b80601f0160208091040260200160405190810160405280929190818152602001828054612636906146f3565b80156126835780601f1061265857610100808354040283529160200191612683565b820191906000526020600020905b81548152906001019060200180831161266657829003601f168201915b5050505050905090565b61269561361f565b6126b160046000848152602001908152602001600020546131cc565b9050919050565b6126c0612327565b6bffffffffffffffffffffffff16816bffffffffffffffffffffffff16111561271e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612715906142d4565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141561278e576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612785906142b4565b60405180910390fd5b60405180604001604052808373ffffffffffffffffffffffffffffffffffffffff168152602001826bffffffffffffffffffffffff168152506009600085815260200190815260200160002060008201518160000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060208201518160000160146101000a8154816bffffffffffffffffffffffff02191690836bffffffffffffffffffffffff160217905550905050505050565b60096000828152602001908152602001600020600080820160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690556000820160146101000a8154906bffffffffffffffffffffffff0219169055505050565b60006128ce8360000183613282565b60001c905092915050565b60008054905090565b60006128ec612186565b60005403905090565b6008600080820160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690556000820160146101000a8154906bffffffffffffffffffffffff02191690555050565b60008373ffffffffffffffffffffffffffffffffffffffff1663150b7a0261296861217e565b8786866040518563ffffffff1660e01b815260040161298a9493929190614123565b602060405180830381600087803b1580156129a457600080fd5b505af19250505080156129d557506040513d601f19601f820116820180604052508101906129d29190613b5b565b60015b612a4f573d8060008114612a05576040519150601f19603f3d011682016040523d82523d6000602084013e612a0a565b606091505b50600081511415612a47576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805181602001fd5b63150b7a0260e01b7bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916817bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614915050949350505050565b612aaa61361f565b612abb612ab68361218f565b6131cc565b9050919050565b606060806040510190508060405280825b600115612afe57600183039250600a81066030018353600a8104905080612af957612afe565b612ad3565b508181036020830392508083525050919050565b6000612b20826000016132d3565b9050919050565b612b2f612327565b6bffffffffffffffffffffffff16816bffffffffffffffffffffffff161115612b8d576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612b84906142d4565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415612bfd576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612bf4906142f4565b60405180910390fd5b60405180604001604052808373ffffffffffffffffffffffffffffffffffffffff168152602001826bffffffffffffffffffffffff16815250600860008201518160000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060208201518160000160146101000a8154816bffffffffffffffffffffffff02191690836bffffffffffffffffffffffff1602179055509050505050565b6000612cc983836132e4565b612d22578260000182908060018154018082558091505060019003906000526020600020016000909190919091505582600001805490508360010160008481526020019081526020016000208190555060019050612d27565b600090505b92915050565b60007f7965db0b000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff19161480612da05750612d9f82613307565b5b9050919050565b60009392505050565b606060006002836002612dc39190614540565b612dcd91906144b9565b67ffffffffffffffff811115612e0c577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6040519080825280601f01601f191660200182016040528015612e3e5781602001600182028036833780820191505090505b5090507f300000000000000000000000000000000000000000000000000000000000000081600081518110612e9c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053507f780000000000000000000000000000000000000000000000000000000000000081600181518110612f26577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a90535060006001846002612f669190614540565b612f7091906144b9565b90505b600181111561305c577f3031323334353637383961626364656600000000000000000000000000000000600f861660108110612fd8577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b1a60f81b828281518110613015577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a905350600485901c945080613055906146c9565b9050612f73565b50600084146130a0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161309790614234565b60405180910390fd5b8091505092915050565b6130b482826116d5565b15613188576000600a600084815260200190815260200160002060000160008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff02191690831515021790555061312d612331565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff16837ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b60405160405180910390a45b5050565b60006131b4836000018373ffffffffffffffffffffffffffffffffffffffff1660001b613381565b905092915050565b60006001821460e11b9050919050565b6131d461361f565b81816000019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff168152505060a082901c816020019067ffffffffffffffff16908167ffffffffffffffff168152505060007c01000000000000000000000000000000000000000000000000000000008316141581604001901515908115158152505060e882901c816060019062ffffff16908162ffffff1681525050919050565b60008260000182815481106132c0577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200154905092915050565b600081600001805490509050919050565b600080836001016000848152602001908152602001600020541415905092915050565b60007f2a55205a000000000000000000000000000000000000000000000000000000007bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916148061337a575061337982613507565b5b9050919050565b600080836001016000848152602001908152602001600020549050600081146134fb5760006001826133b3919061459a565b90506000600186600001805490506133cb919061459a565b9050818114613486576000866000018281548110613412577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b906000526020600020015490508087600001848154811061345c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90600052602060002001819055508387600101600083815260200190815260200160002081905550505b856000018054806134c0577f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fd5b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050613501565b60009150505b92915050565b60006301ffc9a760e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916148061356257506380ac58cd60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b806135925750635b5e139f60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b9050919050565b8280546135a5906146f3565b90600052602060002090601f0160209004810192826135c7576000855561360e565b82601f106135e057803560ff191683800117855561360e565b8280016001018555821561360e579182015b8281111561360d5782358255916020019190600101906135f2565b5b50905061361b919061366e565b5090565b6040518060800160405280600073ffffffffffffffffffffffffffffffffffffffff168152602001600067ffffffffffffffff168152602001600015158152602001600062ffffff1681525090565b5b8082111561368757600081600090555060010161366f565b5090565b600061369e613699846143d3565b6143ae565b9050828152602081018484840111156136b657600080fd5b6136c1848285614687565b509392505050565b6000813590506136d881614a09565b92915050565b60008083601f8401126136f057600080fd5b8235905067ffffffffffffffff81111561370957600080fd5b60208301915083602082028301111561372157600080fd5b9250929050565b60008135905061373781614a20565b92915050565b60008135905061374c81614a37565b92915050565b60008135905061376181614a4e565b92915050565b60008151905061377681614a4e565b92915050565b600082601f83011261378d57600080fd5b813561379d84826020860161368b565b91505092915050565b60008083601f8401126137b857600080fd5b8235905067ffffffffffffffff8111156137d157600080fd5b6020830191508360018202830111156137e957600080fd5b9250929050565b6000813590506137ff81614a65565b92915050565b60008135905061381481614a7c565b92915050565b60006020828403121561382c57600080fd5b600061383a848285016136c9565b91505092915050565b6000806040838503121561385657600080fd5b6000613864858286016136c9565b9250506020613875858286016136c9565b9150509250929050565b60008060006060848603121561389457600080fd5b60006138a2868287016136c9565b93505060206138b3868287016136c9565b92505060406138c4868287016137f0565b9150509250925092565b600080600080608085870312156138e457600080fd5b60006138f2878288016136c9565b9450506020613903878288016136c9565b9350506040613914878288016137f0565b925050606085013567ffffffffffffffff81111561393157600080fd5b61393d8782880161377c565b91505092959194509250565b6000806040838503121561395c57600080fd5b600061396a858286016136c9565b925050602061397b85828601613728565b9150509250929050565b6000806040838503121561399857600080fd5b60006139a6858286016136c9565b92505060206139b7858286016137f0565b9150509250929050565b6000806000606084860312156139d657600080fd5b60006139e4868287016136c9565b93505060206139f5868287016137f0565b9250506040613a06868287016137f0565b9150509250925092565b60008060408385031215613a2357600080fd5b6000613a31858286016136c9565b9250506020613a4285828601613805565b9150509250929050565b60008060208385031215613a5f57600080fd5b600083013567ffffffffffffffff811115613a7957600080fd5b613a85858286016136de565b92509250509250929050565b600060208284031215613aa357600080fd5b6000613ab18482850161373d565b91505092915050565b60008060408385031215613acd57600080fd5b6000613adb8582860161373d565b9250506020613aec858286016136c9565b9150509250929050565b60008060408385031215613b0957600080fd5b6000613b178582860161373d565b9250506020613b28858286016137f0565b9150509250929050565b600060208284031215613b4457600080fd5b6000613b5284828501613752565b91505092915050565b600060208284031215613b6d57600080fd5b6000613b7b84828501613767565b91505092915050565b60008060208385031215613b9757600080fd5b600083013567ffffffffffffffff811115613bb157600080fd5b613bbd858286016137a6565b92509250509250929050565b600060208284031215613bdb57600080fd5b6000613be9848285016137f0565b91505092915050565b600080600060608486031215613c0757600080fd5b6000613c15868287016137f0565b9350506020613c26868287016136c9565b9250506040613c3786828701613805565b9150509250925092565b60008060408385031215613c5457600080fd5b6000613c62858286016137f0565b9250506020613c73858286016137f0565b9150509250929050565b6000613c898383613fb5565b60808301905092915050565b6000613ca1838361406e565b60208301905092915050565b613cb6816145ce565b82525050565b613cc5816145ce565b82525050565b6000613cd682614424565b613ce0818561446a565b9350613ceb83614404565b8060005b83811015613d1c578151613d038882613c7d565b9750613d0e83614450565b925050600181019050613cef565b5085935050505092915050565b6000613d348261442f565b613d3e818561447b565b9350613d4983614414565b8060005b83811015613d7a578151613d618882613c95565b9750613d6c8361445d565b925050600181019050613d4d565b5085935050505092915050565b613d90816145e0565b82525050565b613d9f816145e0565b82525050565b613dae816145ec565b82525050565b6000613dbf8261443a565b613dc9818561448c565b9350613dd9818560208601614696565b613de281614812565b840191505092915050565b6000613df882614445565b613e02818561449d565b9350613e12818560208601614696565b613e1b81614812565b840191505092915050565b6000613e3182614445565b613e3b81856144ae565b9350613e4b818560208601614696565b80840191505092915050565b6000613e6460208361449d565b9150613e6f82614823565b602082019050919050565b6000613e8760118361449d565b9150613e928261484c565b602082019050919050565b6000613eaa60158361449d565b9150613eb582614875565b602082019050919050565b6000613ecd60128361449d565b9150613ed88261489e565b602082019050919050565b6000613ef0601b8361449d565b9150613efb826148c7565b602082019050919050565b6000613f136017836144ae565b9150613f1e826148f0565b601782019050919050565b6000613f36602a8361449d565b9150613f4182614919565b604082019050919050565b6000613f5960198361449d565b9150613f6482614968565b602082019050919050565b6000613f7c6011836144ae565b9150613f8782614991565b601182019050919050565b6000613f9f602f8361449d565b9150613faa826149ba565b604082019050919050565b608082016000820151613fcb6000850182613cad565b506020820151613fde602085018261408c565b506040820151613ff16040850182613d87565b506060820151614004606085018261405f565b50505050565b6080820160008201516140206000850182613cad565b506020820151614033602085018261408c565b5060408201516140466040850182613d87565b506060820151614059606085018261405f565b50505050565b61406881614642565b82525050565b61407781614651565b82525050565b61408681614651565b82525050565b6140958161465b565b82525050565b6140a48161466f565b82525050565b60006140b68285613e26565b91506140c28284613e26565b91508190509392505050565b60006140d982613f06565b91506140e58285613e26565b91506140f082613f6f565b91506140fc8284613e26565b91508190509392505050565b600060208201905061411d6000830184613cbc565b92915050565b60006080820190506141386000830187613cbc565b6141456020830186613cbc565b614152604083018561407d565b81810360608301526141648184613db4565b905095945050505050565b60006040820190506141846000830185613cbc565b614191602083018461407d565b9392505050565b600060208201905081810360008301526141b28184613ccb565b905092915050565b600060208201905081810360008301526141d48184613d29565b905092915050565b60006020820190506141f16000830184613d96565b92915050565b600060208201905061420c6000830184613da5565b92915050565b6000602082019050818103600083015261422c8184613ded565b905092915050565b6000602082019050818103600083015261424d81613e57565b9050919050565b6000602082019050818103600083015261426d81613e7a565b9050919050565b6000602082019050818103600083015261428d81613e9d565b9050919050565b600060208201905081810360008301526142ad81613ec0565b9050919050565b600060208201905081810360008301526142cd81613ee3565b9050919050565b600060208201905081810360008301526142ed81613f29565b9050919050565b6000602082019050818103600083015261430d81613f4c565b9050919050565b6000602082019050818103600083015261432d81613f92565b9050919050565b6000608082019050614349600083018461400a565b92915050565b6000602082019050614364600083018461407d565b92915050565b600060408201905061437f600083018561407d565b61438c602083018461407d565b9392505050565b60006020820190506143a8600083018461409b565b92915050565b60006143b86143c9565b90506143c48282614725565b919050565b6000604051905090565b600067ffffffffffffffff8211156143ee576143ed6147e3565b5b6143f782614812565b9050602081019050919050565b6000819050602082019050919050565b6000819050602082019050919050565b600081519050919050565b600081519050919050565b600081519050919050565b600081519050919050565b6000602082019050919050565b6000602082019050919050565b600082825260208201905092915050565b600082825260208201905092915050565b600082825260208201905092915050565b600082825260208201905092915050565b600081905092915050565b60006144c482614651565b91506144cf83614651565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561450457614503614756565b5b828201905092915050565b600061451a82614651565b915061452583614651565b92508261453557614534614785565b5b828204905092915050565b600061454b82614651565b915061455683614651565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff048311821515161561458f5761458e614756565b5b828202905092915050565b60006145a582614651565b91506145b083614651565b9250828210156145c3576145c2614756565b5b828203905092915050565b60006145d982614622565b9050919050565b60008115159050919050565b6000819050919050565b60007fffffffff0000000000000000000000000000000000000000000000000000000082169050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b600062ffffff82169050919050565b6000819050919050565b600067ffffffffffffffff82169050919050565b60006bffffffffffffffffffffffff82169050919050565b82818337600083830152505050565b60005b838110156146b4578082015181840152602081019050614699565b838111156146c3576000848401525b50505050565b60006146d482614651565b915060008214156146e8576146e7614756565b5b600182039050919050565b6000600282049050600182168061470b57607f821691505b6020821081141561471f5761471e6147b4565b5b50919050565b61472e82614812565b810181811067ffffffffffffffff8211171561474d5761474c6147e3565b5b80604052505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6000601f19601f8301169050919050565b7f537472696e67733a20686578206c656e67746820696e73756666696369656e74600082015250565b7f696e76616c6964206d6178537570706c79000000000000000000000000000000600082015250565b7f6e6f207065726d697373696f6e20746f2063616c6c0000000000000000000000600082015250565b7f6d617820737570706c7920726561636865640000000000000000000000000000600082015250565b7f455243323938313a20496e76616c696420706172616d65746572730000000000600082015250565b7f416363657373436f6e74726f6c3a206163636f756e7420000000000000000000600082015250565b7f455243323938313a20726f79616c7479206665652077696c6c2065786365656460008201527f2073616c65507269636500000000000000000000000000000000000000000000602082015250565b7f455243323938313a20696e76616c696420726563656976657200000000000000600082015250565b7f206973206d697373696e6720726f6c6520000000000000000000000000000000600082015250565b7f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560008201527f20726f6c657320666f722073656c660000000000000000000000000000000000602082015250565b614a12816145ce565b8114614a1d57600080fd5b50565b614a29816145e0565b8114614a3457600080fd5b50565b614a40816145ec565b8114614a4b57600080fd5b50565b614a57816145f6565b8114614a6257600080fd5b50565b614a6e81614651565b8114614a7957600080fd5b50565b614a858161466f565b8114614a9057600080fd5b5056fea26469706673582212207c755d20770f722879594472df615ea301b913f4ff5e739aa17e030bf0789cca64736f6c63430008040033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
00000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002710000000000000000000000000083bbe83c1b91e1caeaf277335bd1a82f593d8430000000000000000000000005607ee6014b0ecdb649216bc93dbbe687143a85400000000000000000000000000000000000000000000000000000000000001f400000000000000000000000000000000000000000000000000000000000000114d61746368205265616479204c696f6e7300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000114d61746368205265616479204c696f6e73000000000000000000000000000000
-----Decoded View---------------
Arg [0] : name_ (string): Match Ready Lions
Arg [1] : symbol_ (string): Match Ready Lions
Arg [2] : _maxSupply (uint256): 10000
Arg [3] : _minter (address): 0x083Bbe83c1b91E1CaEaF277335bd1A82F593d843
Arg [4] : _royaltyReceiver (address): 0x5607eE6014b0ecDB649216BC93dbbE687143A854
Arg [5] : _royaltyFee (uint96): 500
-----Encoded View---------------
10 Constructor Arguments found :
Arg [0] : 00000000000000000000000000000000000000000000000000000000000000c0
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000100
Arg [2] : 0000000000000000000000000000000000000000000000000000000000002710
Arg [3] : 000000000000000000000000083bbe83c1b91e1caeaf277335bd1a82f593d843
Arg [4] : 0000000000000000000000005607ee6014b0ecdb649216bc93dbbe687143a854
Arg [5] : 00000000000000000000000000000000000000000000000000000000000001f4
Arg [6] : 0000000000000000000000000000000000000000000000000000000000000011
Arg [7] : 4d61746368205265616479204c696f6e73000000000000000000000000000000
Arg [8] : 0000000000000000000000000000000000000000000000000000000000000011
Arg [9] : 4d61746368205265616479204c696f6e73000000000000000000000000000000
Deployed Bytecode Sourcemap
97237:4213:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;100266:237;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;19440:100;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;25923:218;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;25364:400;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;15191:323;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;29630:2817;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;64257:131;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;85518:494;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;;:::i;:::-;;;;;;;;64650:147;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;65698:218;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;97403:38;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;99264:294;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;32543:185;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;99566:332;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;100127:131;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;92311:528;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;20833:152;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;100028:91;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;16375:233;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;96187:900;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;100951:315;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;101274:173;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;81794:153;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;63126:147;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;19616:104;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;93227:2513;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;62217:49;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;26481:308;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;99163:93;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;100793:150;;;:::i;:::-;;33326:399;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;91724:428;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;19826:318;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;82121:142;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;97448:62;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;65042:149;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;97372:24;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;100527:258;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;26946:164;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;98928:227;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;100266:237;100430:4;100459:36;100483:11;100459:23;:36::i;:::-;100452:43;;100266:237;;;:::o;19440:100::-;19494:13;19527:5;19520:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;19440:100;:::o;25923:218::-;25999:7;26024:16;26032:7;26024;:16::i;:::-;26019:64;;26049:34;;;;;;;;;;;;;;26019:64;26103:15;:24;26119:7;26103:24;;;;;;;;;;;:30;;;;;;;;;;;;26096:37;;25923:218;;;:::o;25364:400::-;25445:13;25461:16;25469:7;25461;:16::i;:::-;25445:32;;25517:5;25494:28;;:19;:17;:19::i;:::-;:28;;;25490:175;;25542:44;25559:5;25566:19;:17;:19::i;:::-;25542:16;:44::i;:::-;25537:128;;25614:35;;;;;;;;;;;;;;25537:128;25490:175;25710:2;25677:15;:24;25693:7;25677:24;;;;;;;;;;;:30;;;:35;;;;;;;;;;;;;;;;;;25748:7;25744:2;25728:28;;25737:5;25728:28;;;;;;;;;;;;25364:400;;;:::o;15191:323::-;15252:7;15480:15;:13;:15::i;:::-;15465:12;;15449:13;;:28;:46;15442:53;;15191:323;:::o;29630:2817::-;29764:27;29794;29813:7;29794:18;:27::i;:::-;29764:57;;29879:4;29838:45;;29854:19;29838:45;;;29834:86;;29892:28;;;;;;;;;;;;;;29834:86;29934:27;29963:23;29990:35;30017:7;29990:26;:35::i;:::-;29933:92;;;;30125:68;30150:15;30167:4;30173:19;:17;:19::i;:::-;30125:24;:68::i;:::-;30120:180;;30213:43;30230:4;30236:19;:17;:19::i;:::-;30213:16;:43::i;:::-;30208:92;;30265:35;;;;;;;;;;;;;;30208:92;30120:180;30331:1;30317:16;;:2;:16;;;30313:52;;;30342:23;;;;;;;;;;;;;;30313:52;30378:43;30400:4;30406:2;30410:7;30419:1;30378:21;:43::i;:::-;30514:15;30511:2;;;30654:1;30633:19;30626:30;30511:2;31051:18;:24;31070:4;31051:24;;;;;;;;;;;;;;;;31049:26;;;;;;;;;;;;31120:18;:22;31139:2;31120:22;;;;;;;;;;;;;;;;31118:24;;;;;;;;;;;31442:146;31479:2;31528:45;31543:4;31549:2;31553:19;31528:14;:45::i;:::-;11590:8;31500:73;31442:18;:146::i;:::-;31413:17;:26;31431:7;31413:26;;;;;;;;;;;:175;;;;31759:1;11590:8;31708:19;:47;:52;31704:627;;;31781:19;31813:1;31803:7;:11;31781:33;;31970:1;31936:17;:30;31954:11;31936:30;;;;;;;;;;;;:35;31932:384;;;32074:13;;32059:11;:28;32055:242;;32254:19;32221:17;:30;32239:11;32221:30;;;;;;;;;;;:52;;;;32055:242;31932:384;31704:627;;32378:7;32374:2;32359:27;;32368:4;32359:27;;;;;;;;;;;;32397:42;32418:4;32424:2;32428:7;32437:1;32397:20;:42::i;:::-;29630:2817;;;;;;:::o;64257:131::-;64331:7;64358:6;:12;64365:4;64358:12;;;;;;;;;;;:22;;;64351:29;;64257:131;;;:::o;85518:494::-;85662:7;85671;85696:26;85725:17;:27;85743:8;85725:27;;;;;;;;;;;85696:56;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;85797:1;85769:30;;:7;:16;;;:30;;;85765:92;;;85826:19;85816:29;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;85765:92;85869:21;85934:17;:15;:17::i;:::-;85893:58;;85907:7;:23;;;85894:36;;:10;:36;;;;:::i;:::-;85893:58;;;;:::i;:::-;85869:82;;85972:7;:16;;;85990:13;85964:40;;;;;;85518:494;;;;;:::o;64650:147::-;64733:18;64746:4;64733:12;:18::i;:::-;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;64764:25:::1;64775:4;64781:7;64764:10;:25::i;:::-;64650:147:::0;;;:::o;65698:218::-;65805:12;:10;:12::i;:::-;65794:23;;:7;:23;;;65786:83;;;;;;;;;;;;:::i;:::-;;;;;;;;;65882:26;65894:4;65900:7;65882:11;:26::i;:::-;65698:218;;:::o;97403:38::-;97440:1;97403:38;:::o;99264:294::-;99336:39;62262:4;99344:18;;99364:10;99336:7;:39::i;:::-;:75;;;;99379:32;97486:24;99400:10;99379:7;:32::i;:::-;99336:75;99314:146;;;;;;;;;;;;:::i;:::-;;;;;;;;;99495:9;;99479:13;:11;:13::i;:::-;:25;99471:56;;;;;;;;;;;;:::i;:::-;;;;;;;;;99538:12;99544:2;99548:1;99538:5;:12::i;:::-;99264:294;:::o;32543:185::-;32681:39;32698:4;32704:2;32708:7;32681:39;;;;;;;;;;;;:16;:39::i;:::-;32543:185;;;:::o;99566:332::-;99657:39;62262:4;99665:18;;99685:10;99657:7;:39::i;:::-;:75;;;;99700:32;97486:24;99721:10;99700:7;:32::i;:::-;99657:75;99635:146;;;;;;;;;;;;:::i;:::-;;;;;;;;;99828:9;;99816:8;99800:13;:11;:13::i;:::-;:24;;;;:::i;:::-;:37;;99792:68;;;;;;;;;;;;:::i;:::-;;;;;;;;;99871:19;99877:2;99881:8;99871:5;:19::i;:::-;99566:332;;:::o;100127:131::-;62262:4;100192:18;;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;100239:11:::1;;100223:13;:27;;;;;;;:::i;:::-;;100127:131:::0;;;:::o;92311:528::-;92455:23;92521:22;92546:8;;:15;;92521:40;;92576:34;92634:14;92613:36;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;92576:73;;92669:9;92664:125;92685:14;92680:1;:19;92664:125;;92741:32;92761:8;;92770:1;92761:11;;;;;;;;;;;;;;;;;;;;;92741:19;:32::i;:::-;92725:10;92736:1;92725:13;;;;;;;;;;;;;;;;;;;;;:48;;;;92701:3;;;;;92664:125;;;;92810:10;92803:17;;;;92311:528;;;;:::o;20833:152::-;20905:7;20948:27;20967:7;20948:18;:27::i;:::-;20925:52;;20833:152;;;:::o;100028:91::-;100068:13;100101:10;:8;:10::i;:::-;100094:17;;100028:91;:::o;16375:233::-;16447:7;16488:1;16471:19;;:5;:19;;;16467:60;;;16499:28;;;;;;;;;;;;;;16467:60;10534:13;16545:18;:25;16564:5;16545:25;;;;;;;;;;;;;;;;:55;16538:62;;16375:233;;;:::o;96187:900::-;96265:16;96319:19;96353:25;96393:22;96418:16;96428:5;96418:9;:16::i;:::-;96393:41;;96449:25;96491:14;96477:29;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;96449:57;;96521:31;;:::i;:::-;96572:9;96584:15;:13;:15::i;:::-;96572:27;;96567:472;96616:14;96601:11;:29;96567:472;;96668:15;96681:1;96668:12;:15::i;:::-;96656:27;;96706:9;:16;;;96702:73;;;96747:8;;96702:73;96823:1;96797:28;;:9;:14;;;:28;;;96793:111;;96870:9;:14;;;96850:34;;96793:111;96947:5;96926:26;;:17;:26;;;96922:102;;;97003:1;96977:8;96986:13;;;;;;96977:23;;;;;;;;;;;;;;;;;;;;;:27;;;;;96922:102;96567:472;96632:3;;;;;96567:472;;;;97060:8;97053:15;;;;;;;96187:900;;;:::o;100951:315::-;62262:4;101095:18;;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;101126:57:::1;101143:8;101153:16;101171:11;101126:16;:57::i;:::-;101228:16;101199:59;;101218:8;101199:59;101246:11;101199:59;;;;;;:::i;:::-;;;;;;;;100951:315:::0;;;;:::o;101274:173::-;62262:4;101337:18;;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;101368:28:::1;101387:8;101368:18;:28::i;:::-;101430:8;101412:27;;;;;;;;;;101274:173:::0;;:::o;81794:153::-;81884:7;81911:28;81933:5;81911:12;:18;81924:4;81911:18;;;;;;;;;;;:21;;:28;;;;:::i;:::-;81904:35;;81794:153;;;;:::o;63126:147::-;63212:4;63236:6;:12;63243:4;63236:12;;;;;;;;;;;:20;;:29;63257:7;63236:29;;;;;;;;;;;;;;;;;;;;;;;;;63229:36;;63126:147;;;;:::o;19616:104::-;19672:13;19705:7;19698:14;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;19616:104;:::o;93227:2513::-;93370:16;93437:4;93428:5;:13;93424:45;;93450:19;;;;;;;;;;;;;;93424:45;93484:19;93518:17;93538:14;:12;:14::i;:::-;93518:34;;93638:15;:13;:15::i;:::-;93630:5;:23;93626:87;;;93682:15;:13;:15::i;:::-;93674:23;;93626:87;93789:9;93782:4;:16;93778:73;;;93826:9;93819:16;;93778:73;93865:25;93893:16;93903:5;93893:9;:16::i;:::-;93865:44;;94087:4;94079:5;:12;94075:278;;;94112:19;94141:5;94134:4;:12;94112:34;;94183:17;94169:11;:31;94165:111;;;94245:11;94225:31;;94165:111;94075:278;;;;94336:1;94316:21;;94075:278;94367:25;94409:17;94395:32;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;94367:60;;94467:1;94446:17;:22;94442:78;;;94496:8;94489:15;;;;;;;;94442:78;94664:31;94698:26;94718:5;94698:19;:26::i;:::-;94664:60;;94739:25;94984:9;:16;;;94979:92;;95041:9;:14;;;95021:34;;94979:92;95090:9;95102:5;95090:17;;95085:478;95114:4;95109:1;:9;;:45;;;;;95137:17;95122:11;:32;;95109:45;95085:478;;;95192:15;95205:1;95192:12;:15::i;:::-;95180:27;;95230:9;:16;;;95226:73;;;95271:8;;95226:73;95347:1;95321:28;;:9;:14;;;:28;;;95317:111;;95394:9;:14;;;95374:34;;95317:111;95471:5;95450:26;;:17;:26;;;95446:102;;;95527:1;95501:8;95510:13;;;;;;95501:23;;;;;;;;;;;;;;;;;;;;;:27;;;;;95446:102;95085:478;95156:3;;;;;95085:478;;;;95665:11;95655:8;95648:29;95713:8;95706:15;;;;;;;;93227:2513;;;;;;:::o;62217:49::-;62262:4;62217:49;;;:::o;26481:308::-;26592:19;:17;:19::i;:::-;26580:31;;:8;:31;;;26576:61;;;26620:17;;;;;;;;;;;;;;26576:61;26702:8;26650:18;:39;26669:19;:17;:19::i;:::-;26650:39;;;;;;;;;;;;;;;:49;26690:8;26650:49;;;;;;;;;;;;;;;;:60;;;;;;;;;;;;;;;;;;26762:8;26726:55;;26741:19;:17;:19::i;:::-;26726:55;;;26772:8;26726:55;;;;;;:::i;:::-;;;;;;;;26481:308;;:::o;99163:93::-;99207:7;99234:14;:12;:14::i;:::-;99227:21;;99163:93;:::o;100793:150::-;62262:4;100843:18;;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;100874:23:::1;:21;:23::i;:::-;100913:22;;;;;;;;;;100793:150:::0;:::o;33326:399::-;33493:31;33506:4;33512:2;33516:7;33493:12;:31::i;:::-;33557:1;33539:2;:14;;;:19;33535:183;;33578:56;33609:4;33615:2;33619:7;33628:5;33578:30;:56::i;:::-;33573:145;;33662:40;;;;;;;;;;;;;;33573:145;33535:183;33326:399;;;;:::o;91724:428::-;91808:21;;:::i;:::-;91842:31;;:::i;:::-;91898:15;:13;:15::i;:::-;91888:7;:25;:54;;;;91928:14;:12;:14::i;:::-;91917:7;:25;;91888:54;91884:103;;;91966:9;91959:16;;;;;91884:103;92009:21;92022:7;92009:12;:21::i;:::-;91997:33;;92045:9;:16;;;92041:65;;;92085:9;92078:16;;;;;92041:65;92123:21;92136:7;92123:12;:21::i;:::-;92116:28;;;91724:428;;;;:::o;19826:318::-;19899:13;19930:16;19938:7;19930;:16::i;:::-;19925:59;;19955:29;;;;;;;;;;;;;;19925:59;19997:21;20021:10;:8;:10::i;:::-;19997:34;;20074:1;20055:7;20049:21;:26;;:87;;;;;;;;;;;;;;;;;20102:7;20111:18;20121:7;20111:9;:18::i;:::-;20085:45;;;;;;;;;:::i;:::-;;;;;;;;;;;;;20049:87;20042:94;;;19826:318;;;:::o;82121:142::-;82201:7;82228:27;:12;:18;82241:4;82228:18;;;;;;;;;;;:25;:27::i;:::-;82221:34;;82121:142;;;:::o;97448:62::-;97486:24;97448:62;:::o;65042:149::-;65126:18;65139:4;65126:12;:18::i;:::-;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;65157:26:::1;65169:4;65175:7;65157:11;:26::i;:::-;65042:149:::0;;;:::o;97372:24::-;;;;:::o;100527:258::-;62262:4;100632:18;;62708:30;62719:4;62725:12;:10;:12::i;:::-;62708:10;:30::i;:::-;100668:49:::1;100687:16;100705:11;100668:18;:49::i;:::-;100747:16;100733:44;;;100765:11;100733:44;;;;;;:::i;:::-;;;;;;;;100527:258:::0;;;:::o;26946:164::-;27043:4;27067:18;:25;27086:5;27067:25;;;;;;;;;;;;;;;:35;27093:8;27067:35;;;;;;;;;;;;;;;;;;;;;;;;;27060:42;;26946:164;;;;:::o;98928:227::-;99019:13;:11;:13::i;:::-;99002;:30;;98994:60;;;;;;;;;;;;:::i;:::-;;;;;;;;;99070:41;99086:9;;99097:13;99070:41;;;;;;;:::i;:::-;;;;;;;;99134:13;99122:9;:25;;;;98928:227;:::o;67199:238::-;67283:22;67291:4;67297:7;67283;:22::i;:::-;67278:152;;67354:4;67322:6;:12;67329:4;67322:12;;;;;;;;;;;:20;;:29;67343:7;67322:29;;;;;;;;;;;;;;;;:36;;;;;;;;;;;;;;;;;;67405:12;:10;:12::i;:::-;67378:40;;67396:7;67378:40;;67390:4;67378:40;;;;;;;;;;67278:152;67199:238;;:::o;75693:152::-;75763:4;75787:50;75792:3;:10;;75828:5;75812:23;;75804:32;;75787:4;:50::i;:::-;75780:57;;75693:152;;;;:::o;80981:214::-;81066:4;81105:42;81090:57;;;:11;:57;;;;:97;;;;81151:36;81175:11;81151:23;:36::i;:::-;81090:97;81083:104;;80981:214;;;:::o;27368:282::-;27433:4;27489:7;27470:15;:13;:15::i;:::-;:26;;:66;;;;;27523:13;;27513:7;:23;27470:66;:153;;;;;27622:1;11310:8;27574:17;:26;27592:7;27574:26;;;;;;;;;;;;:44;:49;27470:153;27450:173;;27368:282;;;:::o;49134:105::-;49194:7;49221:10;49214:17;;49134:105;:::o;98810:110::-;98875:7;97440:1;98895:17;;98810:110;:::o;21988:1275::-;22055:7;22075:12;22090:7;22075:22;;22158:4;22139:15;:13;:15::i;:::-;:23;22135:1061;;22192:13;;22185:4;:20;22181:1015;;;22230:14;22247:17;:23;22265:4;22247:23;;;;;;;;;;;;22230:40;;22364:1;11310:8;22336:6;:24;:29;22332:845;;;23001:113;23018:1;23008:6;:11;23001:113;;;23061:17;:25;23079:6;;;;;;;23061:25;;;;;;;;;;;;23052:34;;23001:113;;;23147:6;23140:13;;;;;;22332:845;22181:1015;;22135:1061;23224:31;;;;;;;;;;;;;;21988:1275;;;;:::o;28531:479::-;28633:27;28662:23;28703:38;28744:15;:24;28760:7;28744:24;;;;;;;;;;;28703:65;;28915:18;28892:41;;28972:19;28966:26;28947:45;;28877:126;;;;:::o;27759:659::-;27908:11;28073:16;28066:5;28062:28;28053:37;;28233:16;28222:9;28218:32;28205:45;;28383:15;28372:9;28369:30;28361:5;28350:9;28347:20;28344:56;28334:66;;27941:470;;;;;:::o;34387:159::-;;;;;:::o;48443:311::-;48578:7;48598:16;11714:3;48624:19;:41;;48598:68;;11714:3;48692:31;48703:4;48709:2;48713:9;48692:10;:31::i;:::-;48684:40;;:62;;48677:69;;;48443:311;;;;;:::o;23811:450::-;23891:14;24059:16;24052:5;24048:28;24039:37;;24236:5;24222:11;24197:23;24193:41;24190:52;24183:5;24180:63;24170:73;;23927:327;;;;:::o;35211:158::-;;;;;:::o;86294:97::-;86352:6;86378:5;86371:12;;86294:97;:::o;57891:98::-;57944:7;57971:10;57964:17;;57891:98;:::o;63563:505::-;63652:22;63660:4;63666:7;63652;:22::i;:::-;63647:414;;63840:41;63868:7;63840:41;;63878:2;63840:19;:41::i;:::-;63954:38;63982:4;63974:13;;63989:2;63954:19;:38::i;:::-;63745:270;;;;;;;;;:::i;:::-;;;;;;;;;;;;;63691:358;;;;;;;;;;;:::i;:::-;;;;;;;;63647:414;63563:505;;:::o;82356:169::-;82444:31;82461:4;82467:7;82444:16;:31::i;:::-;82486;82509:7;82486:12;:18;82499:4;82486:18;;;;;;;;;;;:22;;:31;;;;:::i;:::-;;82356:169;;:::o;82619:174::-;82708:32;82726:4;82732:7;82708:17;:32::i;:::-;82751:34;82777:7;82751:12;:18;82764:4;82751:18;;;;;;;;;;;:25;;:34;;;;:::i;:::-;;82619:174;;:::o;36987:2454::-;37060:20;37083:13;;37060:36;;37123:1;37111:8;:13;37107:44;;;37133:18;;;;;;;;;;;;;;37107:44;37164:61;37194:1;37198:2;37202:12;37216:8;37164:21;:61::i;:::-;37708:1;10672:2;37678:1;:26;;37677:32;37665:8;:45;37639:18;:22;37658:2;37639:22;;;;;;;;;;;;;;;;:71;;;;;;;;;;;37987:139;38024:2;38078:33;38101:1;38105:2;38109:1;38078:14;:33::i;:::-;38045:30;38066:8;38045:20;:30::i;:::-;:66;37987:18;:139::i;:::-;37953:17;:31;37971:12;37953:31;;;;;;;;;;;:173;;;;38143:16;38174:11;38203:8;38188:12;:23;38174:37;;38458:16;38454:2;38450:25;38438:37;;38830:12;38790:8;38749:1;38687:25;38628:1;38567;38540:335;38955:1;38941:12;38937:20;38895:346;38996:3;38987:7;38984:16;38895:346;;39214:7;39204:8;39201:1;39174:25;39171:1;39168;39163:59;39049:1;39040:7;39036:15;39025:26;;38895:346;;;38899:77;39286:1;39274:8;:13;39270:45;;;39296:19;;;;;;;;;;;;;;39270:45;39348:3;39332:13;:19;;;;36987:2454;;39373:60;39402:1;39406:2;39410:12;39424:8;39373:20;:60::i;:::-;36987:2454;;;:::o;99906:114::-;99966:13;99999;99992:20;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;99906:114;:::o;21436:161::-;21504:21;;:::i;:::-;21545:44;21564:17;:24;21582:5;21564:24;;;;;;;;;;;;21545:18;:44::i;:::-;21538:51;;21436:161;;;:::o;87489:390::-;87657:17;:15;:17::i;:::-;87641:33;;:12;:33;;;;87633:88;;;;;;;;;;;;:::i;:::-;;;;;;;;;87760:1;87740:22;;:8;:22;;;;87732:62;;;;;;;;;;;;:::i;:::-;;;;;;;;;87836:35;;;;;;;;87848:8;87836:35;;;;;;87858:12;87836:35;;;;;87807:17;:26;87825:7;87807:26;;;;;;;;;;;:64;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;87489:390;;;:::o;87990:114::-;88070:17;:26;88088:7;88070:26;;;;;;;;;;;;88063:33;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;87990:114;:::o;76989:158::-;77063:7;77114:22;77118:3;:10;;77130:5;77114:3;:22::i;:::-;77106:31;;77083:56;;76989:158;;;;:::o;14878:103::-;14933:7;14960:13;;14953:20;;14878:103;:::o;15612:296::-;15667:7;15874:15;:13;:15::i;:::-;15858:13;;:31;15851:38;;15612:296;:::o;87070:95::-;87138:19;;87131:26;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;87070:95::o;35809:716::-;35972:4;36018:2;35993:45;;;36039:19;:17;:19::i;:::-;36060:4;36066:7;36075:5;35993:88;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;35989:529;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;36293:1;36276:6;:13;:18;36272:235;;;36322:40;;;;;;;;;;;;;;36272:235;36465:6;36459:13;36450:6;36446:2;36442:15;36435:38;35989:529;36162:54;;;36152:64;;;:6;:64;;;;36145:71;;;35809:716;;;;;;:::o;21174:166::-;21244:21;;:::i;:::-;21285:47;21304:27;21323:7;21304:18;:27::i;:::-;21285:18;:47::i;:::-;21278:54;;21174:166;;;:::o;49341:1581::-;49406:17;49831:4;49824;49818:11;49814:22;49807:29;;49923:3;49917:4;49910:17;50029:3;50268:5;50250:428;50276:1;50250:428;;;50316:1;50311:3;50307:11;50300:18;;50487:2;50481:4;50477:13;50473:2;50469:22;50464:3;50456:36;50581:2;50575:4;50571:13;50563:21;;50648:4;50638:2;;50656:5;;50638:2;50250:428;;;50254:21;50717:3;50712;50708:13;50832:4;50827:3;50823:14;50816:21;;50897:6;50892:3;50885:19;49445:1470;;;;;:::o;76518:117::-;76581:7;76608:19;76616:3;:10;;76608:7;:19::i;:::-;76601:26;;76518:117;;;:::o;86662:332::-;86781:17;:15;:17::i;:::-;86765:33;;:12;:33;;;;86757:88;;;;;;;;;;;;:::i;:::-;;;;;;;;;86884:1;86864:22;;:8;:22;;;;86856:60;;;;;;;;;;;;:::i;:::-;;;;;;;;;86951:35;;;;;;;;86963:8;86951:35;;;;;;86973:12;86951:35;;;;;86929:19;:57;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;86662:332;;:::o;69608:414::-;69671:4;69693:21;69703:3;69708:5;69693:9;:21::i;:::-;69688:327;;69731:3;:11;;69748:5;69731:23;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;69914:3;:11;;:18;;;;69892:3;:12;;:19;69905:5;69892:19;;;;;;;;;;;:40;;;;69954:4;69947:11;;;;69688:327;69998:5;69991:12;;69608:414;;;;;:::o;62830:204::-;62915:4;62954:32;62939:47;;;:11;:47;;;;:87;;;;62990:36;63014:11;62990:23;:36::i;:::-;62939:87;62932:94;;62830:204;;;:::o;48144:147::-;48281:6;48144:147;;;;;:::o;59777:451::-;59852:13;59878:19;59923:1;59914:6;59910:1;:10;;;;:::i;:::-;:14;;;;:::i;:::-;59900:25;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;59878:47;;59936:15;:6;59943:1;59936:9;;;;;;;;;;;;;;;;;;;:15;;;;;;;;;;;59962;:6;59969:1;59962:9;;;;;;;;;;;;;;;;;;;:15;;;;;;;;;;;59993:9;60018:1;60009:6;60005:1;:10;;;;:::i;:::-;:14;;;;:::i;:::-;59993:26;;59988:135;60025:1;60021;:5;59988:135;;;60060:12;60081:3;60073:5;:11;60060:25;;;;;;;;;;;;;;;;;;60048:6;60055:1;60048:9;;;;;;;;;;;;;;;;;;;:37;;;;;;;;;;;60110:1;60100:11;;;;;60028:3;;;;:::i;:::-;;;59988:135;;;;60150:1;60141:5;:10;60133:55;;;;;;;;;;;;:::i;:::-;;;;;;;;;60213:6;60199:21;;;59777:451;;;;:::o;67569:239::-;67653:22;67661:4;67667:7;67653;:22::i;:::-;67649:152;;;67724:5;67692:6;:12;67699:4;67692:12;;;;;;;;;;;:20;;:29;67713:7;67692:29;;;;;;;;;;;;;;;;:37;;;;;;;;;;;;;;;;;;67776:12;:10;:12::i;:::-;67749:40;;67767:7;67749:40;;67761:4;67749:40;;;;;;;;;;67649:152;67569:239;;:::o;76021:158::-;76094:4;76118:53;76126:3;:10;;76162:5;76146:23;;76138:32;;76118:7;:53::i;:::-;76111:60;;76021:158;;;;:::o;24363:324::-;24433:14;24666:1;24656:8;24653:15;24627:24;24623:46;24613:56;;24535:145;;;:::o;23362:366::-;23428:31;;:::i;:::-;23505:6;23472:9;:14;;:41;;;;;;;;;;;11193:3;23558:6;:33;;23524:9;:24;;:68;;;;;;;;;;;23650:1;11310:8;23622:6;:24;:29;;23603:9;:16;;:48;;;;;;;;;;;11714:3;23691:6;:28;;23662:9;:19;;:58;;;;;;;;;;;23362:366;;;:::o;72382:120::-;72449:7;72476:3;:11;;72488:5;72476:18;;;;;;;;;;;;;;;;;;;;;;;;72469:25;;72382:120;;;;:::o;71919:109::-;71975:7;72002:3;:11;;:18;;;;71995:25;;71919:109;;;:::o;71704:129::-;71777:4;71824:1;71801:3;:12;;:19;71814:5;71801:19;;;;;;;;;;;;:24;;71794:31;;71704:129;;;;:::o;85248:215::-;85350:4;85389:26;85374:41;;;:11;:41;;;;:81;;;;85419:36;85443:11;85419:23;:36::i;:::-;85374:81;85367:88;;85248:215;;;:::o;70198:1420::-;70264:4;70382:18;70403:3;:12;;:19;70416:5;70403:19;;;;;;;;;;;;70382:40;;70453:1;70439:10;:15;70435:1176;;70814:21;70851:1;70838:10;:14;;;;:::i;:::-;70814:38;;70867:17;70908:1;70887:3;:11;;:18;;;;:22;;;;:::i;:::-;70867:42;;70943:13;70930:9;:26;70926:405;;70977:17;70997:3;:11;;71009:9;70997:22;;;;;;;;;;;;;;;;;;;;;;;;70977:42;;71151:9;71122:3;:11;;71134:13;71122:26;;;;;;;;;;;;;;;;;;;;;;;:38;;;;71262:10;71236:3;:12;;:23;71249:9;71236:23;;;;;;;;;;;:36;;;;70926:405;;71412:3;:11;;:17;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;71507:3;:12;;:19;71520:5;71507:19;;;;;;;;;;;71500:26;;;71550:4;71543:11;;;;;;;70435:1176;71594:5;71587:12;;;70198:1420;;;;;:::o;18538:639::-;18623:4;18962:10;18947:25;;:11;:25;;;;:102;;;;19039:10;19024:25;;:11;:25;;;;18947:102;:179;;;;19116:10;19101:25;;:11;:25;;;;18947:179;18927:199;;18538:639;;;:::o;-1:-1:-1:-;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;:::o;7:343:1:-;84:5;109:65;125:48;166:6;125:48;:::i;:::-;109:65;:::i;:::-;100:74;;197:6;190:5;183:21;235:4;228:5;224:16;273:3;264:6;259:3;255:16;252:25;249:2;;;290:1;287;280:12;249:2;303:41;337:6;332:3;327;303:41;:::i;:::-;90:260;;;;;;:::o;356:139::-;402:5;440:6;427:20;418:29;;456:33;483:5;456:33;:::i;:::-;408:87;;;;:::o;518:367::-;591:8;601:6;651:3;644:4;636:6;632:17;628:27;618:2;;669:1;666;659:12;618:2;705:6;692:20;682:30;;735:18;727:6;724:30;721:2;;;767:1;764;757:12;721:2;804:4;796:6;792:17;780:29;;858:3;850:4;842:6;838:17;828:8;824:32;821:41;818:2;;;875:1;872;865:12;818:2;608:277;;;;;:::o;891:133::-;934:5;972:6;959:20;950:29;;988:30;1012:5;988:30;:::i;:::-;940:84;;;;:::o;1030:139::-;1076:5;1114:6;1101:20;1092:29;;1130:33;1157:5;1130:33;:::i;:::-;1082:87;;;;:::o;1175:137::-;1220:5;1258:6;1245:20;1236:29;;1274:32;1300:5;1274:32;:::i;:::-;1226:86;;;;:::o;1318:141::-;1374:5;1405:6;1399:13;1390:22;;1421:32;1447:5;1421:32;:::i;:::-;1380:79;;;;:::o;1478:271::-;1533:5;1582:3;1575:4;1567:6;1563:17;1559:27;1549:2;;1600:1;1597;1590:12;1549:2;1640:6;1627:20;1665:78;1739:3;1731:6;1724:4;1716:6;1712:17;1665:78;:::i;:::-;1656:87;;1539:210;;;;;:::o;1769:352::-;1827:8;1837:6;1887:3;1880:4;1872:6;1868:17;1864:27;1854:2;;1905:1;1902;1895:12;1854:2;1941:6;1928:20;1918:30;;1971:18;1963:6;1960:30;1957:2;;;2003:1;2000;1993:12;1957:2;2040:4;2032:6;2028:17;2016:29;;2094:3;2086:4;2078:6;2074:17;2064:8;2060:32;2057:41;2054:2;;;2111:1;2108;2101:12;2054:2;1844:277;;;;;:::o;2127:139::-;2173:5;2211:6;2198:20;2189:29;;2227:33;2254:5;2227:33;:::i;:::-;2179:87;;;;:::o;2272:137::-;2317:5;2355:6;2342:20;2333:29;;2371:32;2397:5;2371:32;:::i;:::-;2323:86;;;;:::o;2415:262::-;2474:6;2523:2;2511:9;2502:7;2498:23;2494:32;2491:2;;;2539:1;2536;2529:12;2491:2;2582:1;2607:53;2652:7;2643:6;2632:9;2628:22;2607:53;:::i;:::-;2597:63;;2553:117;2481:196;;;;:::o;2683:407::-;2751:6;2759;2808:2;2796:9;2787:7;2783:23;2779:32;2776:2;;;2824:1;2821;2814:12;2776:2;2867:1;2892:53;2937:7;2928:6;2917:9;2913:22;2892:53;:::i;:::-;2882:63;;2838:117;2994:2;3020:53;3065:7;3056:6;3045:9;3041:22;3020:53;:::i;:::-;3010:63;;2965:118;2766:324;;;;;:::o;3096:552::-;3173:6;3181;3189;3238:2;3226:9;3217:7;3213:23;3209:32;3206:2;;;3254:1;3251;3244:12;3206:2;3297:1;3322:53;3367:7;3358:6;3347:9;3343:22;3322:53;:::i;:::-;3312:63;;3268:117;3424:2;3450:53;3495:7;3486:6;3475:9;3471:22;3450:53;:::i;:::-;3440:63;;3395:118;3552:2;3578:53;3623:7;3614:6;3603:9;3599:22;3578:53;:::i;:::-;3568:63;;3523:118;3196:452;;;;;:::o;3654:809::-;3749:6;3757;3765;3773;3822:3;3810:9;3801:7;3797:23;3793:33;3790:2;;;3839:1;3836;3829:12;3790:2;3882:1;3907:53;3952:7;3943:6;3932:9;3928:22;3907:53;:::i;:::-;3897:63;;3853:117;4009:2;4035:53;4080:7;4071:6;4060:9;4056:22;4035:53;:::i;:::-;4025:63;;3980:118;4137:2;4163:53;4208:7;4199:6;4188:9;4184:22;4163:53;:::i;:::-;4153:63;;4108:118;4293:2;4282:9;4278:18;4265:32;4324:18;4316:6;4313:30;4310:2;;;4356:1;4353;4346:12;4310:2;4384:62;4438:7;4429:6;4418:9;4414:22;4384:62;:::i;:::-;4374:72;;4236:220;3780:683;;;;;;;:::o;4469:401::-;4534:6;4542;4591:2;4579:9;4570:7;4566:23;4562:32;4559:2;;;4607:1;4604;4597:12;4559:2;4650:1;4675:53;4720:7;4711:6;4700:9;4696:22;4675:53;:::i;:::-;4665:63;;4621:117;4777:2;4803:50;4845:7;4836:6;4825:9;4821:22;4803:50;:::i;:::-;4793:60;;4748:115;4549:321;;;;;:::o;4876:407::-;4944:6;4952;5001:2;4989:9;4980:7;4976:23;4972:32;4969:2;;;5017:1;5014;5007:12;4969:2;5060:1;5085:53;5130:7;5121:6;5110:9;5106:22;5085:53;:::i;:::-;5075:63;;5031:117;5187:2;5213:53;5258:7;5249:6;5238:9;5234:22;5213:53;:::i;:::-;5203:63;;5158:118;4959:324;;;;;:::o;5289:552::-;5366:6;5374;5382;5431:2;5419:9;5410:7;5406:23;5402:32;5399:2;;;5447:1;5444;5437:12;5399:2;5490:1;5515:53;5560:7;5551:6;5540:9;5536:22;5515:53;:::i;:::-;5505:63;;5461:117;5617:2;5643:53;5688:7;5679:6;5668:9;5664:22;5643:53;:::i;:::-;5633:63;;5588:118;5745:2;5771:53;5816:7;5807:6;5796:9;5792:22;5771:53;:::i;:::-;5761:63;;5716:118;5389:452;;;;;:::o;5847:405::-;5914:6;5922;5971:2;5959:9;5950:7;5946:23;5942:32;5939:2;;;5987:1;5984;5977:12;5939:2;6030:1;6055:53;6100:7;6091:6;6080:9;6076:22;6055:53;:::i;:::-;6045:63;;6001:117;6157:2;6183:52;6227:7;6218:6;6207:9;6203:22;6183:52;:::i;:::-;6173:62;;6128:117;5929:323;;;;;:::o;6258:425::-;6344:6;6352;6401:2;6389:9;6380:7;6376:23;6372:32;6369:2;;;6417:1;6414;6407:12;6369:2;6488:1;6477:9;6473:17;6460:31;6518:18;6510:6;6507:30;6504:2;;;6550:1;6547;6540:12;6504:2;6586:80;6658:7;6649:6;6638:9;6634:22;6586:80;:::i;:::-;6568:98;;;;6431:245;6359:324;;;;;:::o;6689:262::-;6748:6;6797:2;6785:9;6776:7;6772:23;6768:32;6765:2;;;6813:1;6810;6803:12;6765:2;6856:1;6881:53;6926:7;6917:6;6906:9;6902:22;6881:53;:::i;:::-;6871:63;;6827:117;6755:196;;;;:::o;6957:407::-;7025:6;7033;7082:2;7070:9;7061:7;7057:23;7053:32;7050:2;;;7098:1;7095;7088:12;7050:2;7141:1;7166:53;7211:7;7202:6;7191:9;7187:22;7166:53;:::i;:::-;7156:63;;7112:117;7268:2;7294:53;7339:7;7330:6;7319:9;7315:22;7294:53;:::i;:::-;7284:63;;7239:118;7040:324;;;;;:::o;7370:407::-;7438:6;7446;7495:2;7483:9;7474:7;7470:23;7466:32;7463:2;;;7511:1;7508;7501:12;7463:2;7554:1;7579:53;7624:7;7615:6;7604:9;7600:22;7579:53;:::i;:::-;7569:63;;7525:117;7681:2;7707:53;7752:7;7743:6;7732:9;7728:22;7707:53;:::i;:::-;7697:63;;7652:118;7453:324;;;;;:::o;7783:260::-;7841:6;7890:2;7878:9;7869:7;7865:23;7861:32;7858:2;;;7906:1;7903;7896:12;7858:2;7949:1;7974:52;8018:7;8009:6;7998:9;7994:22;7974:52;:::i;:::-;7964:62;;7920:116;7848:195;;;;:::o;8049:282::-;8118:6;8167:2;8155:9;8146:7;8142:23;8138:32;8135:2;;;8183:1;8180;8173:12;8135:2;8226:1;8251:63;8306:7;8297:6;8286:9;8282:22;8251:63;:::i;:::-;8241:73;;8197:127;8125:206;;;;:::o;8337:395::-;8408:6;8416;8465:2;8453:9;8444:7;8440:23;8436:32;8433:2;;;8481:1;8478;8471:12;8433:2;8552:1;8541:9;8537:17;8524:31;8582:18;8574:6;8571:30;8568:2;;;8614:1;8611;8604:12;8568:2;8650:65;8707:7;8698:6;8687:9;8683:22;8650:65;:::i;:::-;8632:83;;;;8495:230;8423:309;;;;;:::o;8738:262::-;8797:6;8846:2;8834:9;8825:7;8821:23;8817:32;8814:2;;;8862:1;8859;8852:12;8814:2;8905:1;8930:53;8975:7;8966:6;8955:9;8951:22;8930:53;:::i;:::-;8920:63;;8876:117;8804:196;;;;:::o;9006:550::-;9082:6;9090;9098;9147:2;9135:9;9126:7;9122:23;9118:32;9115:2;;;9163:1;9160;9153:12;9115:2;9206:1;9231:53;9276:7;9267:6;9256:9;9252:22;9231:53;:::i;:::-;9221:63;;9177:117;9333:2;9359:53;9404:7;9395:6;9384:9;9380:22;9359:53;:::i;:::-;9349:63;;9304:118;9461:2;9487:52;9531:7;9522:6;9511:9;9507:22;9487:52;:::i;:::-;9477:62;;9432:117;9105:451;;;;;:::o;9562:407::-;9630:6;9638;9687:2;9675:9;9666:7;9662:23;9658:32;9655:2;;;9703:1;9700;9693:12;9655:2;9746:1;9771:53;9816:7;9807:6;9796:9;9792:22;9771:53;:::i;:::-;9761:63;;9717:117;9873:2;9899:53;9944:7;9935:6;9924:9;9920:22;9899:53;:::i;:::-;9889:63;;9844:118;9645:324;;;;;:::o;9975:299::-;10104:10;10125:106;10227:3;10219:6;10125:106;:::i;:::-;10263:4;10258:3;10254:14;10240:28;;10115:159;;;;:::o;10280:179::-;10349:10;10370:46;10412:3;10404:6;10370:46;:::i;:::-;10448:4;10443:3;10439:14;10425:28;;10360:99;;;;:::o;10465:108::-;10542:24;10560:5;10542:24;:::i;:::-;10537:3;10530:37;10520:53;;:::o;10579:118::-;10666:24;10684:5;10666:24;:::i;:::-;10661:3;10654:37;10644:53;;:::o;10779:972::-;10958:3;10987:84;11065:5;10987:84;:::i;:::-;11087:116;11196:6;11191:3;11087:116;:::i;:::-;11080:123;;11227:86;11307:5;11227:86;:::i;:::-;11336:7;11367:1;11352:374;11377:6;11374:1;11371:13;11352:374;;;11453:6;11447:13;11480:123;11599:3;11584:13;11480:123;:::i;:::-;11473:130;;11626:90;11709:6;11626:90;:::i;:::-;11616:100;;11412:314;11399:1;11396;11392:9;11387:14;;11352:374;;;11356:14;11742:3;11735:10;;10963:788;;;;;;;:::o;11787:732::-;11906:3;11935:54;11983:5;11935:54;:::i;:::-;12005:86;12084:6;12079:3;12005:86;:::i;:::-;11998:93;;12115:56;12165:5;12115:56;:::i;:::-;12194:7;12225:1;12210:284;12235:6;12232:1;12229:13;12210:284;;;12311:6;12305:13;12338:63;12397:3;12382:13;12338:63;:::i;:::-;12331:70;;12424:60;12477:6;12424:60;:::i;:::-;12414:70;;12270:224;12257:1;12254;12250:9;12245:14;;12210:284;;;12214:14;12510:3;12503:10;;11911:608;;;;;;;:::o;12525:99::-;12596:21;12611:5;12596:21;:::i;:::-;12591:3;12584:34;12574:50;;:::o;12630:109::-;12711:21;12726:5;12711:21;:::i;:::-;12706:3;12699:34;12689:50;;:::o;12745:118::-;12832:24;12850:5;12832:24;:::i;:::-;12827:3;12820:37;12810:53;;:::o;12869:360::-;12955:3;12983:38;13015:5;12983:38;:::i;:::-;13037:70;13100:6;13095:3;13037:70;:::i;:::-;13030:77;;13116:52;13161:6;13156:3;13149:4;13142:5;13138:16;13116:52;:::i;:::-;13193:29;13215:6;13193:29;:::i;:::-;13188:3;13184:39;13177:46;;12959:270;;;;;:::o;13235:364::-;13323:3;13351:39;13384:5;13351:39;:::i;:::-;13406:71;13470:6;13465:3;13406:71;:::i;:::-;13399:78;;13486:52;13531:6;13526:3;13519:4;13512:5;13508:16;13486:52;:::i;:::-;13563:29;13585:6;13563:29;:::i;:::-;13558:3;13554:39;13547:46;;13327:272;;;;;:::o;13605:377::-;13711:3;13739:39;13772:5;13739:39;:::i;:::-;13794:89;13876:6;13871:3;13794:89;:::i;:::-;13787:96;;13892:52;13937:6;13932:3;13925:4;13918:5;13914:16;13892:52;:::i;:::-;13969:6;13964:3;13960:16;13953:23;;13715:267;;;;;:::o;13988:366::-;14130:3;14151:67;14215:2;14210:3;14151:67;:::i;:::-;14144:74;;14227:93;14316:3;14227:93;:::i;:::-;14345:2;14340:3;14336:12;14329:19;;14134:220;;;:::o;14360:366::-;14502:3;14523:67;14587:2;14582:3;14523:67;:::i;:::-;14516:74;;14599:93;14688:3;14599:93;:::i;:::-;14717:2;14712:3;14708:12;14701:19;;14506:220;;;:::o;14732:366::-;14874:3;14895:67;14959:2;14954:3;14895:67;:::i;:::-;14888:74;;14971:93;15060:3;14971:93;:::i;:::-;15089:2;15084:3;15080:12;15073:19;;14878:220;;;:::o;15104:366::-;15246:3;15267:67;15331:2;15326:3;15267:67;:::i;:::-;15260:74;;15343:93;15432:3;15343:93;:::i;:::-;15461:2;15456:3;15452:12;15445:19;;15250:220;;;:::o;15476:366::-;15618:3;15639:67;15703:2;15698:3;15639:67;:::i;:::-;15632:74;;15715:93;15804:3;15715:93;:::i;:::-;15833:2;15828:3;15824:12;15817:19;;15622:220;;;:::o;15848:402::-;16008:3;16029:85;16111:2;16106:3;16029:85;:::i;:::-;16022:92;;16123:93;16212:3;16123:93;:::i;:::-;16241:2;16236:3;16232:12;16225:19;;16012:238;;;:::o;16256:366::-;16398:3;16419:67;16483:2;16478:3;16419:67;:::i;:::-;16412:74;;16495:93;16584:3;16495:93;:::i;:::-;16613:2;16608:3;16604:12;16597:19;;16402:220;;;:::o;16628:366::-;16770:3;16791:67;16855:2;16850:3;16791:67;:::i;:::-;16784:74;;16867:93;16956:3;16867:93;:::i;:::-;16985:2;16980:3;16976:12;16969:19;;16774:220;;;:::o;17000:402::-;17160:3;17181:85;17263:2;17258:3;17181:85;:::i;:::-;17174:92;;17275:93;17364:3;17275:93;:::i;:::-;17393:2;17388:3;17384:12;17377:19;;17164:238;;;:::o;17408:366::-;17550:3;17571:67;17635:2;17630:3;17571:67;:::i;:::-;17564:74;;17647:93;17736:3;17647:93;:::i;:::-;17765:2;17760:3;17756:12;17749:19;;17554:220;;;:::o;17852:862::-;17999:4;17994:3;17990:14;18086:4;18079:5;18075:16;18069:23;18105:63;18162:4;18157:3;18153:14;18139:12;18105:63;:::i;:::-;18014:164;18270:4;18263:5;18259:16;18253:23;18289:61;18344:4;18339:3;18335:14;18321:12;18289:61;:::i;:::-;18188:172;18444:4;18437:5;18433:16;18427:23;18463:57;18514:4;18509:3;18505:14;18491:12;18463:57;:::i;:::-;18370:160;18617:4;18610:5;18606:16;18600:23;18636:61;18691:4;18686:3;18682:14;18668:12;18636:61;:::i;:::-;18540:167;17968:746;;;:::o;18792:872::-;18949:4;18944:3;18940:14;19036:4;19029:5;19025:16;19019:23;19055:63;19112:4;19107:3;19103:14;19089:12;19055:63;:::i;:::-;18964:164;19220:4;19213:5;19209:16;19203:23;19239:61;19294:4;19289:3;19285:14;19271:12;19239:61;:::i;:::-;19138:172;19394:4;19387:5;19383:16;19377:23;19413:57;19464:4;19459:3;19455:14;19441:12;19413:57;:::i;:::-;19320:160;19567:4;19560:5;19556:16;19550:23;19586:61;19641:4;19636:3;19632:14;19618:12;19586:61;:::i;:::-;19490:167;18918:746;;;:::o;19670:105::-;19745:23;19762:5;19745:23;:::i;:::-;19740:3;19733:36;19723:52;;:::o;19781:108::-;19858:24;19876:5;19858:24;:::i;:::-;19853:3;19846:37;19836:53;;:::o;19895:118::-;19982:24;20000:5;19982:24;:::i;:::-;19977:3;19970:37;19960:53;;:::o;20019:105::-;20094:23;20111:5;20094:23;:::i;:::-;20089:3;20082:36;20072:52;;:::o;20130:115::-;20215:23;20232:5;20215:23;:::i;:::-;20210:3;20203:36;20193:52;;:::o;20251:435::-;20431:3;20453:95;20544:3;20535:6;20453:95;:::i;:::-;20446:102;;20565:95;20656:3;20647:6;20565:95;:::i;:::-;20558:102;;20677:3;20670:10;;20435:251;;;;;:::o;20692:967::-;21074:3;21096:148;21240:3;21096:148;:::i;:::-;21089:155;;21261:95;21352:3;21343:6;21261:95;:::i;:::-;21254:102;;21373:148;21517:3;21373:148;:::i;:::-;21366:155;;21538:95;21629:3;21620:6;21538:95;:::i;:::-;21531:102;;21650:3;21643:10;;21078:581;;;;;:::o;21665:222::-;21758:4;21796:2;21785:9;21781:18;21773:26;;21809:71;21877:1;21866:9;21862:17;21853:6;21809:71;:::i;:::-;21763:124;;;;:::o;21893:640::-;22088:4;22126:3;22115:9;22111:19;22103:27;;22140:71;22208:1;22197:9;22193:17;22184:6;22140:71;:::i;:::-;22221:72;22289:2;22278:9;22274:18;22265:6;22221:72;:::i;:::-;22303;22371:2;22360:9;22356:18;22347:6;22303:72;:::i;:::-;22422:9;22416:4;22412:20;22407:2;22396:9;22392:18;22385:48;22450:76;22521:4;22512:6;22450:76;:::i;:::-;22442:84;;22093:440;;;;;;;:::o;22539:332::-;22660:4;22698:2;22687:9;22683:18;22675:26;;22711:71;22779:1;22768:9;22764:17;22755:6;22711:71;:::i;:::-;22792:72;22860:2;22849:9;22845:18;22836:6;22792:72;:::i;:::-;22665:206;;;;;:::o;22877:493::-;23080:4;23118:2;23107:9;23103:18;23095:26;;23167:9;23161:4;23157:20;23153:1;23142:9;23138:17;23131:47;23195:168;23358:4;23349:6;23195:168;:::i;:::-;23187:176;;23085:285;;;;:::o;23376:373::-;23519:4;23557:2;23546:9;23542:18;23534:26;;23606:9;23600:4;23596:20;23592:1;23581:9;23577:17;23570:47;23634:108;23737:4;23728:6;23634:108;:::i;:::-;23626:116;;23524:225;;;;:::o;23755:210::-;23842:4;23880:2;23869:9;23865:18;23857:26;;23893:65;23955:1;23944:9;23940:17;23931:6;23893:65;:::i;:::-;23847:118;;;;:::o;23971:222::-;24064:4;24102:2;24091:9;24087:18;24079:26;;24115:71;24183:1;24172:9;24168:17;24159:6;24115:71;:::i;:::-;24069:124;;;;:::o;24199:313::-;24312:4;24350:2;24339:9;24335:18;24327:26;;24399:9;24393:4;24389:20;24385:1;24374:9;24370:17;24363:47;24427:78;24500:4;24491:6;24427:78;:::i;:::-;24419:86;;24317:195;;;;:::o;24518:419::-;24684:4;24722:2;24711:9;24707:18;24699:26;;24771:9;24765:4;24761:20;24757:1;24746:9;24742:17;24735:47;24799:131;24925:4;24799:131;:::i;:::-;24791:139;;24689:248;;;:::o;24943:419::-;25109:4;25147:2;25136:9;25132:18;25124:26;;25196:9;25190:4;25186:20;25182:1;25171:9;25167:17;25160:47;25224:131;25350:4;25224:131;:::i;:::-;25216:139;;25114:248;;;:::o;25368:419::-;25534:4;25572:2;25561:9;25557:18;25549:26;;25621:9;25615:4;25611:20;25607:1;25596:9;25592:17;25585:47;25649:131;25775:4;25649:131;:::i;:::-;25641:139;;25539:248;;;:::o;25793:419::-;25959:4;25997:2;25986:9;25982:18;25974:26;;26046:9;26040:4;26036:20;26032:1;26021:9;26017:17;26010:47;26074:131;26200:4;26074:131;:::i;:::-;26066:139;;25964:248;;;:::o;26218:419::-;26384:4;26422:2;26411:9;26407:18;26399:26;;26471:9;26465:4;26461:20;26457:1;26446:9;26442:17;26435:47;26499:131;26625:4;26499:131;:::i;:::-;26491:139;;26389:248;;;:::o;26643:419::-;26809:4;26847:2;26836:9;26832:18;26824:26;;26896:9;26890:4;26886:20;26882:1;26871:9;26867:17;26860:47;26924:131;27050:4;26924:131;:::i;:::-;26916:139;;26814:248;;;:::o;27068:419::-;27234:4;27272:2;27261:9;27257:18;27249:26;;27321:9;27315:4;27311:20;27307:1;27296:9;27292:17;27285:47;27349:131;27475:4;27349:131;:::i;:::-;27341:139;;27239:248;;;:::o;27493:419::-;27659:4;27697:2;27686:9;27682:18;27674:26;;27746:9;27740:4;27736:20;27732:1;27721:9;27717:17;27710:47;27774:131;27900:4;27774:131;:::i;:::-;27766:139;;27664:248;;;:::o;27918:343::-;28071:4;28109:3;28098:9;28094:19;28086:27;;28123:131;28251:1;28240:9;28236:17;28227:6;28123:131;:::i;:::-;28076:185;;;;:::o;28267:222::-;28360:4;28398:2;28387:9;28383:18;28375:26;;28411:71;28479:1;28468:9;28464:17;28455:6;28411:71;:::i;:::-;28365:124;;;;:::o;28495:332::-;28616:4;28654:2;28643:9;28639:18;28631:26;;28667:71;28735:1;28724:9;28720:17;28711:6;28667:71;:::i;:::-;28748:72;28816:2;28805:9;28801:18;28792:6;28748:72;:::i;:::-;28621:206;;;;;:::o;28833:218::-;28924:4;28962:2;28951:9;28947:18;28939:26;;28975:69;29041:1;29030:9;29026:17;29017:6;28975:69;:::i;:::-;28929:122;;;;:::o;29057:129::-;29091:6;29118:20;;:::i;:::-;29108:30;;29147:33;29175:4;29167:6;29147:33;:::i;:::-;29098:88;;;:::o;29192:75::-;29225:6;29258:2;29252:9;29242:19;;29232:35;:::o;29273:307::-;29334:4;29424:18;29416:6;29413:30;29410:2;;;29446:18;;:::i;:::-;29410:2;29484:29;29506:6;29484:29;:::i;:::-;29476:37;;29568:4;29562;29558:15;29550:23;;29339:241;;;:::o;29586:162::-;29683:4;29706:3;29698:11;;29736:4;29731:3;29727:14;29719:22;;29688:60;;;:::o;29754:132::-;29821:4;29844:3;29836:11;;29874:4;29869:3;29865:14;29857:22;;29826:60;;;:::o;29892:144::-;29989:6;30023:5;30017:12;30007:22;;29996:40;;;:::o;30042:114::-;30109:6;30143:5;30137:12;30127:22;;30116:40;;;:::o;30162:98::-;30213:6;30247:5;30241:12;30231:22;;30220:40;;;:::o;30266:99::-;30318:6;30352:5;30346:12;30336:22;;30325:40;;;:::o;30371:143::-;30471:4;30503;30498:3;30494:14;30486:22;;30476:38;;;:::o;30520:113::-;30590:4;30622;30617:3;30613:14;30605:22;;30595:38;;;:::o;30639:214::-;30768:11;30802:6;30797:3;30790:19;30842:4;30837:3;30833:14;30818:29;;30780:73;;;;:::o;30859:184::-;30958:11;30992:6;30987:3;30980:19;31032:4;31027:3;31023:14;31008:29;;30970:73;;;;:::o;31049:168::-;31132:11;31166:6;31161:3;31154:19;31206:4;31201:3;31197:14;31182:29;;31144:73;;;;:::o;31223:169::-;31307:11;31341:6;31336:3;31329:19;31381:4;31376:3;31372:14;31357:29;;31319:73;;;;:::o;31398:148::-;31500:11;31537:3;31522:18;;31512:34;;;;:::o;31552:305::-;31592:3;31611:20;31629:1;31611:20;:::i;:::-;31606:25;;31645:20;31663:1;31645:20;:::i;:::-;31640:25;;31799:1;31731:66;31727:74;31724:1;31721:81;31718:2;;;31805:18;;:::i;:::-;31718:2;31849:1;31846;31842:9;31835:16;;31596:261;;;;:::o;31863:185::-;31903:1;31920:20;31938:1;31920:20;:::i;:::-;31915:25;;31954:20;31972:1;31954:20;:::i;:::-;31949:25;;31993:1;31983:2;;31998:18;;:::i;:::-;31983:2;32040:1;32037;32033:9;32028:14;;31905:143;;;;:::o;32054:348::-;32094:7;32117:20;32135:1;32117:20;:::i;:::-;32112:25;;32151:20;32169:1;32151:20;:::i;:::-;32146:25;;32339:1;32271:66;32267:74;32264:1;32261:81;32256:1;32249:9;32242:17;32238:105;32235:2;;;32346:18;;:::i;:::-;32235:2;32394:1;32391;32387:9;32376:20;;32102:300;;;;:::o;32408:191::-;32448:4;32468:20;32486:1;32468:20;:::i;:::-;32463:25;;32502:20;32520:1;32502:20;:::i;:::-;32497:25;;32541:1;32538;32535:8;32532:2;;;32546:18;;:::i;:::-;32532:2;32591:1;32588;32584:9;32576:17;;32453:146;;;;:::o;32605:96::-;32642:7;32671:24;32689:5;32671:24;:::i;:::-;32660:35;;32650:51;;;:::o;32707:90::-;32741:7;32784:5;32777:13;32770:21;32759:32;;32749:48;;;:::o;32803:77::-;32840:7;32869:5;32858:16;;32848:32;;;:::o;32886:149::-;32922:7;32962:66;32955:5;32951:78;32940:89;;32930:105;;;:::o;33041:126::-;33078:7;33118:42;33111:5;33107:54;33096:65;;33086:81;;;:::o;33173:91::-;33209:7;33249:8;33242:5;33238:20;33227:31;;33217:47;;;:::o;33270:77::-;33307:7;33336:5;33325:16;;33315:32;;;:::o;33353:101::-;33389:7;33429:18;33422:5;33418:30;33407:41;;33397:57;;;:::o;33460:109::-;33496:7;33536:26;33529:5;33525:38;33514:49;;33504:65;;;:::o;33575:154::-;33659:6;33654:3;33649;33636:30;33721:1;33712:6;33707:3;33703:16;33696:27;33626:103;;;:::o;33735:307::-;33803:1;33813:113;33827:6;33824:1;33821:13;33813:113;;;33912:1;33907:3;33903:11;33897:18;33893:1;33888:3;33884:11;33877:39;33849:2;33846:1;33842:10;33837:15;;33813:113;;;33944:6;33941:1;33938:13;33935:2;;;34024:1;34015:6;34010:3;34006:16;33999:27;33935:2;33784:258;;;;:::o;34048:171::-;34087:3;34110:24;34128:5;34110:24;:::i;:::-;34101:33;;34156:4;34149:5;34146:15;34143:2;;;34164:18;;:::i;:::-;34143:2;34211:1;34204:5;34200:13;34193:20;;34091:128;;;:::o;34225:320::-;34269:6;34306:1;34300:4;34296:12;34286:22;;34353:1;34347:4;34343:12;34374:18;34364:2;;34430:4;34422:6;34418:17;34408:27;;34364:2;34492;34484:6;34481:14;34461:18;34458:38;34455:2;;;34511:18;;:::i;:::-;34455:2;34276:269;;;;:::o;34551:281::-;34634:27;34656:4;34634:27;:::i;:::-;34626:6;34622:40;34764:6;34752:10;34749:22;34728:18;34716:10;34713:34;34710:62;34707:2;;;34775:18;;:::i;:::-;34707:2;34815:10;34811:2;34804:22;34594:238;;;:::o;34838:180::-;34886:77;34883:1;34876:88;34983:4;34980:1;34973:15;35007:4;35004:1;34997:15;35024:180;35072:77;35069:1;35062:88;35169:4;35166:1;35159:15;35193:4;35190:1;35183:15;35210:180;35258:77;35255:1;35248:88;35355:4;35352:1;35345:15;35379:4;35376:1;35369:15;35396:180;35444:77;35441:1;35434:88;35541:4;35538:1;35531:15;35565:4;35562:1;35555:15;35582:102;35623:6;35674:2;35670:7;35665:2;35658:5;35654:14;35650:28;35640:38;;35630:54;;;:::o;35690:182::-;35830:34;35826:1;35818:6;35814:14;35807:58;35796:76;:::o;35878:167::-;36018:19;36014:1;36006:6;36002:14;35995:43;35984:61;:::o;36051:171::-;36191:23;36187:1;36179:6;36175:14;36168:47;36157:65;:::o;36228:168::-;36368:20;36364:1;36356:6;36352:14;36345:44;36334:62;:::o;36402:177::-;36542:29;36538:1;36530:6;36526:14;36519:53;36508:71;:::o;36585:173::-;36725:25;36721:1;36713:6;36709:14;36702:49;36691:67;:::o;36764:229::-;36904:34;36900:1;36892:6;36888:14;36881:58;36973:12;36968:2;36960:6;36956:15;36949:37;36870:123;:::o;36999:175::-;37139:27;37135:1;37127:6;37123:14;37116:51;37105:69;:::o;37180:167::-;37320:19;37316:1;37308:6;37304:14;37297:43;37286:61;:::o;37353:234::-;37493:34;37489:1;37481:6;37477:14;37470:58;37562:17;37557:2;37549:6;37545:15;37538:42;37459:128;:::o;37593:122::-;37666:24;37684:5;37666:24;:::i;:::-;37659:5;37656:35;37646:2;;37705:1;37702;37695:12;37646:2;37636:79;:::o;37721:116::-;37791:21;37806:5;37791:21;:::i;:::-;37784:5;37781:32;37771:2;;37827:1;37824;37817:12;37771:2;37761:76;:::o;37843:122::-;37916:24;37934:5;37916:24;:::i;:::-;37909:5;37906:35;37896:2;;37955:1;37952;37945:12;37896:2;37886:79;:::o;37971:120::-;38043:23;38060:5;38043:23;:::i;:::-;38036:5;38033:34;38023:2;;38081:1;38078;38071:12;38023:2;38013:78;:::o;38097:122::-;38170:24;38188:5;38170:24;:::i;:::-;38163:5;38160:35;38150:2;;38209:1;38206;38199:12;38150:2;38140:79;:::o;38225:120::-;38297:23;38314:5;38297:23;:::i;:::-;38290:5;38287:34;38277:2;;38335:1;38332;38325:12;38277:2;38267:78;:::o
Swarm Source
ipfs://7c755d20770f722879594472df615ea301b913f4ff5e739aa17e030bf0789cca
Loading...
Loading
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 30 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|
[ 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.