ERC-721
Overview
Max Total Supply
445 GT
Holders
190
Total Transfers
-
Market
Volume (24H)
N/A
Min Price (24H)
N/A
Max Price (24H)
N/A
Other Info
Token Contract
Loading...
Loading
Loading...
Loading
Loading...
Loading
# | Exchange | Pair | Price | 24H Volume | % Volume |
---|
Contract Source Code Verified (Exact Match)
Contract Name:
GiftedTigers
Compiler Version
v0.8.11+commit.d7f03943
Contract Source Code (Solidity Multiple files format)
// SPDX-License-Identifier: MIT pragma solidity ^0.8.11; import "./ERC721A.sol"; import "./MerkleProof.sol"; import "./Ownable.sol"; contract GiftedTigers is ERC721A, Ownable { uint256 public mintPrice = 0.085 ether; uint256 public presalePrice = 0.075 ether; uint256 private reserveAtATime = 100; uint256 private reservedCount = 0; uint256 private maxReserveCount = 100; bytes32 public merkleRoot; string _baseTokenURI; bool public isActive = true; bool public isPresaleActive = false; uint256 public MAX_SUPPLY = 8888; uint256 public maximumAllowedTokensPerPurchase = 10; uint256 public maximumAllowedTokensPerWallet = 20; constructor(string memory baseURI) ERC721A("GiftedTigers", "GT") { setBaseURI(baseURI); } modifier saleIsOpen { require(totalSupply() <= MAX_SUPPLY, "Sale has ended."); _; } modifier isValidMerkleProof(bytes32[] calldata merkleProof) { require( MerkleProof.verify( merkleProof, merkleRoot, keccak256(abi.encodePacked(msg.sender)) ), "Address does not exist in list" ); _; } function setMerkleRootHash(bytes32 _rootHash) public onlyOwner { merkleRoot = _rootHash; } function setMaxReserve(uint256 val) public onlyOwner { maxReserveCount = val; } function setReserveAtATime(uint256 val) public onlyOwner { reserveAtATime = val; } function getReserveAtATime() external view returns (uint256) { return reserveAtATime; } function setMaximumAllowedTokens(uint256 _count) public onlyOwner { maximumAllowedTokensPerPurchase = _count; } function setMaximumAllowedTokensPerWallet(uint256 _count) public onlyOwner { maximumAllowedTokensPerWallet = _count; } function setMaxMintSupply(uint256 maxMintSupply) external onlyOwner { MAX_SUPPLY = maxMintSupply; } function setPrice(uint256 _price) public onlyOwner { mintPrice = _price; } function setPresalePrice(uint256 _preslaePrice) public onlyOwner { presalePrice = _preslaePrice; } function toggleSaleStatus() public onlyOwner { isActive = !isActive; } function togglePresaleStatus() external onlyOwner { isPresaleActive = !isPresaleActive; } function setBaseURI(string memory baseURI) public onlyOwner { _baseTokenURI = baseURI; } function _baseURI() internal view virtual override returns (string memory) { return _baseTokenURI; } function airdrop(uint256 _count, address _address) external onlyOwner { uint256 supply = totalSupply(); require(supply + _count <= MAX_SUPPLY, "Total supply exceeded."); require(supply <= MAX_SUPPLY, "Total supply spent."); _safeMint(_address, _count); } function batchAirdrop(uint256 _count, address[] calldata addresses) external onlyOwner { uint256 supply = totalSupply(); require(supply + _count <= MAX_SUPPLY, "Total supply exceeded."); require(supply <= MAX_SUPPLY, "Total supply spent."); for (uint256 i = 0; i < addresses.length; i++) { require(addresses[i] != address(0), "Can't add a null address"); _safeMint(addresses[i], _count); } } function mint(uint256 _count) public payable saleIsOpen { uint256 mintIndex = totalSupply(); uint256 counter = 0; if (msg.sender != owner()) { require(isActive, "Sale is not active currently."); require(balanceOf(msg.sender) + _count <= maximumAllowedTokensPerWallet, "Max holding cap reached."); } require(mintIndex + _count <= MAX_SUPPLY, "Total supply exceeded."); require( _count <= maximumAllowedTokensPerPurchase, "Exceeds maximum allowed tokens"); for(uint256 i = balanceOf(msg.sender) + 1; i <= balanceOf(msg.sender) + _count; i++) { if(i % 5 == 0) { counter++; } } require(msg.value >= (mintPrice * (_count - counter)), "Insufficient ETH amount sent."); _safeMint(msg.sender, _count); } function preSaleMint(bytes32[] calldata _merkleProof, uint256 _count) public payable isValidMerkleProof(_merkleProof) saleIsOpen { uint256 mintIndex = totalSupply(); uint256 counter = 0; require(isPresaleActive, "Presale is not active"); require(mintIndex < MAX_SUPPLY, "All tokens have been minted"); require(balanceOf(msg.sender) + _count <= maximumAllowedTokensPerWallet, "Cannot purchase this many tokens"); for(uint256 i = balanceOf(msg.sender) + 1; i <= balanceOf(msg.sender) + _count; i++) { if(i % 4 == 0) { counter++; } } require(msg.value >= (presalePrice * (_count - counter)), "Insufficient ETH amount sent."); _safeMint(msg.sender, _count); } function withdraw() external onlyOwner { uint balance = address(this).balance; payable(owner()).transfer(balance); } }
// SPDX-License-Identifier: MIT // 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; } }
// SPDX-License-Identifier: MIT // ERC721A Contracts v4.2.2 // Creator: Chiru Labs pragma solidity ^0.8.4; import './IERC721A.sol'; /** * @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) } } }
// 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); }
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts (last updated v4.7.0) (utils/cryptography/MerkleProof.sol) pragma solidity ^0.8.0; /** * @dev These functions deal with verification of Merkle Tree proofs. * * The proofs can be generated using the JavaScript library * https://github.com/miguelmota/merkletreejs[merkletreejs]. * Note: the hashing algorithm should be keccak256 and pair sorting should be enabled. * * See `test/utils/cryptography/MerkleProof.test.js` for some examples. * * WARNING: You should avoid using leaf values that are 64 bytes long prior to * hashing, or use a hash function other than keccak256 for hashing leaves. * This is because the concatenation of a sorted pair of internal nodes in * the merkle tree could be reinterpreted as a leaf value. */ library MerkleProof { /** * @dev Returns true if a `leaf` can be proved to be a part of a Merkle tree * defined by `root`. For this, a `proof` must be provided, containing * sibling hashes on the branch from the leaf to the root of the tree. Each * pair of leaves and each pair of pre-images are assumed to be sorted. */ function verify( bytes32[] memory proof, bytes32 root, bytes32 leaf ) internal pure returns (bool) { return processProof(proof, leaf) == root; } /** * @dev Calldata version of {verify} * * _Available since v4.7._ */ function verifyCalldata( bytes32[] calldata proof, bytes32 root, bytes32 leaf ) internal pure returns (bool) { return processProofCalldata(proof, leaf) == root; } /** * @dev Returns the rebuilt hash obtained by traversing a Merkle tree up * from `leaf` using `proof`. A `proof` is valid if and only if the rebuilt * hash matches the root of the tree. When processing the proof, the pairs * of leafs & pre-images are assumed to be sorted. * * _Available since v4.4._ */ function processProof(bytes32[] memory proof, bytes32 leaf) internal pure returns (bytes32) { bytes32 computedHash = leaf; for (uint256 i = 0; i < proof.length; i++) { computedHash = _hashPair(computedHash, proof[i]); } return computedHash; } /** * @dev Calldata version of {processProof} * * _Available since v4.7._ */ function processProofCalldata(bytes32[] calldata proof, bytes32 leaf) internal pure returns (bytes32) { bytes32 computedHash = leaf; for (uint256 i = 0; i < proof.length; i++) { computedHash = _hashPair(computedHash, proof[i]); } return computedHash; } /** * @dev Returns true if the `leaves` can be proved to be a part of a Merkle tree defined by * `root`, according to `proof` and `proofFlags` as described in {processMultiProof}. * * _Available since v4.7._ */ function multiProofVerify( bytes32[] memory proof, bool[] memory proofFlags, bytes32 root, bytes32[] memory leaves ) internal pure returns (bool) { return processMultiProof(proof, proofFlags, leaves) == root; } /** * @dev Calldata version of {multiProofVerify} * * _Available since v4.7._ */ function multiProofVerifyCalldata( bytes32[] calldata proof, bool[] calldata proofFlags, bytes32 root, bytes32[] memory leaves ) internal pure returns (bool) { return processMultiProofCalldata(proof, proofFlags, leaves) == root; } /** * @dev Returns the root of a tree reconstructed from `leaves` and the sibling nodes in `proof`, * consuming from one or the other at each step according to the instructions given by * `proofFlags`. * * _Available since v4.7._ */ function processMultiProof( bytes32[] memory proof, bool[] memory proofFlags, bytes32[] memory leaves ) internal pure returns (bytes32 merkleRoot) { // This function rebuild the root hash by traversing the tree up from the leaves. The root is rebuilt by // consuming and producing values on a queue. The queue starts with the `leaves` array, then goes onto the // `hashes` array. At the end of the process, the last hash in the `hashes` array should contain the root of // the merkle tree. uint256 leavesLen = leaves.length; uint256 totalHashes = proofFlags.length; // Check proof validity. require(leavesLen + proof.length - 1 == totalHashes, "MerkleProof: invalid multiproof"); // The xxxPos values are "pointers" to the next value to consume in each array. All accesses are done using // `xxx[xxxPos++]`, which return the current value and increment the pointer, thus mimicking a queue's "pop". bytes32[] memory hashes = new bytes32[](totalHashes); uint256 leafPos = 0; uint256 hashPos = 0; uint256 proofPos = 0; // At each step, we compute the next hash using two values: // - a value from the "main queue". If not all leaves have been consumed, we get the next leaf, otherwise we // get the next hash. // - depending on the flag, either another value for the "main queue" (merging branches) or an element from the // `proof` array. for (uint256 i = 0; i < totalHashes; i++) { bytes32 a = leafPos < leavesLen ? leaves[leafPos++] : hashes[hashPos++]; bytes32 b = proofFlags[i] ? leafPos < leavesLen ? leaves[leafPos++] : hashes[hashPos++] : proof[proofPos++]; hashes[i] = _hashPair(a, b); } if (totalHashes > 0) { return hashes[totalHashes - 1]; } else if (leavesLen > 0) { return leaves[0]; } else { return proof[0]; } } /** * @dev Calldata version of {processMultiProof} * * _Available since v4.7._ */ function processMultiProofCalldata( bytes32[] calldata proof, bool[] calldata proofFlags, bytes32[] memory leaves ) internal pure returns (bytes32 merkleRoot) { // This function rebuild the root hash by traversing the tree up from the leaves. The root is rebuilt by // consuming and producing values on a queue. The queue starts with the `leaves` array, then goes onto the // `hashes` array. At the end of the process, the last hash in the `hashes` array should contain the root of // the merkle tree. uint256 leavesLen = leaves.length; uint256 totalHashes = proofFlags.length; // Check proof validity. require(leavesLen + proof.length - 1 == totalHashes, "MerkleProof: invalid multiproof"); // The xxxPos values are "pointers" to the next value to consume in each array. All accesses are done using // `xxx[xxxPos++]`, which return the current value and increment the pointer, thus mimicking a queue's "pop". bytes32[] memory hashes = new bytes32[](totalHashes); uint256 leafPos = 0; uint256 hashPos = 0; uint256 proofPos = 0; // At each step, we compute the next hash using two values: // - a value from the "main queue". If not all leaves have been consumed, we get the next leaf, otherwise we // get the next hash. // - depending on the flag, either another value for the "main queue" (merging branches) or an element from the // `proof` array. for (uint256 i = 0; i < totalHashes; i++) { bytes32 a = leafPos < leavesLen ? leaves[leafPos++] : hashes[hashPos++]; bytes32 b = proofFlags[i] ? leafPos < leavesLen ? leaves[leafPos++] : hashes[hashPos++] : proof[proofPos++]; hashes[i] = _hashPair(a, b); } if (totalHashes > 0) { return hashes[totalHashes - 1]; } else if (leavesLen > 0) { return leaves[0]; } else { return proof[0]; } } function _hashPair(bytes32 a, bytes32 b) private pure returns (bytes32) { return a < b ? _efficientHash(a, b) : _efficientHash(b, a); } function _efficientHash(bytes32 a, bytes32 b) private pure returns (bytes32 value) { /// @solidity memory-safe-assembly assembly { mstore(0x00, a) mstore(0x20, b) value := keccak256(0x00, 0x40) } } }
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol) pragma solidity ^0.8.0; import "./Context.sol"; /** * @dev Contract module which provides a basic access control mechanism, where * there is an account (an owner) that can be granted exclusive access to * specific functions. * * By default, the owner account will be the one that deploys the contract. This * can later be changed with {transferOwnership}. * * This module is used through inheritance. It will make available the modifier * `onlyOwner`, which can be applied to your functions to restrict their use to * the owner. */ abstract contract Ownable is Context { address private _owner; event OwnershipTransferred(address indexed previousOwner, address indexed newOwner); /** * @dev Initializes the contract setting the deployer as the initial owner. */ constructor() { _transferOwnership(_msgSender()); } /** * @dev Throws if called by any account other than the owner. */ modifier onlyOwner() { _checkOwner(); _; } /** * @dev Returns the address of the current owner. */ function owner() public view virtual returns (address) { return _owner; } /** * @dev Throws if the sender is not the owner. */ function _checkOwner() internal view virtual { require(owner() == _msgSender(), "Ownable: caller is not the owner"); } /** * @dev Leaves the contract without owner. It will not be possible to call * `onlyOwner` functions anymore. Can only be called by the current owner. * * NOTE: Renouncing ownership will leave the contract without an owner, * thereby removing any functionality that is only available to the owner. */ function renounceOwnership() public virtual onlyOwner { _transferOwnership(address(0)); } /** * @dev Transfers ownership of the contract to a new account (`newOwner`). * Can only be called by the current owner. */ function transferOwnership(address newOwner) public virtual onlyOwner { require(newOwner != address(0), "Ownable: new owner is the zero address"); _transferOwnership(newOwner); } /** * @dev Transfers ownership of the contract to a new account (`newOwner`). * Internal function without access restriction. */ function _transferOwnership(address newOwner) internal virtual { address oldOwner = _owner; _owner = newOwner; emit OwnershipTransferred(oldOwner, newOwner); } }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"string","name":"baseURI","type":"string"}],"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":"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":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"inputs":[],"name":"MAX_SUPPLY","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_count","type":"uint256"},{"internalType":"address","name":"_address","type":"address"}],"name":"airdrop","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_count","type":"uint256"},{"internalType":"address[]","name":"addresses","type":"address[]"}],"name":"batchAirdrop","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getReserveAtATime","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"isActive","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":"isPresaleActive","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maximumAllowedTokensPerPurchase","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maximumAllowedTokensPerWallet","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"merkleRoot","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_count","type":"uint256"}],"name":"mint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"mintPrice","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"ownerOf","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32[]","name":"_merkleProof","type":"bytes32[]"},{"internalType":"uint256","name":"_count","type":"uint256"}],"name":"preSaleMint","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"presalePrice","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","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":"baseURI","type":"string"}],"name":"setBaseURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"maxMintSupply","type":"uint256"}],"name":"setMaxMintSupply","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"val","type":"uint256"}],"name":"setMaxReserve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_count","type":"uint256"}],"name":"setMaximumAllowedTokens","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_count","type":"uint256"}],"name":"setMaximumAllowedTokensPerWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"_rootHash","type":"bytes32"}],"name":"setMerkleRootHash","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_preslaePrice","type":"uint256"}],"name":"setPresalePrice","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_price","type":"uint256"}],"name":"setPrice","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"val","type":"uint256"}],"name":"setReserveAtATime","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"togglePresaleStatus","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"toggleSaleStatus","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"withdraw","outputs":[],"stateMutability":"nonpayable","type":"function"}]
Contract Creation Code
608060405267012dfb0cb5e8800060095567010a741a46278000600a556064600b556000600c556064600d556001601060006101000a81548160ff0219169083151502179055506000601060016101000a81548160ff0219169083151502179055506122b8601155600a60125560146013553480156200007e57600080fd5b50604051620041c5380380620041c58339818101604052810190620000a4919062000599565b6040518060400160405280600c81526020017f47696674656454696765727300000000000000000000000000000000000000008152506040518060400160405280600281526020017f47540000000000000000000000000000000000000000000000000000000000008152508160029080519060200190620001289291906200034c565b508060039080519060200190620001419291906200034c565b50620001526200019260201b60201c565b60008190555050506200017a6200016e6200019760201b60201c565b6200019f60201b60201c565b6200018b816200026560201b60201c565b50620006d2565b600090565b600033905090565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905081600860006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a35050565b620002756200029160201b60201c565b80600f90805190602001906200028d9291906200034c565b5050565b620002a16200019760201b60201c565b73ffffffffffffffffffffffffffffffffffffffff16620002c76200032260201b60201c565b73ffffffffffffffffffffffffffffffffffffffff161462000320576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040162000317906200064b565b60405180910390fd5b565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b8280546200035a906200069c565b90600052602060002090601f0160209004810192826200037e5760008555620003ca565b82601f106200039957805160ff1916838001178555620003ca565b82800160010185558215620003ca579182015b82811115620003c9578251825591602001919060010190620003ac565b5b509050620003d99190620003dd565b5090565b5b80821115620003f8576000816000905550600101620003de565b5090565b6000604051905090565b600080fd5b600080fd5b600080fd5b600080fd5b6000601f19601f8301169050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b62000465826200041a565b810181811067ffffffffffffffff821117156200048757620004866200042b565b5b80604052505050565b60006200049c620003fc565b9050620004aa82826200045a565b919050565b600067ffffffffffffffff821115620004cd57620004cc6200042b565b5b620004d8826200041a565b9050602081019050919050565b60005b8381101562000505578082015181840152602081019050620004e8565b8381111562000515576000848401525b50505050565b6000620005326200052c84620004af565b62000490565b90508281526020810184848401111562000551576200055062000415565b5b6200055e848285620004e5565b509392505050565b600082601f8301126200057e576200057d62000410565b5b8151620005908482602086016200051b565b91505092915050565b600060208284031215620005b257620005b162000406565b5b600082015167ffffffffffffffff811115620005d357620005d26200040b565b5b620005e18482850162000566565b91505092915050565b600082825260208201905092915050565b7f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572600082015250565b600062000633602083620005ea565b91506200064082620005fb565b602082019050919050565b60006020820190508181036000830152620006668162000624565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b60006002820490506001821680620006b557607f821691505b60208210811415620006cc57620006cb6200066d565b5b50919050565b613ae380620006e26000396000f3fe6080604052600436106102505760003560e01c8063715018a611610139578063a22cb465116100b6578063e7b62d961161007a578063e7b62d9614610833578063e985e9c51461085e578063ea6eb8361461089b578063f2fde38b146108c4578063f6c9d9e3146108ed578063fb7e6ccb1461091657610250565b8063a22cb46514610750578063b88d4fde14610779578063bc63f02e146107a2578063c87b56dd146107cb578063cadf88181461080857610250565b806391b7f5ed116100fd57806391b7f5ed1461068c57806395d89b41146106b55780639a3bf728146106e05780639ba411b11461070b578063a0712d681461073457610250565b8063715018a6146105ee5780637389fbb714610605578063781799761461062e5780637bffb4ce1461064a5780638da5cb5b1461066157610250565b806332cb6b0c116101d257806355f804b31161019657806355f804b3146104cc57806356a87caa146104f557806360d938dc1461051e5780636352211e146105495780636817c76c1461058657806370a08231146105b157610250565b806332cb6b0c1461040f5780633549345e1461043a5780633ccfd60b1461046357806342842e0e1461047a5780634dfea627146104a357610250565b8063095ea7b311610219578063095ea7b31461033c57806318160ddd1461036557806322f3e2d41461039057806323b872dd146103bb5780632eb4a7ab146103e457610250565b80620e7fa81461025557806301ffc9a714610280578063049c5c49146102bd57806306fdde03146102d4578063081812fc146102ff575b600080fd5b34801561026157600080fd5b5061026a61093f565b60405161027791906127d6565b60405180910390f35b34801561028c57600080fd5b506102a760048036038101906102a2919061285d565b610945565b6040516102b491906128a5565b60405180910390f35b3480156102c957600080fd5b506102d26109d7565b005b3480156102e057600080fd5b506102e9610a0b565b6040516102f69190612959565b60405180910390f35b34801561030b57600080fd5b50610326600480360381019061032191906129a7565b610a9d565b6040516103339190612a15565b60405180910390f35b34801561034857600080fd5b50610363600480360381019061035e9190612a5c565b610b1c565b005b34801561037157600080fd5b5061037a610c60565b60405161038791906127d6565b60405180910390f35b34801561039c57600080fd5b506103a5610c77565b6040516103b291906128a5565b60405180910390f35b3480156103c757600080fd5b506103e260048036038101906103dd9190612a9c565b610c8a565b005b3480156103f057600080fd5b506103f9610faf565b6040516104069190612b08565b60405180910390f35b34801561041b57600080fd5b50610424610fb5565b60405161043191906127d6565b60405180910390f35b34801561044657600080fd5b50610461600480360381019061045c91906129a7565b610fbb565b005b34801561046f57600080fd5b50610478610fcd565b005b34801561048657600080fd5b506104a1600480360381019061049c9190612a9c565b61102b565b005b3480156104af57600080fd5b506104ca60048036038101906104c591906129a7565b61104b565b005b3480156104d857600080fd5b506104f360048036038101906104ee9190612c58565b61105d565b005b34801561050157600080fd5b5061051c600480360381019061051791906129a7565b61107f565b005b34801561052a57600080fd5b50610533611091565b60405161054091906128a5565b60405180910390f35b34801561055557600080fd5b50610570600480360381019061056b91906129a7565b6110a4565b60405161057d9190612a15565b60405180910390f35b34801561059257600080fd5b5061059b6110b6565b6040516105a891906127d6565b60405180910390f35b3480156105bd57600080fd5b506105d860048036038101906105d39190612ca1565b6110bc565b6040516105e591906127d6565b60405180910390f35b3480156105fa57600080fd5b50610603611175565b005b34801561061157600080fd5b5061062c600480360381019061062791906129a7565b611189565b005b61064860048036038101906106439190612d2e565b61119b565b005b34801561065657600080fd5b5061065f61146f565b005b34801561066d57600080fd5b506106766114a3565b6040516106839190612a15565b60405180910390f35b34801561069857600080fd5b506106b360048036038101906106ae91906129a7565b6114cd565b005b3480156106c157600080fd5b506106ca6114df565b6040516106d79190612959565b60405180910390f35b3480156106ec57600080fd5b506106f5611571565b60405161070291906127d6565b60405180910390f35b34801561071757600080fd5b50610732600480360381019061072d9190612dba565b611577565b005b61074e600480360381019061074991906129a7565b611589565b005b34801561075c57600080fd5b5061077760048036038101906107729190612e13565b611830565b005b34801561078557600080fd5b506107a0600480360381019061079b9190612ef4565b6119a8565b005b3480156107ae57600080fd5b506107c960048036038101906107c49190612f77565b611a1b565b005b3480156107d757600080fd5b506107f260048036038101906107ed91906129a7565b611ad3565b6040516107ff9190612959565b60405180910390f35b34801561081457600080fd5b5061081d611b72565b60405161082a91906127d6565b60405180910390f35b34801561083f57600080fd5b50610848611b78565b60405161085591906127d6565b60405180910390f35b34801561086a57600080fd5b5061088560048036038101906108809190612fb7565b611b82565b60405161089291906128a5565b60405180910390f35b3480156108a757600080fd5b506108c260048036038101906108bd91906129a7565b611c16565b005b3480156108d057600080fd5b506108eb60048036038101906108e69190612ca1565b611c28565b005b3480156108f957600080fd5b50610914600480360381019061090f91906129a7565b611cac565b005b34801561092257600080fd5b5061093d6004803603810190610938919061304d565b611cbe565b005b600a5481565b60006301ffc9a760e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614806109a057506380ac58cd60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b806109d05750635b5e139f60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b9050919050565b6109df611e57565b601060009054906101000a900460ff1615601060006101000a81548160ff021916908315150217905550565b606060028054610a1a906130dc565b80601f0160208091040260200160405190810160405280929190818152602001828054610a46906130dc565b8015610a935780601f10610a6857610100808354040283529160200191610a93565b820191906000526020600020905b815481529060010190602001808311610a7657829003601f168201915b5050505050905090565b6000610aa882611ed5565b610ade576040517fcf4700e400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6006600083815260200190815260200160002060000160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff169050919050565b6000610b27826110a4565b90508073ffffffffffffffffffffffffffffffffffffffff16610b48611f34565b73ffffffffffffffffffffffffffffffffffffffff1614610bab57610b7481610b6f611f34565b611b82565b610baa576040517fcfb3b94200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b826006600084815260200190815260200160002060000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550818373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a4505050565b6000610c6a611f3c565b6001546000540303905090565b601060009054906101000a900460ff1681565b6000610c9582611f41565b90508373ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614610cfc576040517fa114810000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b600080610d088461200f565b91509150610d1e8187610d19611f34565b612036565b610d6a57610d3386610d2e611f34565b611b82565b610d69576040517f59c896be00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415610dd1576040517fea553b3400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610dde868686600161207a565b8015610de957600082555b600560008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600081546001900391905081905550600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000815460010191905081905550610eb785610e93888887612080565b7c0200000000000000000000000000000000000000000000000000000000176120a8565b600460008681526020019081526020016000208190555060007c020000000000000000000000000000000000000000000000000000000084161415610f3f576000600185019050600060046000838152602001908152602001600020541415610f3d576000548114610f3c578360046000838152602001908152602001600020819055505b5b505b838573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4610fa786868660016120d3565b505050505050565b600e5481565b60115481565b610fc3611e57565b80600a8190555050565b610fd5611e57565b6000479050610fe26114a3565b73ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015611027573d6000803e3d6000fd5b5050565b611046838383604051806020016040528060008152506119a8565b505050565b611053611e57565b8060128190555050565b611065611e57565b80600f908051906020019061107b92919061271a565b5050565b611087611e57565b80600d8190555050565b601060019054906101000a900460ff1681565b60006110af82611f41565b9050919050565b60095481565b60008073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611124576040517f8f4eb60400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b67ffffffffffffffff600560008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054169050919050565b61117d611e57565b61118760006120d9565b565b611191611e57565b8060118190555050565b8282611211828280806020026020016040519081016040528093929190818152602001838360200280828437600081840152601f19601f82011690508083019250505050505050600e54336040516020016111f69190613156565b6040516020818303038152906040528051906020012061219f565b611250576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611247906131bd565b60405180910390fd5b60115461125b610c60565b111561129c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161129390613229565b60405180910390fd5b60006112a6610c60565b90506000601060019054906101000a900460ff166112f9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016112f090613295565b60405180910390fd5b601154821061133d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161133490613301565b60405180910390fd5b6013548561134a336110bc565b6113549190613350565b1115611395576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161138c906133f2565b60405180910390fd5b600060016113a2336110bc565b6113ac9190613350565b90505b856113b9336110bc565b6113c39190613350565b81116114005760006004826113d89190613441565b14156113ed5781806113e990613472565b9250505b80806113f890613472565b9150506113af565b50808561140d91906134bb565b600a5461141a91906134ef565b34101561145c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161145390613595565b60405180910390fd5b61146633866121b6565b50505050505050565b611477611e57565b601060019054906101000a900460ff1615601060016101000a81548160ff021916908315150217905550565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6114d5611e57565b8060098190555050565b6060600380546114ee906130dc565b80601f016020809104026020016040519081016040528092919081815260200182805461151a906130dc565b80156115675780601f1061153c57610100808354040283529160200191611567565b820191906000526020600020905b81548152906001019060200180831161154a57829003601f168201915b5050505050905090565b60125481565b61157f611e57565b80600e8190555050565b601154611594610c60565b11156115d5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016115cc90613229565b60405180910390fd5b60006115df610c60565b905060006115eb6114a3565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146116c557601060009054906101000a900460ff1661166c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161166390613601565b60405180910390fd5b60135483611679336110bc565b6116839190613350565b11156116c4576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016116bb9061366d565b60405180910390fd5b5b60115483836116d49190613350565b1115611715576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161170c906136d9565b60405180910390fd5b60125483111561175a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161175190613745565b60405180910390fd5b60006001611767336110bc565b6117719190613350565b90505b8361177e336110bc565b6117889190613350565b81116117c557600060058261179d9190613441565b14156117b25781806117ae90613472565b9250505b80806117bd90613472565b915050611774565b5080836117d291906134bb565b6009546117df91906134ef565b341015611821576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161181890613595565b60405180910390fd5b61182b33846121b6565b505050565b611838611f34565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141561189d576040517fb06307db00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b80600760006118aa611f34565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055508173ffffffffffffffffffffffffffffffffffffffff16611957611f34565b73ffffffffffffffffffffffffffffffffffffffff167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c318360405161199c91906128a5565b60405180910390a35050565b6119b3848484610c8a565b60008373ffffffffffffffffffffffffffffffffffffffff163b14611a15576119de848484846121d4565b611a14576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b50505050565b611a23611e57565b6000611a2d610c60565b90506011548382611a3e9190613350565b1115611a7f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611a76906136d9565b60405180910390fd5b601154811115611ac4576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611abb906137b1565b60405180910390fd5b611ace82846121b6565b505050565b6060611ade82611ed5565b611b14576040517fa14c4b5000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000611b1e612325565b9050600081511415611b3f5760405180602001604052806000815250611b6a565b80611b49846123b7565b604051602001611b5a92919061380d565b6040516020818303038152906040525b915050919050565b60135481565b6000600b54905090565b6000600760008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b611c1e611e57565b8060138190555050565b611c30611e57565b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415611ca0576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611c97906138a3565b60405180910390fd5b611ca9816120d9565b50565b611cb4611e57565b80600b8190555050565b611cc6611e57565b6000611cd0610c60565b90506011548482611ce19190613350565b1115611d22576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611d19906136d9565b60405180910390fd5b601154811115611d67576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611d5e906137b1565b60405180910390fd5b60005b83839050811015611e5057600073ffffffffffffffffffffffffffffffffffffffff16848483818110611da057611d9f6138c3565b5b9050602002016020810190611db59190612ca1565b73ffffffffffffffffffffffffffffffffffffffff161415611e0c576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611e039061393e565b60405180910390fd5b611e3d848483818110611e2257611e216138c3565b5b9050602002016020810190611e379190612ca1565b866121b6565b8080611e4890613472565b915050611d6a565b5050505050565b611e5f612407565b73ffffffffffffffffffffffffffffffffffffffff16611e7d6114a3565b73ffffffffffffffffffffffffffffffffffffffff1614611ed3576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611eca906139aa565b60405180910390fd5b565b600081611ee0611f3c565b11158015611eef575060005482105b8015611f2d575060007c0100000000000000000000000000000000000000000000000000000000600460008581526020019081526020016000205416145b9050919050565b600033905090565b600090565b60008082905080611f50611f3c565b11611fd857600054811015611fd75760006004600083815260200190815260200160002054905060007c010000000000000000000000000000000000000000000000000000000082161415611fd5575b6000811415611fcb576004600083600190039350838152602001908152602001600020549050611fa0565b809250505061200a565b505b5b6040517fdf2d9b4200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b919050565b60008060006006600085815260200190815260200160002090508092508254915050915091565b600073ffffffffffffffffffffffffffffffffffffffff8316925073ffffffffffffffffffffffffffffffffffffffff821691508382148383141790509392505050565b50505050565b60008060e883901c905060e861209786868461240f565b62ffffff16901b9150509392505050565b600073ffffffffffffffffffffffffffffffffffffffff83169250814260a01b178317905092915050565b50505050565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905081600860006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a35050565b6000826121ac8584612418565b1490509392505050565b6121d082826040518060200160405280600081525061246e565b5050565b60008373ffffffffffffffffffffffffffffffffffffffff1663150b7a026121fa611f34565b8786866040518563ffffffff1660e01b815260040161221c9493929190613a1f565b6020604051808303816000875af192505050801561225857506040513d601f19601f820116820180604052508101906122559190613a80565b60015b6122d2573d8060008114612288576040519150601f19603f3d011682016040523d82523d6000602084013e61228d565b606091505b506000815114156122ca576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805181602001fd5b63150b7a0260e01b7bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916817bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614915050949350505050565b6060600f8054612334906130dc565b80601f0160208091040260200160405190810160405280929190818152602001828054612360906130dc565b80156123ad5780601f10612382576101008083540402835291602001916123ad565b820191906000526020600020905b81548152906001019060200180831161239057829003601f168201915b5050505050905090565b606060806040510190508060405280825b6001156123f357600183039250600a81066030018353600a81049050806123ee576123f3565b6123c8565b508181036020830392508083525050919050565b600033905090565b60009392505050565b60008082905060005b84518110156124635761244e82868381518110612441576124406138c3565b5b602002602001015161250b565b9150808061245b90613472565b915050612421565b508091505092915050565b6124788383612536565b60008373ffffffffffffffffffffffffffffffffffffffff163b1461250657600080549050600083820390505b6124b860008683806001019450866121d4565b6124ee576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8181106124a557816000541461250357600080fd5b50505b505050565b60008183106125235761251e82846126f3565b61252e565b61252d83836126f3565b5b905092915050565b6000805490506000821415612577576040517fb562e8dd00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b612584600084838561207a565b600160406001901b178202600560008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055506125fb836125ec6000866000612080565b6125f58561270a565b176120a8565b6004600083815260200190815260200160002081905550600080838301905073ffffffffffffffffffffffffffffffffffffffff85169150828260007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600183015b81811461269c57808360007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600181019050612661565b5060008214156126d8576040517f2e07630000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060008190555050506126ee60008483856120d3565b505050565b600082600052816020526040600020905092915050565b60006001821460e11b9050919050565b828054612726906130dc565b90600052602060002090601f016020900481019282612748576000855561278f565b82601f1061276157805160ff191683800117855561278f565b8280016001018555821561278f579182015b8281111561278e578251825591602001919060010190612773565b5b50905061279c91906127a0565b5090565b5b808211156127b95760008160009055506001016127a1565b5090565b6000819050919050565b6127d0816127bd565b82525050565b60006020820190506127eb60008301846127c7565b92915050565b6000604051905090565b600080fd5b600080fd5b60007fffffffff0000000000000000000000000000000000000000000000000000000082169050919050565b61283a81612805565b811461284557600080fd5b50565b60008135905061285781612831565b92915050565b600060208284031215612873576128726127fb565b5b600061288184828501612848565b91505092915050565b60008115159050919050565b61289f8161288a565b82525050565b60006020820190506128ba6000830184612896565b92915050565b600081519050919050565b600082825260208201905092915050565b60005b838110156128fa5780820151818401526020810190506128df565b83811115612909576000848401525b50505050565b6000601f19601f8301169050919050565b600061292b826128c0565b61293581856128cb565b93506129458185602086016128dc565b61294e8161290f565b840191505092915050565b600060208201905081810360008301526129738184612920565b905092915050565b612984816127bd565b811461298f57600080fd5b50565b6000813590506129a18161297b565b92915050565b6000602082840312156129bd576129bc6127fb565b5b60006129cb84828501612992565b91505092915050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b60006129ff826129d4565b9050919050565b612a0f816129f4565b82525050565b6000602082019050612a2a6000830184612a06565b92915050565b612a39816129f4565b8114612a4457600080fd5b50565b600081359050612a5681612a30565b92915050565b60008060408385031215612a7357612a726127fb565b5b6000612a8185828601612a47565b9250506020612a9285828601612992565b9150509250929050565b600080600060608486031215612ab557612ab46127fb565b5b6000612ac386828701612a47565b9350506020612ad486828701612a47565b9250506040612ae586828701612992565b9150509250925092565b6000819050919050565b612b0281612aef565b82525050565b6000602082019050612b1d6000830184612af9565b92915050565b600080fd5b600080fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b612b658261290f565b810181811067ffffffffffffffff82111715612b8457612b83612b2d565b5b80604052505050565b6000612b976127f1565b9050612ba38282612b5c565b919050565b600067ffffffffffffffff821115612bc357612bc2612b2d565b5b612bcc8261290f565b9050602081019050919050565b82818337600083830152505050565b6000612bfb612bf684612ba8565b612b8d565b905082815260208101848484011115612c1757612c16612b28565b5b612c22848285612bd9565b509392505050565b600082601f830112612c3f57612c3e612b23565b5b8135612c4f848260208601612be8565b91505092915050565b600060208284031215612c6e57612c6d6127fb565b5b600082013567ffffffffffffffff811115612c8c57612c8b612800565b5b612c9884828501612c2a565b91505092915050565b600060208284031215612cb757612cb66127fb565b5b6000612cc584828501612a47565b91505092915050565b600080fd5b600080fd5b60008083601f840112612cee57612ced612b23565b5b8235905067ffffffffffffffff811115612d0b57612d0a612cce565b5b602083019150836020820283011115612d2757612d26612cd3565b5b9250929050565b600080600060408486031215612d4757612d466127fb565b5b600084013567ffffffffffffffff811115612d6557612d64612800565b5b612d7186828701612cd8565b93509350506020612d8486828701612992565b9150509250925092565b612d9781612aef565b8114612da257600080fd5b50565b600081359050612db481612d8e565b92915050565b600060208284031215612dd057612dcf6127fb565b5b6000612dde84828501612da5565b91505092915050565b612df08161288a565b8114612dfb57600080fd5b50565b600081359050612e0d81612de7565b92915050565b60008060408385031215612e2a57612e296127fb565b5b6000612e3885828601612a47565b9250506020612e4985828601612dfe565b9150509250929050565b600067ffffffffffffffff821115612e6e57612e6d612b2d565b5b612e778261290f565b9050602081019050919050565b6000612e97612e9284612e53565b612b8d565b905082815260208101848484011115612eb357612eb2612b28565b5b612ebe848285612bd9565b509392505050565b600082601f830112612edb57612eda612b23565b5b8135612eeb848260208601612e84565b91505092915050565b60008060008060808587031215612f0e57612f0d6127fb565b5b6000612f1c87828801612a47565b9450506020612f2d87828801612a47565b9350506040612f3e87828801612992565b925050606085013567ffffffffffffffff811115612f5f57612f5e612800565b5b612f6b87828801612ec6565b91505092959194509250565b60008060408385031215612f8e57612f8d6127fb565b5b6000612f9c85828601612992565b9250506020612fad85828601612a47565b9150509250929050565b60008060408385031215612fce57612fcd6127fb565b5b6000612fdc85828601612a47565b9250506020612fed85828601612a47565b9150509250929050565b60008083601f84011261300d5761300c612b23565b5b8235905067ffffffffffffffff81111561302a57613029612cce565b5b60208301915083602082028301111561304657613045612cd3565b5b9250929050565b600080600060408486031215613066576130656127fb565b5b600061307486828701612992565b935050602084013567ffffffffffffffff81111561309557613094612800565b5b6130a186828701612ff7565b92509250509250925092565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b600060028204905060018216806130f457607f821691505b60208210811415613108576131076130ad565b5b50919050565b60008160601b9050919050565b60006131268261310e565b9050919050565b60006131388261311b565b9050919050565b61315061314b826129f4565b61312d565b82525050565b6000613162828461313f565b60148201915081905092915050565b7f4164647265737320646f6573206e6f7420657869737420696e206c6973740000600082015250565b60006131a7601e836128cb565b91506131b282613171565b602082019050919050565b600060208201905081810360008301526131d68161319a565b9050919050565b7f53616c652068617320656e6465642e0000000000000000000000000000000000600082015250565b6000613213600f836128cb565b915061321e826131dd565b602082019050919050565b6000602082019050818103600083015261324281613206565b9050919050565b7f50726573616c65206973206e6f74206163746976650000000000000000000000600082015250565b600061327f6015836128cb565b915061328a82613249565b602082019050919050565b600060208201905081810360008301526132ae81613272565b9050919050565b7f416c6c20746f6b656e732068617665206265656e206d696e7465640000000000600082015250565b60006132eb601b836128cb565b91506132f6826132b5565b602082019050919050565b6000602082019050818103600083015261331a816132de565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b600061335b826127bd565b9150613366836127bd565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561339b5761339a613321565b5b828201905092915050565b7f43616e6e6f742070757263686173652074686973206d616e7920746f6b656e73600082015250565b60006133dc6020836128cb565b91506133e7826133a6565b602082019050919050565b6000602082019050818103600083015261340b816133cf565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b600061344c826127bd565b9150613457836127bd565b92508261346757613466613412565b5b828206905092915050565b600061347d826127bd565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8214156134b0576134af613321565b5b600182019050919050565b60006134c6826127bd565b91506134d1836127bd565b9250828210156134e4576134e3613321565b5b828203905092915050565b60006134fa826127bd565b9150613505836127bd565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff048311821515161561353e5761353d613321565b5b828202905092915050565b7f496e73756666696369656e742045544820616d6f756e742073656e742e000000600082015250565b600061357f601d836128cb565b915061358a82613549565b602082019050919050565b600060208201905081810360008301526135ae81613572565b9050919050565b7f53616c65206973206e6f74206163746976652063757272656e746c792e000000600082015250565b60006135eb601d836128cb565b91506135f6826135b5565b602082019050919050565b6000602082019050818103600083015261361a816135de565b9050919050565b7f4d617820686f6c64696e672063617020726561636865642e0000000000000000600082015250565b60006136576018836128cb565b915061366282613621565b602082019050919050565b600060208201905081810360008301526136868161364a565b9050919050565b7f546f74616c20737570706c792065786365656465642e00000000000000000000600082015250565b60006136c36016836128cb565b91506136ce8261368d565b602082019050919050565b600060208201905081810360008301526136f2816136b6565b9050919050565b7f45786365656473206d6178696d756d20616c6c6f77656420746f6b656e730000600082015250565b600061372f601e836128cb565b915061373a826136f9565b602082019050919050565b6000602082019050818103600083015261375e81613722565b9050919050565b7f546f74616c20737570706c79207370656e742e00000000000000000000000000600082015250565b600061379b6013836128cb565b91506137a682613765565b602082019050919050565b600060208201905081810360008301526137ca8161378e565b9050919050565b600081905092915050565b60006137e7826128c0565b6137f181856137d1565b93506138018185602086016128dc565b80840191505092915050565b600061381982856137dc565b915061382582846137dc565b91508190509392505050565b7f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160008201527f6464726573730000000000000000000000000000000000000000000000000000602082015250565b600061388d6026836128cb565b915061389882613831565b604082019050919050565b600060208201905081810360008301526138bc81613880565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b7f43616e2774206164642061206e756c6c20616464726573730000000000000000600082015250565b60006139286018836128cb565b9150613933826138f2565b602082019050919050565b600060208201905081810360008301526139578161391b565b9050919050565b7f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572600082015250565b60006139946020836128cb565b915061399f8261395e565b602082019050919050565b600060208201905081810360008301526139c381613987565b9050919050565b600081519050919050565b600082825260208201905092915050565b60006139f1826139ca565b6139fb81856139d5565b9350613a0b8185602086016128dc565b613a148161290f565b840191505092915050565b6000608082019050613a346000830187612a06565b613a416020830186612a06565b613a4e60408301856127c7565b8181036060830152613a6081846139e6565b905095945050505050565b600081519050613a7a81612831565b92915050565b600060208284031215613a9657613a956127fb565b5b6000613aa484828501613a6b565b9150509291505056fea2646970667358221220a2d766f66df6c481f08e31028079e2e5299550fd9d6ce8b8cb16b4d4dbb8623964736f6c634300080b003300000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000
Deployed Bytecode
0x6080604052600436106102505760003560e01c8063715018a611610139578063a22cb465116100b6578063e7b62d961161007a578063e7b62d9614610833578063e985e9c51461085e578063ea6eb8361461089b578063f2fde38b146108c4578063f6c9d9e3146108ed578063fb7e6ccb1461091657610250565b8063a22cb46514610750578063b88d4fde14610779578063bc63f02e146107a2578063c87b56dd146107cb578063cadf88181461080857610250565b806391b7f5ed116100fd57806391b7f5ed1461068c57806395d89b41146106b55780639a3bf728146106e05780639ba411b11461070b578063a0712d681461073457610250565b8063715018a6146105ee5780637389fbb714610605578063781799761461062e5780637bffb4ce1461064a5780638da5cb5b1461066157610250565b806332cb6b0c116101d257806355f804b31161019657806355f804b3146104cc57806356a87caa146104f557806360d938dc1461051e5780636352211e146105495780636817c76c1461058657806370a08231146105b157610250565b806332cb6b0c1461040f5780633549345e1461043a5780633ccfd60b1461046357806342842e0e1461047a5780634dfea627146104a357610250565b8063095ea7b311610219578063095ea7b31461033c57806318160ddd1461036557806322f3e2d41461039057806323b872dd146103bb5780632eb4a7ab146103e457610250565b80620e7fa81461025557806301ffc9a714610280578063049c5c49146102bd57806306fdde03146102d4578063081812fc146102ff575b600080fd5b34801561026157600080fd5b5061026a61093f565b60405161027791906127d6565b60405180910390f35b34801561028c57600080fd5b506102a760048036038101906102a2919061285d565b610945565b6040516102b491906128a5565b60405180910390f35b3480156102c957600080fd5b506102d26109d7565b005b3480156102e057600080fd5b506102e9610a0b565b6040516102f69190612959565b60405180910390f35b34801561030b57600080fd5b50610326600480360381019061032191906129a7565b610a9d565b6040516103339190612a15565b60405180910390f35b34801561034857600080fd5b50610363600480360381019061035e9190612a5c565b610b1c565b005b34801561037157600080fd5b5061037a610c60565b60405161038791906127d6565b60405180910390f35b34801561039c57600080fd5b506103a5610c77565b6040516103b291906128a5565b60405180910390f35b3480156103c757600080fd5b506103e260048036038101906103dd9190612a9c565b610c8a565b005b3480156103f057600080fd5b506103f9610faf565b6040516104069190612b08565b60405180910390f35b34801561041b57600080fd5b50610424610fb5565b60405161043191906127d6565b60405180910390f35b34801561044657600080fd5b50610461600480360381019061045c91906129a7565b610fbb565b005b34801561046f57600080fd5b50610478610fcd565b005b34801561048657600080fd5b506104a1600480360381019061049c9190612a9c565b61102b565b005b3480156104af57600080fd5b506104ca60048036038101906104c591906129a7565b61104b565b005b3480156104d857600080fd5b506104f360048036038101906104ee9190612c58565b61105d565b005b34801561050157600080fd5b5061051c600480360381019061051791906129a7565b61107f565b005b34801561052a57600080fd5b50610533611091565b60405161054091906128a5565b60405180910390f35b34801561055557600080fd5b50610570600480360381019061056b91906129a7565b6110a4565b60405161057d9190612a15565b60405180910390f35b34801561059257600080fd5b5061059b6110b6565b6040516105a891906127d6565b60405180910390f35b3480156105bd57600080fd5b506105d860048036038101906105d39190612ca1565b6110bc565b6040516105e591906127d6565b60405180910390f35b3480156105fa57600080fd5b50610603611175565b005b34801561061157600080fd5b5061062c600480360381019061062791906129a7565b611189565b005b61064860048036038101906106439190612d2e565b61119b565b005b34801561065657600080fd5b5061065f61146f565b005b34801561066d57600080fd5b506106766114a3565b6040516106839190612a15565b60405180910390f35b34801561069857600080fd5b506106b360048036038101906106ae91906129a7565b6114cd565b005b3480156106c157600080fd5b506106ca6114df565b6040516106d79190612959565b60405180910390f35b3480156106ec57600080fd5b506106f5611571565b60405161070291906127d6565b60405180910390f35b34801561071757600080fd5b50610732600480360381019061072d9190612dba565b611577565b005b61074e600480360381019061074991906129a7565b611589565b005b34801561075c57600080fd5b5061077760048036038101906107729190612e13565b611830565b005b34801561078557600080fd5b506107a0600480360381019061079b9190612ef4565b6119a8565b005b3480156107ae57600080fd5b506107c960048036038101906107c49190612f77565b611a1b565b005b3480156107d757600080fd5b506107f260048036038101906107ed91906129a7565b611ad3565b6040516107ff9190612959565b60405180910390f35b34801561081457600080fd5b5061081d611b72565b60405161082a91906127d6565b60405180910390f35b34801561083f57600080fd5b50610848611b78565b60405161085591906127d6565b60405180910390f35b34801561086a57600080fd5b5061088560048036038101906108809190612fb7565b611b82565b60405161089291906128a5565b60405180910390f35b3480156108a757600080fd5b506108c260048036038101906108bd91906129a7565b611c16565b005b3480156108d057600080fd5b506108eb60048036038101906108e69190612ca1565b611c28565b005b3480156108f957600080fd5b50610914600480360381019061090f91906129a7565b611cac565b005b34801561092257600080fd5b5061093d6004803603810190610938919061304d565b611cbe565b005b600a5481565b60006301ffc9a760e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614806109a057506380ac58cd60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b806109d05750635b5e139f60e01b827bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916145b9050919050565b6109df611e57565b601060009054906101000a900460ff1615601060006101000a81548160ff021916908315150217905550565b606060028054610a1a906130dc565b80601f0160208091040260200160405190810160405280929190818152602001828054610a46906130dc565b8015610a935780601f10610a6857610100808354040283529160200191610a93565b820191906000526020600020905b815481529060010190602001808311610a7657829003601f168201915b5050505050905090565b6000610aa882611ed5565b610ade576040517fcf4700e400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6006600083815260200190815260200160002060000160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff169050919050565b6000610b27826110a4565b90508073ffffffffffffffffffffffffffffffffffffffff16610b48611f34565b73ffffffffffffffffffffffffffffffffffffffff1614610bab57610b7481610b6f611f34565b611b82565b610baa576040517fcfb3b94200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b826006600084815260200190815260200160002060000160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550818373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a4505050565b6000610c6a611f3c565b6001546000540303905090565b601060009054906101000a900460ff1681565b6000610c9582611f41565b90508373ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614610cfc576040517fa114810000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b600080610d088461200f565b91509150610d1e8187610d19611f34565b612036565b610d6a57610d3386610d2e611f34565b611b82565b610d69576040517f59c896be00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b600073ffffffffffffffffffffffffffffffffffffffff168573ffffffffffffffffffffffffffffffffffffffff161415610dd1576040517fea553b3400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b610dde868686600161207a565b8015610de957600082555b600560008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600081546001900391905081905550600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000815460010191905081905550610eb785610e93888887612080565b7c0200000000000000000000000000000000000000000000000000000000176120a8565b600460008681526020019081526020016000208190555060007c020000000000000000000000000000000000000000000000000000000084161415610f3f576000600185019050600060046000838152602001908152602001600020541415610f3d576000548114610f3c578360046000838152602001908152602001600020819055505b5b505b838573ffffffffffffffffffffffffffffffffffffffff168773ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4610fa786868660016120d3565b505050505050565b600e5481565b60115481565b610fc3611e57565b80600a8190555050565b610fd5611e57565b6000479050610fe26114a3565b73ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015611027573d6000803e3d6000fd5b5050565b611046838383604051806020016040528060008152506119a8565b505050565b611053611e57565b8060128190555050565b611065611e57565b80600f908051906020019061107b92919061271a565b5050565b611087611e57565b80600d8190555050565b601060019054906101000a900460ff1681565b60006110af82611f41565b9050919050565b60095481565b60008073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415611124576040517f8f4eb60400000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b67ffffffffffffffff600560008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054169050919050565b61117d611e57565b61118760006120d9565b565b611191611e57565b8060118190555050565b8282611211828280806020026020016040519081016040528093929190818152602001838360200280828437600081840152601f19601f82011690508083019250505050505050600e54336040516020016111f69190613156565b6040516020818303038152906040528051906020012061219f565b611250576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611247906131bd565b60405180910390fd5b60115461125b610c60565b111561129c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161129390613229565b60405180910390fd5b60006112a6610c60565b90506000601060019054906101000a900460ff166112f9576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016112f090613295565b60405180910390fd5b601154821061133d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161133490613301565b60405180910390fd5b6013548561134a336110bc565b6113549190613350565b1115611395576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161138c906133f2565b60405180910390fd5b600060016113a2336110bc565b6113ac9190613350565b90505b856113b9336110bc565b6113c39190613350565b81116114005760006004826113d89190613441565b14156113ed5781806113e990613472565b9250505b80806113f890613472565b9150506113af565b50808561140d91906134bb565b600a5461141a91906134ef565b34101561145c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161145390613595565b60405180910390fd5b61146633866121b6565b50505050505050565b611477611e57565b601060019054906101000a900460ff1615601060016101000a81548160ff021916908315150217905550565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6114d5611e57565b8060098190555050565b6060600380546114ee906130dc565b80601f016020809104026020016040519081016040528092919081815260200182805461151a906130dc565b80156115675780601f1061153c57610100808354040283529160200191611567565b820191906000526020600020905b81548152906001019060200180831161154a57829003601f168201915b5050505050905090565b60125481565b61157f611e57565b80600e8190555050565b601154611594610c60565b11156115d5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016115cc90613229565b60405180910390fd5b60006115df610c60565b905060006115eb6114a3565b73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff16146116c557601060009054906101000a900460ff1661166c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161166390613601565b60405180910390fd5b60135483611679336110bc565b6116839190613350565b11156116c4576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016116bb9061366d565b60405180910390fd5b5b60115483836116d49190613350565b1115611715576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161170c906136d9565b60405180910390fd5b60125483111561175a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161175190613745565b60405180910390fd5b60006001611767336110bc565b6117719190613350565b90505b8361177e336110bc565b6117889190613350565b81116117c557600060058261179d9190613441565b14156117b25781806117ae90613472565b9250505b80806117bd90613472565b915050611774565b5080836117d291906134bb565b6009546117df91906134ef565b341015611821576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161181890613595565b60405180910390fd5b61182b33846121b6565b505050565b611838611f34565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141561189d576040517fb06307db00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b80600760006118aa611f34565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055508173ffffffffffffffffffffffffffffffffffffffff16611957611f34565b73ffffffffffffffffffffffffffffffffffffffff167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c318360405161199c91906128a5565b60405180910390a35050565b6119b3848484610c8a565b60008373ffffffffffffffffffffffffffffffffffffffff163b14611a15576119de848484846121d4565b611a14576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b5b50505050565b611a23611e57565b6000611a2d610c60565b90506011548382611a3e9190613350565b1115611a7f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611a76906136d9565b60405180910390fd5b601154811115611ac4576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611abb906137b1565b60405180910390fd5b611ace82846121b6565b505050565b6060611ade82611ed5565b611b14576040517fa14c4b5000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6000611b1e612325565b9050600081511415611b3f5760405180602001604052806000815250611b6a565b80611b49846123b7565b604051602001611b5a92919061380d565b6040516020818303038152906040525b915050919050565b60135481565b6000600b54905090565b6000600760008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16905092915050565b611c1e611e57565b8060138190555050565b611c30611e57565b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415611ca0576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611c97906138a3565b60405180910390fd5b611ca9816120d9565b50565b611cb4611e57565b80600b8190555050565b611cc6611e57565b6000611cd0610c60565b90506011548482611ce19190613350565b1115611d22576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611d19906136d9565b60405180910390fd5b601154811115611d67576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611d5e906137b1565b60405180910390fd5b60005b83839050811015611e5057600073ffffffffffffffffffffffffffffffffffffffff16848483818110611da057611d9f6138c3565b5b9050602002016020810190611db59190612ca1565b73ffffffffffffffffffffffffffffffffffffffff161415611e0c576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611e039061393e565b60405180910390fd5b611e3d848483818110611e2257611e216138c3565b5b9050602002016020810190611e379190612ca1565b866121b6565b8080611e4890613472565b915050611d6a565b5050505050565b611e5f612407565b73ffffffffffffffffffffffffffffffffffffffff16611e7d6114a3565b73ffffffffffffffffffffffffffffffffffffffff1614611ed3576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611eca906139aa565b60405180910390fd5b565b600081611ee0611f3c565b11158015611eef575060005482105b8015611f2d575060007c0100000000000000000000000000000000000000000000000000000000600460008581526020019081526020016000205416145b9050919050565b600033905090565b600090565b60008082905080611f50611f3c565b11611fd857600054811015611fd75760006004600083815260200190815260200160002054905060007c010000000000000000000000000000000000000000000000000000000082161415611fd5575b6000811415611fcb576004600083600190039350838152602001908152602001600020549050611fa0565b809250505061200a565b505b5b6040517fdf2d9b4200000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b919050565b60008060006006600085815260200190815260200160002090508092508254915050915091565b600073ffffffffffffffffffffffffffffffffffffffff8316925073ffffffffffffffffffffffffffffffffffffffff821691508382148383141790509392505050565b50505050565b60008060e883901c905060e861209786868461240f565b62ffffff16901b9150509392505050565b600073ffffffffffffffffffffffffffffffffffffffff83169250814260a01b178317905092915050565b50505050565b6000600860009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905081600860006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a35050565b6000826121ac8584612418565b1490509392505050565b6121d082826040518060200160405280600081525061246e565b5050565b60008373ffffffffffffffffffffffffffffffffffffffff1663150b7a026121fa611f34565b8786866040518563ffffffff1660e01b815260040161221c9493929190613a1f565b6020604051808303816000875af192505050801561225857506040513d601f19601f820116820180604052508101906122559190613a80565b60015b6122d2573d8060008114612288576040519150601f19603f3d011682016040523d82523d6000602084013e61228d565b606091505b506000815114156122ca576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b805181602001fd5b63150b7a0260e01b7bffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916817bffffffffffffffffffffffffffffffffffffffffffffffffffffffff191614915050949350505050565b6060600f8054612334906130dc565b80601f0160208091040260200160405190810160405280929190818152602001828054612360906130dc565b80156123ad5780601f10612382576101008083540402835291602001916123ad565b820191906000526020600020905b81548152906001019060200180831161239057829003601f168201915b5050505050905090565b606060806040510190508060405280825b6001156123f357600183039250600a81066030018353600a81049050806123ee576123f3565b6123c8565b508181036020830392508083525050919050565b600033905090565b60009392505050565b60008082905060005b84518110156124635761244e82868381518110612441576124406138c3565b5b602002602001015161250b565b9150808061245b90613472565b915050612421565b508091505092915050565b6124788383612536565b60008373ffffffffffffffffffffffffffffffffffffffff163b1461250657600080549050600083820390505b6124b860008683806001019450866121d4565b6124ee576040517fd1a57ed600000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8181106124a557816000541461250357600080fd5b50505b505050565b60008183106125235761251e82846126f3565b61252e565b61252d83836126f3565b5b905092915050565b6000805490506000821415612577576040517fb562e8dd00000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b612584600084838561207a565b600160406001901b178202600560008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055506125fb836125ec6000866000612080565b6125f58561270a565b176120a8565b6004600083815260200190815260200160002081905550600080838301905073ffffffffffffffffffffffffffffffffffffffff85169150828260007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600183015b81811461269c57808360007fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef600080a4600181019050612661565b5060008214156126d8576040517f2e07630000000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b8060008190555050506126ee60008483856120d3565b505050565b600082600052816020526040600020905092915050565b60006001821460e11b9050919050565b828054612726906130dc565b90600052602060002090601f016020900481019282612748576000855561278f565b82601f1061276157805160ff191683800117855561278f565b8280016001018555821561278f579182015b8281111561278e578251825591602001919060010190612773565b5b50905061279c91906127a0565b5090565b5b808211156127b95760008160009055506001016127a1565b5090565b6000819050919050565b6127d0816127bd565b82525050565b60006020820190506127eb60008301846127c7565b92915050565b6000604051905090565b600080fd5b600080fd5b60007fffffffff0000000000000000000000000000000000000000000000000000000082169050919050565b61283a81612805565b811461284557600080fd5b50565b60008135905061285781612831565b92915050565b600060208284031215612873576128726127fb565b5b600061288184828501612848565b91505092915050565b60008115159050919050565b61289f8161288a565b82525050565b60006020820190506128ba6000830184612896565b92915050565b600081519050919050565b600082825260208201905092915050565b60005b838110156128fa5780820151818401526020810190506128df565b83811115612909576000848401525b50505050565b6000601f19601f8301169050919050565b600061292b826128c0565b61293581856128cb565b93506129458185602086016128dc565b61294e8161290f565b840191505092915050565b600060208201905081810360008301526129738184612920565b905092915050565b612984816127bd565b811461298f57600080fd5b50565b6000813590506129a18161297b565b92915050565b6000602082840312156129bd576129bc6127fb565b5b60006129cb84828501612992565b91505092915050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b60006129ff826129d4565b9050919050565b612a0f816129f4565b82525050565b6000602082019050612a2a6000830184612a06565b92915050565b612a39816129f4565b8114612a4457600080fd5b50565b600081359050612a5681612a30565b92915050565b60008060408385031215612a7357612a726127fb565b5b6000612a8185828601612a47565b9250506020612a9285828601612992565b9150509250929050565b600080600060608486031215612ab557612ab46127fb565b5b6000612ac386828701612a47565b9350506020612ad486828701612a47565b9250506040612ae586828701612992565b9150509250925092565b6000819050919050565b612b0281612aef565b82525050565b6000602082019050612b1d6000830184612af9565b92915050565b600080fd5b600080fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b612b658261290f565b810181811067ffffffffffffffff82111715612b8457612b83612b2d565b5b80604052505050565b6000612b976127f1565b9050612ba38282612b5c565b919050565b600067ffffffffffffffff821115612bc357612bc2612b2d565b5b612bcc8261290f565b9050602081019050919050565b82818337600083830152505050565b6000612bfb612bf684612ba8565b612b8d565b905082815260208101848484011115612c1757612c16612b28565b5b612c22848285612bd9565b509392505050565b600082601f830112612c3f57612c3e612b23565b5b8135612c4f848260208601612be8565b91505092915050565b600060208284031215612c6e57612c6d6127fb565b5b600082013567ffffffffffffffff811115612c8c57612c8b612800565b5b612c9884828501612c2a565b91505092915050565b600060208284031215612cb757612cb66127fb565b5b6000612cc584828501612a47565b91505092915050565b600080fd5b600080fd5b60008083601f840112612cee57612ced612b23565b5b8235905067ffffffffffffffff811115612d0b57612d0a612cce565b5b602083019150836020820283011115612d2757612d26612cd3565b5b9250929050565b600080600060408486031215612d4757612d466127fb565b5b600084013567ffffffffffffffff811115612d6557612d64612800565b5b612d7186828701612cd8565b93509350506020612d8486828701612992565b9150509250925092565b612d9781612aef565b8114612da257600080fd5b50565b600081359050612db481612d8e565b92915050565b600060208284031215612dd057612dcf6127fb565b5b6000612dde84828501612da5565b91505092915050565b612df08161288a565b8114612dfb57600080fd5b50565b600081359050612e0d81612de7565b92915050565b60008060408385031215612e2a57612e296127fb565b5b6000612e3885828601612a47565b9250506020612e4985828601612dfe565b9150509250929050565b600067ffffffffffffffff821115612e6e57612e6d612b2d565b5b612e778261290f565b9050602081019050919050565b6000612e97612e9284612e53565b612b8d565b905082815260208101848484011115612eb357612eb2612b28565b5b612ebe848285612bd9565b509392505050565b600082601f830112612edb57612eda612b23565b5b8135612eeb848260208601612e84565b91505092915050565b60008060008060808587031215612f0e57612f0d6127fb565b5b6000612f1c87828801612a47565b9450506020612f2d87828801612a47565b9350506040612f3e87828801612992565b925050606085013567ffffffffffffffff811115612f5f57612f5e612800565b5b612f6b87828801612ec6565b91505092959194509250565b60008060408385031215612f8e57612f8d6127fb565b5b6000612f9c85828601612992565b9250506020612fad85828601612a47565b9150509250929050565b60008060408385031215612fce57612fcd6127fb565b5b6000612fdc85828601612a47565b9250506020612fed85828601612a47565b9150509250929050565b60008083601f84011261300d5761300c612b23565b5b8235905067ffffffffffffffff81111561302a57613029612cce565b5b60208301915083602082028301111561304657613045612cd3565b5b9250929050565b600080600060408486031215613066576130656127fb565b5b600061307486828701612992565b935050602084013567ffffffffffffffff81111561309557613094612800565b5b6130a186828701612ff7565b92509250509250925092565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602260045260246000fd5b600060028204905060018216806130f457607f821691505b60208210811415613108576131076130ad565b5b50919050565b60008160601b9050919050565b60006131268261310e565b9050919050565b60006131388261311b565b9050919050565b61315061314b826129f4565b61312d565b82525050565b6000613162828461313f565b60148201915081905092915050565b7f4164647265737320646f6573206e6f7420657869737420696e206c6973740000600082015250565b60006131a7601e836128cb565b91506131b282613171565b602082019050919050565b600060208201905081810360008301526131d68161319a565b9050919050565b7f53616c652068617320656e6465642e0000000000000000000000000000000000600082015250565b6000613213600f836128cb565b915061321e826131dd565b602082019050919050565b6000602082019050818103600083015261324281613206565b9050919050565b7f50726573616c65206973206e6f74206163746976650000000000000000000000600082015250565b600061327f6015836128cb565b915061328a82613249565b602082019050919050565b600060208201905081810360008301526132ae81613272565b9050919050565b7f416c6c20746f6b656e732068617665206265656e206d696e7465640000000000600082015250565b60006132eb601b836128cb565b91506132f6826132b5565b602082019050919050565b6000602082019050818103600083015261331a816132de565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b600061335b826127bd565b9150613366836127bd565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561339b5761339a613321565b5b828201905092915050565b7f43616e6e6f742070757263686173652074686973206d616e7920746f6b656e73600082015250565b60006133dc6020836128cb565b91506133e7826133a6565b602082019050919050565b6000602082019050818103600083015261340b816133cf565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b600061344c826127bd565b9150613457836127bd565b92508261346757613466613412565b5b828206905092915050565b600061347d826127bd565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8214156134b0576134af613321565b5b600182019050919050565b60006134c6826127bd565b91506134d1836127bd565b9250828210156134e4576134e3613321565b5b828203905092915050565b60006134fa826127bd565b9150613505836127bd565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff048311821515161561353e5761353d613321565b5b828202905092915050565b7f496e73756666696369656e742045544820616d6f756e742073656e742e000000600082015250565b600061357f601d836128cb565b915061358a82613549565b602082019050919050565b600060208201905081810360008301526135ae81613572565b9050919050565b7f53616c65206973206e6f74206163746976652063757272656e746c792e000000600082015250565b60006135eb601d836128cb565b91506135f6826135b5565b602082019050919050565b6000602082019050818103600083015261361a816135de565b9050919050565b7f4d617820686f6c64696e672063617020726561636865642e0000000000000000600082015250565b60006136576018836128cb565b915061366282613621565b602082019050919050565b600060208201905081810360008301526136868161364a565b9050919050565b7f546f74616c20737570706c792065786365656465642e00000000000000000000600082015250565b60006136c36016836128cb565b91506136ce8261368d565b602082019050919050565b600060208201905081810360008301526136f2816136b6565b9050919050565b7f45786365656473206d6178696d756d20616c6c6f77656420746f6b656e730000600082015250565b600061372f601e836128cb565b915061373a826136f9565b602082019050919050565b6000602082019050818103600083015261375e81613722565b9050919050565b7f546f74616c20737570706c79207370656e742e00000000000000000000000000600082015250565b600061379b6013836128cb565b91506137a682613765565b602082019050919050565b600060208201905081810360008301526137ca8161378e565b9050919050565b600081905092915050565b60006137e7826128c0565b6137f181856137d1565b93506138018185602086016128dc565b80840191505092915050565b600061381982856137dc565b915061382582846137dc565b91508190509392505050565b7f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160008201527f6464726573730000000000000000000000000000000000000000000000000000602082015250565b600061388d6026836128cb565b915061389882613831565b604082019050919050565b600060208201905081810360008301526138bc81613880565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b7f43616e2774206164642061206e756c6c20616464726573730000000000000000600082015250565b60006139286018836128cb565b9150613933826138f2565b602082019050919050565b600060208201905081810360008301526139578161391b565b9050919050565b7f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572600082015250565b60006139946020836128cb565b915061399f8261395e565b602082019050919050565b600060208201905081810360008301526139c381613987565b9050919050565b600081519050919050565b600082825260208201905092915050565b60006139f1826139ca565b6139fb81856139d5565b9350613a0b8185602086016128dc565b613a148161290f565b840191505092915050565b6000608082019050613a346000830187612a06565b613a416020830186612a06565b613a4e60408301856127c7565b8181036060830152613a6081846139e6565b905095945050505050565b600081519050613a7a81612831565b92915050565b600060208284031215613a9657613a956127fb565b5b6000613aa484828501613a6b565b9150509291505056fea2646970667358221220a2d766f66df6c481f08e31028079e2e5299550fd9d6ce8b8cb16b4d4dbb8623964736f6c634300080b0033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000
-----Decoded View---------------
Arg [0] : baseURI (string):
-----Encoded View---------------
2 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000020
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000000
Deployed Bytecode Sourcemap
142:4875:2:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;236:41;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;9112:630:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;2182:78:2;;;;;;;;;;;;;:::i;:::-;;9996:98:1;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;16309:214;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;15769:390;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;5851:317;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;464:27:2;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;19918:2756:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;407:25:2;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;538:32;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;2070:106;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;4885:129;;;;;;;;;;;;;:::i;:::-;;22765:179:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;1611:119:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;2369:96;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;1319:87;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;496:35;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;11348:150:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;193:38:2;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;7002:230:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;1824:101:5;;;;;;;;;;;;;:::i;:::-;;1868:108:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;4141:738;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;2266:97;;;;;;;;;;;;;:::i;:::-;;1194:85:5;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;1982:82:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;10165:102:1;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;575:51:2;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;1215:98;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;3317:818;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;16850:303:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;23525:388;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;2587:281:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;10368:313:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;631:49:2;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;1508:95;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;17303:162:1;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;1736:126:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;2074:198:5;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;1412:90:2;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;2874:437;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;:::i;:::-;;236:41;;;;:::o;9112:630:1:-;9197:4;9530:10;9515:25;;:11;:25;;;;:101;;;;9606:10;9591:25;;:11;:25;;;;9515:101;:177;;;;9682:10;9667:25;;:11;:25;;;;9515:177;9496:196;;9112:630;;;:::o;2182:78:2:-;1087:13:5;:11;:13::i;:::-;2246:8:2::1;;;;;;;;;;;2245:9;2234:8;;:20;;;;;;;;;;;;;;;;;;2182:78::o:0;9996:98:1:-;10050:13;10082:5;10075:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;9996:98;:::o;16309:214::-;16385:7;16409:16;16417:7;16409;:16::i;:::-;16404:64;;16434:34;;;;;;;;;;;;;;16404:64;16486:15;:24;16502:7;16486:24;;;;;;;;;;;:30;;;;;;;;;;;;16479:37;;16309:214;;;:::o;15769:390::-;15849:13;15865:16;15873:7;15865;:16::i;:::-;15849:32;;15919:5;15896:28;;:19;:17;:19::i;:::-;:28;;;15892:172;;15943:44;15960:5;15967:19;:17;:19::i;:::-;15943:16;:44::i;:::-;15938:126;;16014:35;;;;;;;;;;;;;;15938:126;15892:172;16107:2;16074:15;:24;16090:7;16074:24;;;;;;;;;;;:30;;;:35;;;;;;;;;;;;;;;;;;16144:7;16140:2;16124:28;;16133:5;16124:28;;;;;;;;;;;;15839:320;15769:390;;:::o;5851:317::-;5912:7;6136:15;:13;:15::i;:::-;6121:12;;6105:13;;:28;:46;6098:53;;5851:317;:::o;464:27:2:-;;;;;;;;;;;;;:::o;19918:2756:1:-;20047:27;20077;20096:7;20077:18;:27::i;:::-;20047:57;;20160:4;20119:45;;20135:19;20119:45;;;20115:86;;20173:28;;;;;;;;;;;;;;20115:86;20213:27;20242:23;20269:35;20296:7;20269:26;:35::i;:::-;20212:92;;;;20401:68;20426:15;20443:4;20449:19;:17;:19::i;:::-;20401:24;:68::i;:::-;20396:179;;20488:43;20505:4;20511:19;:17;:19::i;:::-;20488:16;:43::i;:::-;20483:92;;20540:35;;;;;;;;;;;;;;20483:92;20396:179;20604:1;20590:16;;:2;:16;;;20586:52;;;20615:23;;;;;;;;;;;;;;20586:52;20649:43;20671:4;20677:2;20681:7;20690:1;20649:21;:43::i;:::-;20781:15;20778:157;;;20919:1;20898:19;20891:30;20778:157;21307:18;:24;21326:4;21307:24;;;;;;;;;;;;;;;;21305:26;;;;;;;;;;;;21375:18;:22;21394:2;21375:22;;;;;;;;;;;;;;;;21373:24;;;;;;;;;;;21690:143;21726:2;21774:45;21789:4;21795:2;21799:19;21774:14;:45::i;:::-;2349:8;21746:73;21690:18;:143::i;:::-;21661:17;:26;21679:7;21661:26;;;;;;;;;;;:172;;;;22001:1;2349:8;21950:19;:47;:52;21946:617;;;22022:19;22054:1;22044:7;:11;22022:33;;22209:1;22175:17;:30;22193:11;22175:30;;;;;;;;;;;;:35;22171:378;;;22311:13;;22296:11;:28;22292:239;;22489:19;22456:17;:30;22474:11;22456:30;;;;;;;;;;;:52;;;;22292:239;22171:378;22004:559;21946:617;22607:7;22603:2;22588:27;;22597:4;22588:27;;;;;;;;;;;;22625:42;22646:4;22652:2;22656:7;22665:1;22625:20;:42::i;:::-;20037:2637;;;19918:2756;;;:::o;407:25:2:-;;;;:::o;538:32::-;;;;:::o;2070:106::-;1087:13:5;:11;:13::i;:::-;2157::2::1;2142:12;:28;;;;2070:106:::0;:::o;4885:129::-;1087:13:5;:11;:13::i;:::-;4931:12:2::1;4946:21;4931:36;;4982:7;:5;:7::i;:::-;4974:25;;:34;5000:7;4974:34;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;4924:90;4885:129::o:0;22765:179:1:-;22898:39;22915:4;22921:2;22925:7;22898:39;;;;;;;;;;;;:16;:39::i;:::-;22765:179;;;:::o;1611:119:2:-;1087:13:5;:11;:13::i;:::-;1718:6:2::1;1684:31;:40;;;;1611:119:::0;:::o;2369:96::-;1087:13:5;:11;:13::i;:::-;2452:7:2::1;2436:13;:23;;;;;;;;;;;;:::i;:::-;;2369:96:::0;:::o;1319:87::-;1087:13:5;:11;:13::i;:::-;1397:3:2::1;1379:15;:21;;;;1319:87:::0;:::o;496:35::-;;;;;;;;;;;;;:::o;11348:150:1:-;11420:7;11462:27;11481:7;11462:18;:27::i;:::-;11439:52;;11348:150;;;:::o;193:38:2:-;;;;:::o;7002:230:1:-;7074:7;7114:1;7097:19;;:5;:19;;;7093:60;;;7125:28;;;;;;;;;;;;;;7093:60;1317:13;7170:18;:25;7189:5;7170:25;;;;;;;;;;;;;;;;:55;7163:62;;7002:230;;;:::o;1824:101:5:-;1087:13;:11;:13::i;:::-;1888:30:::1;1915:1;1888:18;:30::i;:::-;1824:101::o:0;1868:108:2:-;1087:13:5;:11;:13::i;:::-;1957::2::1;1944:10;:26;;;;1868:108:::0;:::o;4141:738::-;4245:12;;985:150;1022:11;;985:150;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;1052:10;;1108;1091:28;;;;;;;;:::i;:::-;;;;;;;;;;;;;1081:39;;;;;;985:18;:150::i;:::-;963:230;;;;;;;;;;;;:::i;:::-;;;;;;;;;842:10:::1;;825:13;:11;:13::i;:::-;:27;;817:55;;;;;;;;;;;;:::i;:::-;;;;;;;;;4277:17:::2;4297:13;:11;:13::i;:::-;4277:33;;4317:15;4353;;;;;;;;;;;4345:49;;;;;;;;;;;;:::i;:::-;;;;;;;;;4421:10;;4409:9;:22;4401:62;;;;;;;;;;;;:::i;:::-;;;;;;;;;4512:29;;4502:6;4478:21;4488:10;4478:9;:21::i;:::-;:30;;;;:::i;:::-;:63;;4470:108;;;;;;;;;;;;:::i;:::-;;;;;;;;;4595:9;4631:1;4607:21;4617:10;4607:9;:21::i;:::-;:25;;;;:::i;:::-;4595:37;;4591:146;4663:6;4639:21;4649:10;4639:9;:21::i;:::-;:30;;;;:::i;:::-;4634:1;:35;4591:146;;4697:1;4692;4688;:5;;;;:::i;:::-;:10;4685:45;;;4711:9;;;;;:::i;:::-;;;;4685:45;4671:3;;;;;:::i;:::-;;;;4591:146;;;;4792:7;4783:6;:16;;;;:::i;:::-;4767:12;;:33;;;;:::i;:::-;4753:9;:48;;4745:90;;;;;;;;;;;;:::i;:::-;;;;;;;;;4842:29;4852:10;4864:6;4842:9;:29::i;:::-;4270:609;;4141:738:::0;;;;;:::o;2266:97::-;1087:13:5;:11;:13::i;:::-;2342:15:2::1;;;;;;;;;;;2341:16;2323:15;;:34;;;;;;;;;;;;;;;;;;2266:97::o:0;1194:85:5:-;1240:7;1266:6;;;;;;;;;;;1259:13;;1194:85;:::o;1982:82:2:-;1087:13:5;:11;:13::i;:::-;2052:6:2::1;2040:9;:18;;;;1982:82:::0;:::o;10165:102:1:-;10221:13;10253:7;10246:14;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;10165:102;:::o;575:51:2:-;;;;:::o;1215:98::-;1087:13:5;:11;:13::i;:::-;1298:9:2::1;1285:10;:22;;;;1215:98:::0;:::o;3317:818::-;842:10;;825:13;:11;:13::i;:::-;:27;;817:55;;;;;;;;;;;;:::i;:::-;;;;;;;;;3380:17:::1;3400:13;:11;:13::i;:::-;3380:33;;3420:15;3473:7;:5;:7::i;:::-;3459:21;;:10;:21;;;3455:203;;3499:8;;;;;;;;;;;3491:50;;;;;;;;;;;;:::i;:::-;;;;;;;;;3592:29;;3582:6;3558:21;3568:10;3558:9;:21::i;:::-;:30;;;;:::i;:::-;:63;;3550:100;;;;;;;;;;;;:::i;:::-;;;;;;;;;3455:203;3696:10;;3686:6;3674:9;:18;;;;:::i;:::-;:32;;3666:67;;;;;;;;;;;;:::i;:::-;;;;;;;;;3759:31;;3749:6;:41;;3740:85;;;;;;;;;;;;:::i;:::-;;;;;;;;;3842:9;3878:1;3854:21;3864:10;3854:9;:21::i;:::-;:25;;;;:::i;:::-;3842:37;;3838:152;3910:6;3886:21;3896:10;3886:9;:21::i;:::-;:30;;;;:::i;:::-;3881:1;:35;3838:152;;3946:1;3941;3937;:5;;;;:::i;:::-;:10;3934:49;;;3962:9;;;;;:::i;:::-;;;;3934:49;3918:3;;;;;:::i;:::-;;;;3838:152;;;;4042:7;4033:6;:16;;;;:::i;:::-;4020:9;;:30;;;;:::i;:::-;4006:9;:45;;3998:87;;;;;;;;;;;;:::i;:::-;;;;;;;;;4094:29;4104:10;4116:6;4094:9;:29::i;:::-;3373:762;;3317:818:::0;:::o;16850:303:1:-;16960:19;:17;:19::i;:::-;16948:31;;:8;:31;;;16944:61;;;16988:17;;;;;;;;;;;;;;16944:61;17068:8;17016:18;:39;17035:19;:17;:19::i;:::-;17016:39;;;;;;;;;;;;;;;:49;17056:8;17016:49;;;;;;;;;;;;;;;;:60;;;;;;;;;;;;;;;;;;17127:8;17091:55;;17106:19;:17;:19::i;:::-;17091:55;;;17137:8;17091:55;;;;;;:::i;:::-;;;;;;;;16850:303;;:::o;23525:388::-;23686:31;23699:4;23705:2;23709:7;23686:12;:31::i;:::-;23749:1;23731:2;:14;;;:19;23727:180;;23769:56;23800:4;23806:2;23810:7;23819:5;23769:30;:56::i;:::-;23764:143;;23852:40;;;;;;;;;;;;;;23764:143;23727:180;23525:388;;;;:::o;2587:281:2:-;1087:13:5;:11;:13::i;:::-;2664:14:2::1;2681:13;:11;:13::i;:::-;2664:30;;2730:10;;2720:6;2711;:15;;;;:::i;:::-;:29;;2703:64;;;;;;;;;;;;:::i;:::-;;;;;;;;;2792:10;;2782:6;:20;;2774:52;;;;;;;;;;;;:::i;:::-;;;;;;;;;2835:27;2845:8;2855:6;2835:9;:27::i;:::-;2657:211;2587:281:::0;;:::o;10368:313:1:-;10441:13;10471:16;10479:7;10471;:16::i;:::-;10466:59;;10496:29;;;;;;;;;;;;;;10466:59;10536:21;10560:10;:8;:10::i;:::-;10536:34;;10612:1;10593:7;10587:21;:26;;:87;;;;;;;;;;;;;;;;;10640:7;10649:18;10659:7;10649:9;:18::i;:::-;10623:45;;;;;;;;;:::i;:::-;;;;;;;;;;;;;10587:87;10580:94;;;10368:313;;;:::o;631:49:2:-;;;;:::o;1508:95::-;1560:7;1583:14;;1576:21;;1508:95;:::o;17303:162:1:-;17400:4;17423:18;:25;17442:5;17423:25;;;;;;;;;;;;;;;:35;17449:8;17423:35;;;;;;;;;;;;;;;;;;;;;;;;;17416:42;;17303:162;;;;:::o;1736:126:2:-;1087:13:5;:11;:13::i;:::-;1850:6:2::1;1818:29;:38;;;;1736:126:::0;:::o;2074:198:5:-;1087:13;:11;:13::i;:::-;2182:1:::1;2162:22;;:8;:22;;;;2154:73;;;;;;;;;;;;:::i;:::-;;;;;;;;;2237:28;2256:8;2237:18;:28::i;:::-;2074:198:::0;:::o;1412:90:2:-;1087:13:5;:11;:13::i;:::-;1493:3:2::1;1476:14;:20;;;;1412:90:::0;:::o;2874:437::-;1087:13:5;:11;:13::i;:::-;2968:14:2::1;2985:13;:11;:13::i;:::-;2968:30;;3034:10;;3024:6;3015;:15;;;;:::i;:::-;:29;;3007:64;;;;;;;;;;;;:::i;:::-;;;;;;;;;3096:10;;3086:6;:20;;3078:52;;;;;;;;;;;;:::i;:::-;;;;;;;;;3144:9;3139:167;3163:9;;:16;;3159:1;:20;3139:167;;;3227:1;3203:26;;:9;;3213:1;3203:12;;;;;;;:::i;:::-;;;;;;;;;;;;;;;:::i;:::-;:26;;;;3195:63;;;;;;;;;;;;:::i;:::-;;;;;;;;;3267:31;3277:9;;3287:1;3277:12;;;;;;;:::i;:::-;;;;;;;;;;;;;;;:::i;:::-;3291:6;3267:9;:31::i;:::-;3181:3;;;;;:::i;:::-;;;;3139:167;;;;2961:350;2874:437:::0;;;:::o;1352:130:5:-;1426:12;:10;:12::i;:::-;1415:23;;:7;:5;:7::i;:::-;:23;;;1407:68;;;;;;;;;;;;:::i;:::-;;;;;;;;;1352:130::o;17714:277:1:-;17779:4;17833:7;17814:15;:13;:15::i;:::-;:26;;:65;;;;;17866:13;;17856:7;:23;17814:65;:151;;;;;17964:1;2075:8;17916:17;:26;17934:7;17916:26;;;;;;;;;;;;:44;:49;17814:151;17795:170;;17714:277;;;:::o;38922:103::-;38982:7;39008:10;39001:17;;38922:103;:::o;5383:90::-;5439:7;5383:90;:::o;12472:1249::-;12539:7;12558:12;12573:7;12558:22;;12638:4;12619:15;:13;:15::i;:::-;:23;12615:1042;;12671:13;;12664:4;:20;12660:997;;;12708:14;12725:17;:23;12743:4;12725:23;;;;;;;;;;;;12708:40;;12840:1;2075:8;12812:6;:24;:29;12808:831;;;13467:111;13484:1;13474:6;:11;13467:111;;;13526:17;:25;13544:6;;;;;;;13526:25;;;;;;;;;;;;13517:34;;13467:111;;;13610:6;13603:13;;;;;;12808:831;12686:971;12660:997;12615:1042;13683:31;;;;;;;;;;;;;;12472:1249;;;;:::o;18849:468::-;18948:27;18977:23;19016:38;19057:15;:24;19073:7;19057:24;;;;;;;;;;;19016:65;;19225:18;19202:41;;19281:19;19275:26;19256:45;;19188:123;18849:468;;;:::o;18095:646::-;18240:11;18402:16;18395:5;18391:28;18382:37;;18560:16;18549:9;18545:32;18532:45;;18708:15;18697:9;18694:30;18686:5;18675:9;18672:20;18669:56;18659:66;;18095:646;;;;;:::o;24557:154::-;;;;;:::o;38249:304::-;38380:7;38399:16;2470:3;38425:19;:41;;38399:68;;2470:3;38492:31;38503:4;38509:2;38513:9;38492:10;:31::i;:::-;38484:40;;:62;;38477:69;;;38249:304;;;;;:::o;14254:443::-;14334:14;14499:16;14492:5;14488:28;14479:37;;14674:5;14660:11;14635:23;14631:41;14628:52;14621:5;14618:63;14608:73;;14254:443;;;;:::o;25358:153::-;;;;;:::o;2426:187:5:-;2499:16;2518:6;;;;;;;;;;;2499:25;;2543:8;2534:6;;:17;;;;;;;;;;;;;;;;;;2597:8;2566:40;;2587:8;2566:40;;;;;;;;;;;;2489:124;2426:187;:::o;1153:184:4:-;1274:4;1326;1297:25;1310:5;1317:4;1297:12;:25::i;:::-;:33;1290:40;;1153:184;;;;;:::o;32908:110:1:-;32984:27;32994:2;32998:8;32984:27;;;;;;;;;;;;:9;:27::i;:::-;32908:110;;:::o;25939:697::-;26097:4;26142:2;26117:45;;;26163:19;:17;:19::i;:::-;26184:4;26190:7;26199:5;26117:88;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;26113:517;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;26412:1;26395:6;:13;:18;26391:229;;;26440:40;;;;;;;;;;;;;;26391:229;26580:6;26574:13;26565:6;26561:2;26557:15;26550:38;26113:517;26283:54;;;26273:64;;;:6;:64;;;;26266:71;;;25939:697;;;;;;:::o;2473:108:2:-;2533:13;2562;2555:20;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2473:108;:::o;39122:1548:1:-;39187:17;39606:4;39599;39593:11;39589:22;39582:29;;39696:3;39690:4;39683:17;39799:3;40033:5;40015:419;40041:1;40015:419;;;40080:1;40075:3;40071:11;40064:18;;40248:2;40242:4;40238:13;40234:2;40230:22;40225:3;40217:36;40340:2;40334:4;40330:13;40322:21;;40405:4;40395:25;;40413:5;;40395:25;40015:419;;;40019:21;40471:3;40466;40462:13;40584:4;40579:3;40575:14;40568:21;;40647:6;40642:3;40635:19;39225:1439;;39122:1548;;;:::o;640:96:0:-;693:7;719:10;712:17;;640:96;:::o;37960:143:1:-;38093:6;37960:143;;;;;:::o;1991:290:4:-;2074:7;2093:20;2116:4;2093:27;;2135:9;2130:116;2154:5;:12;2150:1;:16;2130:116;;;2202:33;2212:12;2226:5;2232:1;2226:8;;;;;;;;:::i;:::-;;;;;;;;2202:9;:33::i;:::-;2187:48;;2168:3;;;;;:::i;:::-;;;;2130:116;;;;2262:12;2255:19;;;1991:290;;;;:::o;32160:669:1:-;32286:19;32292:2;32296:8;32286:5;:19::i;:::-;32362:1;32344:2;:14;;;:19;32340:473;;32383:11;32397:13;;32383:27;;32428:13;32450:8;32444:3;:14;32428:30;;32476:229;32506:62;32545:1;32549:2;32553:7;;;;;;32562:5;32506:30;:62::i;:::-;32501:165;;32603:40;;;;;;;;;;;;;;32501:165;32700:3;32692:5;:11;32476:229;;32785:3;32768:13;;:20;32764:34;;32790:8;;;32764:34;32365:448;;32340:473;32160:669;;;:::o;8054:147:4:-;8117:7;8147:1;8143;:5;:51;;8174:20;8189:1;8192;8174:14;:20::i;:::-;8143:51;;;8151:20;8166:1;8169;8151:14;:20::i;:::-;8143:51;8136:58;;8054:147;;;;:::o;27082:2396:1:-;27154:20;27177:13;;27154:36;;27216:1;27204:8;:13;27200:44;;;27226:18;;;;;;;;;;;;;;27200:44;27255:61;27285:1;27289:2;27293:12;27307:8;27255:21;:61::i;:::-;27788:1;1452:2;27758:1;:26;;27757:32;27745:8;:45;27719:18;:22;27738:2;27719:22;;;;;;;;;;;;;;;;:71;;;;;;;;;;;28060:136;28096:2;28149:33;28172:1;28176:2;28180:1;28149:14;:33::i;:::-;28116:30;28137:8;28116:20;:30::i;:::-;:66;28060:18;:136::i;:::-;28026:17;:31;28044:12;28026:31;;;;;;;;;;;:170;;;;28211:16;28241:11;28270:8;28255:12;:23;28241:37;;28520:16;28516:2;28512:25;28500:37;;28884:12;28845:8;28805:1;28744:25;28686:1;28626;28600:328;29005:1;28991:12;28987:20;28946:339;29045:3;29036:7;29033:16;28946:339;;29259:7;29249:8;29246:1;29219:25;29216:1;29213;29208:59;29097:1;29088:7;29084:15;29073:26;;28946:339;;;28950:75;29328:1;29316:8;:13;29312:45;;;29338:19;;;;;;;;;;;;;;29312:45;29388:3;29372:13;:19;;;;27499:1903;;29411:60;29440:1;29444:2;29448:12;29462:8;29411:20;:60::i;:::-;27144:2334;27082:2396;;:::o;8207:261:4:-;8275:13;8379:1;8373:4;8366:15;8407:1;8401:4;8394:15;8447:4;8441;8431:21;8422:30;;8207:261;;;;:::o;14794:318:1:-;14864:14;15093:1;15083:8;15080:15;15054:24;15050:46;15040:56;;14794:318;;;:::o;-1:-1:-1:-;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;:::o;7:77:6:-;44:7;73:5;62:16;;7:77;;;:::o;90:118::-;177:24;195:5;177:24;:::i;:::-;172:3;165:37;90:118;;:::o;214:222::-;307:4;345:2;334:9;330:18;322:26;;358:71;426:1;415:9;411:17;402:6;358:71;:::i;:::-;214:222;;;;:::o;442:75::-;475:6;508:2;502:9;492:19;;442:75;:::o;523:117::-;632:1;629;622:12;646:117;755:1;752;745:12;769:149;805:7;845:66;838:5;834:78;823:89;;769:149;;;:::o;924:120::-;996:23;1013:5;996:23;:::i;:::-;989:5;986:34;976:62;;1034:1;1031;1024:12;976:62;924:120;:::o;1050:137::-;1095:5;1133:6;1120:20;1111:29;;1149:32;1175:5;1149:32;:::i;:::-;1050:137;;;;:::o;1193:327::-;1251:6;1300:2;1288:9;1279:7;1275:23;1271:32;1268:119;;;1306:79;;:::i;:::-;1268:119;1426:1;1451:52;1495:7;1486:6;1475:9;1471:22;1451:52;:::i;:::-;1441:62;;1397:116;1193:327;;;;:::o;1526:90::-;1560:7;1603:5;1596:13;1589:21;1578:32;;1526:90;;;:::o;1622:109::-;1703:21;1718:5;1703:21;:::i;:::-;1698:3;1691:34;1622:109;;:::o;1737:210::-;1824:4;1862:2;1851:9;1847:18;1839:26;;1875:65;1937:1;1926:9;1922:17;1913:6;1875:65;:::i;:::-;1737:210;;;;:::o;1953:99::-;2005:6;2039:5;2033:12;2023:22;;1953:99;;;:::o;2058:169::-;2142:11;2176:6;2171:3;2164:19;2216:4;2211:3;2207:14;2192:29;;2058:169;;;;:::o;2233:307::-;2301:1;2311:113;2325:6;2322:1;2319:13;2311:113;;;2410:1;2405:3;2401:11;2395:18;2391:1;2386:3;2382:11;2375:39;2347:2;2344:1;2340:10;2335:15;;2311:113;;;2442:6;2439:1;2436:13;2433:101;;;2522:1;2513:6;2508:3;2504:16;2497:27;2433:101;2282:258;2233:307;;;:::o;2546:102::-;2587:6;2638:2;2634:7;2629:2;2622:5;2618:14;2614:28;2604:38;;2546:102;;;:::o;2654:364::-;2742:3;2770:39;2803:5;2770:39;:::i;:::-;2825:71;2889:6;2884:3;2825:71;:::i;:::-;2818:78;;2905:52;2950:6;2945:3;2938:4;2931:5;2927:16;2905:52;:::i;:::-;2982:29;3004:6;2982:29;:::i;:::-;2977:3;2973:39;2966:46;;2746:272;2654:364;;;;:::o;3024:313::-;3137:4;3175:2;3164:9;3160:18;3152:26;;3224:9;3218:4;3214:20;3210:1;3199:9;3195:17;3188:47;3252:78;3325:4;3316:6;3252:78;:::i;:::-;3244:86;;3024:313;;;;:::o;3343:122::-;3416:24;3434:5;3416:24;:::i;:::-;3409:5;3406:35;3396:63;;3455:1;3452;3445:12;3396:63;3343:122;:::o;3471:139::-;3517:5;3555:6;3542:20;3533:29;;3571:33;3598:5;3571:33;:::i;:::-;3471:139;;;;:::o;3616:329::-;3675:6;3724:2;3712:9;3703:7;3699:23;3695:32;3692:119;;;3730:79;;:::i;:::-;3692:119;3850:1;3875:53;3920:7;3911:6;3900:9;3896:22;3875:53;:::i;:::-;3865:63;;3821:117;3616:329;;;;:::o;3951:126::-;3988:7;4028:42;4021:5;4017:54;4006:65;;3951:126;;;:::o;4083:96::-;4120:7;4149:24;4167:5;4149:24;:::i;:::-;4138:35;;4083:96;;;:::o;4185:118::-;4272:24;4290:5;4272:24;:::i;:::-;4267:3;4260:37;4185:118;;:::o;4309:222::-;4402:4;4440:2;4429:9;4425:18;4417:26;;4453:71;4521:1;4510:9;4506:17;4497:6;4453:71;:::i;:::-;4309:222;;;;:::o;4537:122::-;4610:24;4628:5;4610:24;:::i;:::-;4603:5;4600:35;4590:63;;4649:1;4646;4639:12;4590:63;4537:122;:::o;4665:139::-;4711:5;4749:6;4736:20;4727:29;;4765:33;4792:5;4765:33;:::i;:::-;4665:139;;;;:::o;4810:474::-;4878:6;4886;4935:2;4923:9;4914:7;4910:23;4906:32;4903:119;;;4941:79;;:::i;:::-;4903:119;5061:1;5086:53;5131:7;5122:6;5111:9;5107:22;5086:53;:::i;:::-;5076:63;;5032:117;5188:2;5214:53;5259:7;5250:6;5239:9;5235:22;5214:53;:::i;:::-;5204:63;;5159:118;4810:474;;;;;:::o;5290:619::-;5367:6;5375;5383;5432:2;5420:9;5411:7;5407:23;5403:32;5400:119;;;5438:79;;:::i;:::-;5400:119;5558:1;5583:53;5628:7;5619:6;5608:9;5604:22;5583:53;:::i;:::-;5573:63;;5529:117;5685:2;5711:53;5756:7;5747:6;5736:9;5732:22;5711:53;:::i;:::-;5701:63;;5656:118;5813:2;5839:53;5884:7;5875:6;5864:9;5860:22;5839:53;:::i;:::-;5829:63;;5784:118;5290:619;;;;;:::o;5915:77::-;5952:7;5981:5;5970:16;;5915:77;;;:::o;5998:118::-;6085:24;6103:5;6085:24;:::i;:::-;6080:3;6073:37;5998:118;;:::o;6122:222::-;6215:4;6253:2;6242:9;6238:18;6230:26;;6266:71;6334:1;6323:9;6319:17;6310:6;6266:71;:::i;:::-;6122:222;;;;:::o;6350:117::-;6459:1;6456;6449:12;6473:117;6582:1;6579;6572:12;6596:180;6644:77;6641:1;6634:88;6741:4;6738:1;6731:15;6765:4;6762:1;6755:15;6782:281;6865:27;6887:4;6865:27;:::i;:::-;6857:6;6853:40;6995:6;6983:10;6980:22;6959:18;6947:10;6944:34;6941:62;6938:88;;;7006:18;;:::i;:::-;6938:88;7046:10;7042:2;7035:22;6825:238;6782:281;;:::o;7069:129::-;7103:6;7130:20;;:::i;:::-;7120:30;;7159:33;7187:4;7179:6;7159:33;:::i;:::-;7069:129;;;:::o;7204:308::-;7266:4;7356:18;7348:6;7345:30;7342:56;;;7378:18;;:::i;:::-;7342:56;7416:29;7438:6;7416:29;:::i;:::-;7408:37;;7500:4;7494;7490:15;7482:23;;7204:308;;;:::o;7518:154::-;7602:6;7597:3;7592;7579:30;7664:1;7655:6;7650:3;7646:16;7639:27;7518:154;;;:::o;7678:412::-;7756:5;7781:66;7797:49;7839:6;7797:49;:::i;:::-;7781:66;:::i;:::-;7772:75;;7870:6;7863:5;7856:21;7908:4;7901:5;7897:16;7946:3;7937:6;7932:3;7928:16;7925:25;7922:112;;;7953:79;;:::i;:::-;7922:112;8043:41;8077:6;8072:3;8067;8043:41;:::i;:::-;7762:328;7678:412;;;;;:::o;8110:340::-;8166:5;8215:3;8208:4;8200:6;8196:17;8192:27;8182:122;;8223:79;;:::i;:::-;8182:122;8340:6;8327:20;8365:79;8440:3;8432:6;8425:4;8417:6;8413:17;8365:79;:::i;:::-;8356:88;;8172:278;8110:340;;;;:::o;8456:509::-;8525:6;8574:2;8562:9;8553:7;8549:23;8545:32;8542:119;;;8580:79;;:::i;:::-;8542:119;8728:1;8717:9;8713:17;8700:31;8758:18;8750:6;8747:30;8744:117;;;8780:79;;:::i;:::-;8744:117;8885:63;8940:7;8931:6;8920:9;8916:22;8885:63;:::i;:::-;8875:73;;8671:287;8456:509;;;;:::o;8971:329::-;9030:6;9079:2;9067:9;9058:7;9054:23;9050:32;9047:119;;;9085:79;;:::i;:::-;9047:119;9205:1;9230:53;9275:7;9266:6;9255:9;9251:22;9230:53;:::i;:::-;9220:63;;9176:117;8971:329;;;;:::o;9306:117::-;9415:1;9412;9405:12;9429:117;9538:1;9535;9528:12;9569:568;9642:8;9652:6;9702:3;9695:4;9687:6;9683:17;9679:27;9669:122;;9710:79;;:::i;:::-;9669:122;9823:6;9810:20;9800:30;;9853:18;9845:6;9842:30;9839:117;;;9875:79;;:::i;:::-;9839:117;9989:4;9981:6;9977:17;9965:29;;10043:3;10035:4;10027:6;10023:17;10013:8;10009:32;10006:41;10003:128;;;10050:79;;:::i;:::-;10003:128;9569:568;;;;;:::o;10143:704::-;10238:6;10246;10254;10303:2;10291:9;10282:7;10278:23;10274:32;10271:119;;;10309:79;;:::i;:::-;10271:119;10457:1;10446:9;10442:17;10429:31;10487:18;10479:6;10476:30;10473:117;;;10509:79;;:::i;:::-;10473:117;10622:80;10694:7;10685:6;10674:9;10670:22;10622:80;:::i;:::-;10604:98;;;;10400:312;10751:2;10777:53;10822:7;10813:6;10802:9;10798:22;10777:53;:::i;:::-;10767:63;;10722:118;10143:704;;;;;:::o;10853:122::-;10926:24;10944:5;10926:24;:::i;:::-;10919:5;10916:35;10906:63;;10965:1;10962;10955:12;10906:63;10853:122;:::o;10981:139::-;11027:5;11065:6;11052:20;11043:29;;11081:33;11108:5;11081:33;:::i;:::-;10981:139;;;;:::o;11126:329::-;11185:6;11234:2;11222:9;11213:7;11209:23;11205:32;11202:119;;;11240:79;;:::i;:::-;11202:119;11360:1;11385:53;11430:7;11421:6;11410:9;11406:22;11385:53;:::i;:::-;11375:63;;11331:117;11126:329;;;;:::o;11461:116::-;11531:21;11546:5;11531:21;:::i;:::-;11524:5;11521:32;11511:60;;11567:1;11564;11557:12;11511:60;11461:116;:::o;11583:133::-;11626:5;11664:6;11651:20;11642:29;;11680:30;11704:5;11680:30;:::i;:::-;11583:133;;;;:::o;11722:468::-;11787:6;11795;11844:2;11832:9;11823:7;11819:23;11815:32;11812:119;;;11850:79;;:::i;:::-;11812:119;11970:1;11995:53;12040:7;12031:6;12020:9;12016:22;11995:53;:::i;:::-;11985:63;;11941:117;12097:2;12123:50;12165:7;12156:6;12145:9;12141:22;12123:50;:::i;:::-;12113:60;;12068:115;11722:468;;;;;:::o;12196:307::-;12257:4;12347:18;12339:6;12336:30;12333:56;;;12369:18;;:::i;:::-;12333:56;12407:29;12429:6;12407:29;:::i;:::-;12399:37;;12491:4;12485;12481:15;12473:23;;12196:307;;;:::o;12509:410::-;12586:5;12611:65;12627:48;12668:6;12627:48;:::i;:::-;12611:65;:::i;:::-;12602:74;;12699:6;12692:5;12685:21;12737:4;12730:5;12726:16;12775:3;12766:6;12761:3;12757:16;12754:25;12751:112;;;12782:79;;:::i;:::-;12751:112;12872:41;12906:6;12901:3;12896;12872:41;:::i;:::-;12592:327;12509:410;;;;;:::o;12938:338::-;12993:5;13042:3;13035:4;13027:6;13023:17;13019:27;13009:122;;13050:79;;:::i;:::-;13009:122;13167:6;13154:20;13192:78;13266:3;13258:6;13251:4;13243:6;13239:17;13192:78;:::i;:::-;13183:87;;12999:277;12938:338;;;;:::o;13282:943::-;13377:6;13385;13393;13401;13450:3;13438:9;13429:7;13425:23;13421:33;13418:120;;;13457:79;;:::i;:::-;13418:120;13577:1;13602:53;13647:7;13638:6;13627:9;13623:22;13602:53;:::i;:::-;13592:63;;13548:117;13704:2;13730:53;13775:7;13766:6;13755:9;13751:22;13730:53;:::i;:::-;13720:63;;13675:118;13832:2;13858:53;13903:7;13894:6;13883:9;13879:22;13858:53;:::i;:::-;13848:63;;13803:118;13988:2;13977:9;13973:18;13960:32;14019:18;14011:6;14008:30;14005:117;;;14041:79;;:::i;:::-;14005:117;14146:62;14200:7;14191:6;14180:9;14176:22;14146:62;:::i;:::-;14136:72;;13931:287;13282:943;;;;;;;:::o;14231:474::-;14299:6;14307;14356:2;14344:9;14335:7;14331:23;14327:32;14324:119;;;14362:79;;:::i;:::-;14324:119;14482:1;14507:53;14552:7;14543:6;14532:9;14528:22;14507:53;:::i;:::-;14497:63;;14453:117;14609:2;14635:53;14680:7;14671:6;14660:9;14656:22;14635:53;:::i;:::-;14625:63;;14580:118;14231:474;;;;;:::o;14711:::-;14779:6;14787;14836:2;14824:9;14815:7;14811:23;14807:32;14804:119;;;14842:79;;:::i;:::-;14804:119;14962:1;14987:53;15032:7;15023:6;15012:9;15008:22;14987:53;:::i;:::-;14977:63;;14933:117;15089:2;15115:53;15160:7;15151:6;15140:9;15136:22;15115:53;:::i;:::-;15105:63;;15060:118;14711:474;;;;;:::o;15208:568::-;15281:8;15291:6;15341:3;15334:4;15326:6;15322:17;15318:27;15308:122;;15349:79;;:::i;:::-;15308:122;15462:6;15449:20;15439:30;;15492:18;15484:6;15481:30;15478:117;;;15514:79;;:::i;:::-;15478:117;15628:4;15620:6;15616:17;15604:29;;15682:3;15674:4;15666:6;15662:17;15652:8;15648:32;15645:41;15642:128;;;15689:79;;:::i;:::-;15642:128;15208:568;;;;;:::o;15782:704::-;15877:6;15885;15893;15942:2;15930:9;15921:7;15917:23;15913:32;15910:119;;;15948:79;;:::i;:::-;15910:119;16068:1;16093:53;16138:7;16129:6;16118:9;16114:22;16093:53;:::i;:::-;16083:63;;16039:117;16223:2;16212:9;16208:18;16195:32;16254:18;16246:6;16243:30;16240:117;;;16276:79;;:::i;:::-;16240:117;16389:80;16461:7;16452:6;16441:9;16437:22;16389:80;:::i;:::-;16371:98;;;;16166:313;15782:704;;;;;:::o;16492:180::-;16540:77;16537:1;16530:88;16637:4;16634:1;16627:15;16661:4;16658:1;16651:15;16678:320;16722:6;16759:1;16753:4;16749:12;16739:22;;16806:1;16800:4;16796:12;16827:18;16817:81;;16883:4;16875:6;16871:17;16861:27;;16817:81;16945:2;16937:6;16934:14;16914:18;16911:38;16908:84;;;16964:18;;:::i;:::-;16908:84;16729:269;16678:320;;;:::o;17004:94::-;17037:8;17085:5;17081:2;17077:14;17056:35;;17004:94;;;:::o;17104:::-;17143:7;17172:20;17186:5;17172:20;:::i;:::-;17161:31;;17104:94;;;:::o;17204:100::-;17243:7;17272:26;17292:5;17272:26;:::i;:::-;17261:37;;17204:100;;;:::o;17310:157::-;17415:45;17435:24;17453:5;17435:24;:::i;:::-;17415:45;:::i;:::-;17410:3;17403:58;17310:157;;:::o;17473:256::-;17585:3;17600:75;17671:3;17662:6;17600:75;:::i;:::-;17700:2;17695:3;17691:12;17684:19;;17720:3;17713:10;;17473:256;;;;:::o;17735:180::-;17875:32;17871:1;17863:6;17859:14;17852:56;17735:180;:::o;17921:366::-;18063:3;18084:67;18148:2;18143:3;18084:67;:::i;:::-;18077:74;;18160:93;18249:3;18160:93;:::i;:::-;18278:2;18273:3;18269:12;18262:19;;17921:366;;;:::o;18293:419::-;18459:4;18497:2;18486:9;18482:18;18474:26;;18546:9;18540:4;18536:20;18532:1;18521:9;18517:17;18510:47;18574:131;18700:4;18574:131;:::i;:::-;18566:139;;18293:419;;;:::o;18718:165::-;18858:17;18854:1;18846:6;18842:14;18835:41;18718:165;:::o;18889:366::-;19031:3;19052:67;19116:2;19111:3;19052:67;:::i;:::-;19045:74;;19128:93;19217:3;19128:93;:::i;:::-;19246:2;19241:3;19237:12;19230:19;;18889:366;;;:::o;19261:419::-;19427:4;19465:2;19454:9;19450:18;19442:26;;19514:9;19508:4;19504:20;19500:1;19489:9;19485:17;19478:47;19542:131;19668:4;19542:131;:::i;:::-;19534:139;;19261:419;;;:::o;19686:171::-;19826:23;19822:1;19814:6;19810:14;19803:47;19686:171;:::o;19863:366::-;20005:3;20026:67;20090:2;20085:3;20026:67;:::i;:::-;20019:74;;20102:93;20191:3;20102:93;:::i;:::-;20220:2;20215:3;20211:12;20204:19;;19863:366;;;:::o;20235:419::-;20401:4;20439:2;20428:9;20424:18;20416:26;;20488:9;20482:4;20478:20;20474:1;20463:9;20459:17;20452:47;20516:131;20642:4;20516:131;:::i;:::-;20508:139;;20235:419;;;:::o;20660:177::-;20800:29;20796:1;20788:6;20784:14;20777:53;20660:177;:::o;20843:366::-;20985:3;21006:67;21070:2;21065:3;21006:67;:::i;:::-;20999:74;;21082:93;21171:3;21082:93;:::i;:::-;21200:2;21195:3;21191:12;21184:19;;20843:366;;;:::o;21215:419::-;21381:4;21419:2;21408:9;21404:18;21396:26;;21468:9;21462:4;21458:20;21454:1;21443:9;21439:17;21432:47;21496:131;21622:4;21496:131;:::i;:::-;21488:139;;21215:419;;;:::o;21640:180::-;21688:77;21685:1;21678:88;21785:4;21782:1;21775:15;21809:4;21806:1;21799:15;21826:305;21866:3;21885:20;21903:1;21885:20;:::i;:::-;21880:25;;21919:20;21937:1;21919:20;:::i;:::-;21914:25;;22073:1;22005:66;22001:74;21998:1;21995:81;21992:107;;;22079:18;;:::i;:::-;21992:107;22123:1;22120;22116:9;22109:16;;21826:305;;;;:::o;22137:182::-;22277:34;22273:1;22265:6;22261:14;22254:58;22137:182;:::o;22325:366::-;22467:3;22488:67;22552:2;22547:3;22488:67;:::i;:::-;22481:74;;22564:93;22653:3;22564:93;:::i;:::-;22682:2;22677:3;22673:12;22666:19;;22325:366;;;:::o;22697:419::-;22863:4;22901:2;22890:9;22886:18;22878:26;;22950:9;22944:4;22940:20;22936:1;22925:9;22921:17;22914:47;22978:131;23104:4;22978:131;:::i;:::-;22970:139;;22697:419;;;:::o;23122:180::-;23170:77;23167:1;23160:88;23267:4;23264:1;23257:15;23291:4;23288:1;23281:15;23308:176;23340:1;23357:20;23375:1;23357:20;:::i;:::-;23352:25;;23391:20;23409:1;23391:20;:::i;:::-;23386:25;;23430:1;23420:35;;23435:18;;:::i;:::-;23420:35;23476:1;23473;23469:9;23464:14;;23308:176;;;;:::o;23490:233::-;23529:3;23552:24;23570:5;23552:24;:::i;:::-;23543:33;;23598:66;23591:5;23588:77;23585:103;;;23668:18;;:::i;:::-;23585:103;23715:1;23708:5;23704:13;23697:20;;23490:233;;;:::o;23729:191::-;23769:4;23789:20;23807:1;23789:20;:::i;:::-;23784:25;;23823:20;23841:1;23823:20;:::i;:::-;23818:25;;23862:1;23859;23856:8;23853:34;;;23867:18;;:::i;:::-;23853:34;23912:1;23909;23905:9;23897:17;;23729:191;;;;:::o;23926:348::-;23966:7;23989:20;24007:1;23989:20;:::i;:::-;23984:25;;24023:20;24041:1;24023:20;:::i;:::-;24018:25;;24211:1;24143:66;24139:74;24136:1;24133:81;24128:1;24121:9;24114:17;24110:105;24107:131;;;24218:18;;:::i;:::-;24107:131;24266:1;24263;24259:9;24248:20;;23926:348;;;;:::o;24280:179::-;24420:31;24416:1;24408:6;24404:14;24397:55;24280:179;:::o;24465:366::-;24607:3;24628:67;24692:2;24687:3;24628:67;:::i;:::-;24621:74;;24704:93;24793:3;24704:93;:::i;:::-;24822:2;24817:3;24813:12;24806:19;;24465:366;;;:::o;24837:419::-;25003:4;25041:2;25030:9;25026:18;25018:26;;25090:9;25084:4;25080:20;25076:1;25065:9;25061:17;25054:47;25118:131;25244:4;25118:131;:::i;:::-;25110:139;;24837:419;;;:::o;25262:179::-;25402:31;25398:1;25390:6;25386:14;25379:55;25262:179;:::o;25447:366::-;25589:3;25610:67;25674:2;25669:3;25610:67;:::i;:::-;25603:74;;25686:93;25775:3;25686:93;:::i;:::-;25804:2;25799:3;25795:12;25788:19;;25447:366;;;:::o;25819:419::-;25985:4;26023:2;26012:9;26008:18;26000:26;;26072:9;26066:4;26062:20;26058:1;26047:9;26043:17;26036:47;26100:131;26226:4;26100:131;:::i;:::-;26092:139;;25819:419;;;:::o;26244:174::-;26384:26;26380:1;26372:6;26368:14;26361:50;26244:174;:::o;26424:366::-;26566:3;26587:67;26651:2;26646:3;26587:67;:::i;:::-;26580:74;;26663:93;26752:3;26663:93;:::i;:::-;26781:2;26776:3;26772:12;26765:19;;26424:366;;;:::o;26796:419::-;26962:4;27000:2;26989:9;26985:18;26977:26;;27049:9;27043:4;27039:20;27035:1;27024:9;27020:17;27013:47;27077:131;27203:4;27077:131;:::i;:::-;27069:139;;26796:419;;;:::o;27221:172::-;27361:24;27357:1;27349:6;27345:14;27338:48;27221:172;:::o;27399:366::-;27541:3;27562:67;27626:2;27621:3;27562:67;:::i;:::-;27555:74;;27638:93;27727:3;27638:93;:::i;:::-;27756:2;27751:3;27747:12;27740:19;;27399:366;;;:::o;27771:419::-;27937:4;27975:2;27964:9;27960:18;27952:26;;28024:9;28018:4;28014:20;28010:1;27999:9;27995:17;27988:47;28052:131;28178:4;28052:131;:::i;:::-;28044:139;;27771:419;;;:::o;28196:180::-;28336:32;28332:1;28324:6;28320:14;28313:56;28196:180;:::o;28382:366::-;28524:3;28545:67;28609:2;28604:3;28545:67;:::i;:::-;28538:74;;28621:93;28710:3;28621:93;:::i;:::-;28739:2;28734:3;28730:12;28723:19;;28382:366;;;:::o;28754:419::-;28920:4;28958:2;28947:9;28943:18;28935:26;;29007:9;29001:4;28997:20;28993:1;28982:9;28978:17;28971:47;29035:131;29161:4;29035:131;:::i;:::-;29027:139;;28754:419;;;:::o;29179:169::-;29319:21;29315:1;29307:6;29303:14;29296:45;29179:169;:::o;29354:366::-;29496:3;29517:67;29581:2;29576:3;29517:67;:::i;:::-;29510:74;;29593:93;29682:3;29593:93;:::i;:::-;29711:2;29706:3;29702:12;29695:19;;29354:366;;;:::o;29726:419::-;29892:4;29930:2;29919:9;29915:18;29907:26;;29979:9;29973:4;29969:20;29965:1;29954:9;29950:17;29943:47;30007:131;30133:4;30007:131;:::i;:::-;29999:139;;29726:419;;;:::o;30151:148::-;30253:11;30290:3;30275:18;;30151:148;;;;:::o;30305:377::-;30411:3;30439:39;30472:5;30439:39;:::i;:::-;30494:89;30576:6;30571:3;30494:89;:::i;:::-;30487:96;;30592:52;30637:6;30632:3;30625:4;30618:5;30614:16;30592:52;:::i;:::-;30669:6;30664:3;30660:16;30653:23;;30415:267;30305:377;;;;:::o;30688:435::-;30868:3;30890:95;30981:3;30972:6;30890:95;:::i;:::-;30883:102;;31002:95;31093:3;31084:6;31002:95;:::i;:::-;30995:102;;31114:3;31107:10;;30688:435;;;;;:::o;31129:225::-;31269:34;31265:1;31257:6;31253:14;31246:58;31338:8;31333:2;31325:6;31321:15;31314:33;31129:225;:::o;31360:366::-;31502:3;31523:67;31587:2;31582:3;31523:67;:::i;:::-;31516:74;;31599:93;31688:3;31599:93;:::i;:::-;31717:2;31712:3;31708:12;31701:19;;31360:366;;;:::o;31732:419::-;31898:4;31936:2;31925:9;31921:18;31913:26;;31985:9;31979:4;31975:20;31971:1;31960:9;31956:17;31949:47;32013:131;32139:4;32013:131;:::i;:::-;32005:139;;31732:419;;;:::o;32157:180::-;32205:77;32202:1;32195:88;32302:4;32299:1;32292:15;32326:4;32323:1;32316:15;32343:174;32483:26;32479:1;32471:6;32467:14;32460:50;32343:174;:::o;32523:366::-;32665:3;32686:67;32750:2;32745:3;32686:67;:::i;:::-;32679:74;;32762:93;32851:3;32762:93;:::i;:::-;32880:2;32875:3;32871:12;32864:19;;32523:366;;;:::o;32895:419::-;33061:4;33099:2;33088:9;33084:18;33076:26;;33148:9;33142:4;33138:20;33134:1;33123:9;33119:17;33112:47;33176:131;33302:4;33176:131;:::i;:::-;33168:139;;32895:419;;;:::o;33320:182::-;33460:34;33456:1;33448:6;33444:14;33437:58;33320:182;:::o;33508:366::-;33650:3;33671:67;33735:2;33730:3;33671:67;:::i;:::-;33664:74;;33747:93;33836:3;33747:93;:::i;:::-;33865:2;33860:3;33856:12;33849:19;;33508:366;;;:::o;33880:419::-;34046:4;34084:2;34073:9;34069:18;34061:26;;34133:9;34127:4;34123:20;34119:1;34108:9;34104:17;34097:47;34161:131;34287:4;34161:131;:::i;:::-;34153:139;;33880:419;;;:::o;34305:98::-;34356:6;34390:5;34384:12;34374:22;;34305:98;;;:::o;34409:168::-;34492:11;34526:6;34521:3;34514:19;34566:4;34561:3;34557:14;34542:29;;34409:168;;;;:::o;34583:360::-;34669:3;34697:38;34729:5;34697:38;:::i;:::-;34751:70;34814:6;34809:3;34751:70;:::i;:::-;34744:77;;34830:52;34875:6;34870:3;34863:4;34856:5;34852:16;34830:52;:::i;:::-;34907:29;34929:6;34907:29;:::i;:::-;34902:3;34898:39;34891:46;;34673:270;34583:360;;;;:::o;34949:640::-;35144:4;35182:3;35171:9;35167:19;35159:27;;35196:71;35264:1;35253:9;35249:17;35240:6;35196:71;:::i;:::-;35277:72;35345:2;35334:9;35330:18;35321:6;35277:72;:::i;:::-;35359;35427:2;35416:9;35412:18;35403:6;35359:72;:::i;:::-;35478:9;35472:4;35468:20;35463:2;35452:9;35448:18;35441:48;35506:76;35577:4;35568:6;35506:76;:::i;:::-;35498:84;;34949:640;;;;;;;:::o;35595:141::-;35651:5;35682:6;35676:13;35667:22;;35698:32;35724:5;35698:32;:::i;:::-;35595:141;;;;:::o;35742:349::-;35811:6;35860:2;35848:9;35839:7;35835:23;35831:32;35828:119;;;35866:79;;:::i;:::-;35828:119;35986:1;36011:63;36066:7;36057:6;36046:9;36042:22;36011:63;:::i;:::-;36001:73;;35957:127;35742:349;;;;:::o
Swarm Source
ipfs://a2d766f66df6c481f08e31028079e2e5299550fd9d6ce8b8cb16b4d4dbb86239
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
[ Download: CSV Export ]
A token is a representation of an on-chain or off-chain asset. The token page shows information such as price, total supply, holders, transfers and social links. Learn more about this page in our Knowledge Base.