Abstract Testnet

DYLI (DYLI)

Overview

TokenID

10002

Total Transfers

-

Market

Onchain Market Cap

$0.00

Circulating Supply Market Cap

-
TokenID: 10002
Loading...
Loading
Loading...
Loading
Loading...
Loading

Click here to update the token information / general information
This contract may be a proxy contract. Click on More Options and select Is this a proxy? to confirm and enable the "Read as Proxy" & "Write as Proxy" tabs.

Contract Source Code Verified (Exact Match)

Contract Name:
DYLI

Compiler Version
v0.8.24+commit.e11b9ed9

ZkSolc Version
v1.5.7

Optimization Enabled:
Yes with Mode 3

Other Settings:
paris EvmVersion

Contract Source Code (Solidity Standard Json-Input format)

File 1 of 36 : DYLI.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

import "solady/src/utils/ECDSA.sol";
import "solady/src/utils/LibBitmap.sol";
import "solady/src/auth/Ownable.sol";
import "solady/src/utils/LibString.sol";
import {AccessControl} from "@openzeppelin/contracts/access/AccessControl.sol";
import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import {ERC1155C, ERC1155OpenZeppelin} from "@limitbreak/creator-token-contracts/contracts/erc1155c/ERC1155C.sol";
import {ERC2981, BasicRoyalties} from "@limitbreak/creator-token-contracts/contracts/programmable-royalties/BasicRoyalties.sol";
import "hardhat/console.sol";

/**
 * @title DYLI
 * @dev ERC1155C token contract with programmable royalties and queue system
 * @author DYLI (https://www.dyli.io/)
 */
contract DYLI is ERC1155C, Ownable, BasicRoyalties {
    /// @notice BitMap for refund override status of token IDs
    using LibBitmap for LibBitmap.Bitmap;

    /// @notice Error for invalid nonce
    error InvalidNonce();

    /// @notice Error for invalid signature
    error InvalidSignature();

    /// @notice Error when a payment fails
    error PaymentFailed();

    /// @notice Error when the sale has not started
    error SaleNotStarted();

    /// @notice Error when the caller is not the token owner or a marketplace
    error OnlyTokenOwnerOrMarketplaceCanTransfer();

    /// @notice Error when the sale has ended
    error SaleEnded();

    /// @notice Error when exceeding maximum quantity
    error ExceedsMaxQuantity();

    /// @notice Error when token minting is disabled
    error TokenMintingDisabled();

    /// @notice Error when token is not refundable
    error TokenNotRefundable();

    /// @notice Error for refund transfer failure
    error RefundTransferFailed();

    /// @notice Error for blockhash not found
    error BlockhashNotFound();

    /// @notice Error for blockhash expiration
    error BlockhashExpired();

    /// @notice Error for a user not in the queue
    error NotInQueue();

    /// @notice Error when the queue is already processed
    error QueueAlreadyProcessed();

    /// @notice Error when the queue is still open
    error QueueStillOpen();

    /// @notice Error when the queue period has ended
    error QueuePeriodEnded();

    /// @notice Error when the queue is empty
    error QueueEmpty();

    /// @notice Error when a user is already in the queue
    error AlreadyInQueue();

    /// @notice Error when the queue blockhash is not ready
    error BlockhashNotReady();

    /// @notice Error when the queue is already revealed
    error QueueAlreadyRevealed();

    /// @notice Error when a queue has already been committed for processing
    error QueueAlreadyCommitted();

    /// @notice Error for insufficient tokens to refund
    error InsufficientTokensToRefund();

    /// @notice Error for insufficient tokens to redeem
    error InsufficientTokensToRedeem();

    /// @notice Error lose queue refund being more than queue fee
    error LoseQueueRefundExceedsQueueFee();

    /// @notice Mapping of tokenId to queue data
    mapping(uint256 => Queue) public queue;

    /// @notice Mapping of tokenId to whether a user has entered the queue
    mapping(uint256 => mapping(address => bool)) public enteredQueue;

    /// @notice Mapping of tokenId to token data
    mapping(uint256 => TokenData) public tokenData;

    /// @notice Mapping of tokenId to disabled status
    mapping(uint256 => bool) public tokenDisabled;

    /// @notice Mapping of tokenId to total minted count
    mapping(uint256 => uint256) public totalMinted;

    /// @notice Mapping of tokenId to total refunded count
    mapping(uint256 => uint256) public totalRefunded;

    /// @notice Mapping of tokenId to total redeemed count
    mapping(uint256 => uint256) public totalRedeemed;

    /// @notice Mapping of user address to nonce
    mapping(address => uint256) public nonces;

    /// @notice Mapping of user address and nonce to whether it was used
    mapping(address => mapping(uint256 => bool)) public nonceUsed;

    /// @notice Mapping of blacklisted marketplaces
    mapping(address => bool) public blacklistedMarketplaces;

    /// @notice USDC token contract
    IERC20 public immutable USDC;

    /// @notice Current token ID
    uint256 public currentTokenId = 10000;

    /// @notice Address of the signer
    address public signerAddress;

    /// @notice Fee amount
    uint256 public fee;

    /// @notice Queue fee amount
    uint256 public queueFee;

    /// @notice Fee you get back if you lose the queue
    uint256 public loseQueueRefund;

    /// @notice Create fee amount
    uint256 public createFee;

    /// @notice Base URI for tokens
    string public baseURI;

    /// @dev Fee recipient address
    address private _feeRecipient;

    /// @notice Bitmap to override the refundable status of token IDs.
    LibBitmap.Bitmap private isRefundableOverride;

    /// @notice Emitted when a new drop is created
    event DropCreated(
        uint256 indexed tokenId,
        address indexed creator,
        uint256 price
    );

    /// @notice Emitted when a token is minted
    event TokenMinted(
        uint256 indexed tokenId,
        address indexed minter,
        uint256 price,
        uint256 fee
    );

    /// @notice Emitted when a token is refunded
    event TokenRefunded(
        uint256 indexed tokenId,
        address indexed minter,
        uint256 amount,
        uint256 price
    );

    /// @notice Emitted when a token is redeemed
    event TokenRedeemed(uint256 indexed tokenId, address indexed redeemer);

    /// @notice Emitted when a user joins a queue
    event QueueJoined(
        uint256 indexed tokenId,
        address indexed user,
        uint256 amount
    );

    /// @notice Emitted when a user leaves a queue
    event QueueLeft(
        uint256 indexed tokenId,
        address indexed user,
        uint256 amount
    );

    /**
     * @dev Modifier to validate and update nonces
     */
    modifier checkNonce(address user, uint256 nonce) {
        if (nonceUsed[user][nonce]) revert InvalidNonce();
        nonceUsed[user][nonce] = true;
        nonces[user]++;
        _;
    }

    /**
     * @dev Token data structure
     */
    struct TokenData {
        uint256 nonReserved;
        uint256 price;
        uint256 startTimestamp;
        uint256 endTimestamp;
        uint256 minMint;
        address creator;
        bool isOE;
        uint256 reserved;
        uint256 purchased;
    }

    /**
     * @dev Queue structure
     */
    struct Queue {
        uint256 reserved;
        uint256 cost;
        uint256 blockCommit;
        uint256 rng;
        uint256 entries;
        uint256 claimed;
        uint256 queueFee;
        uint256 loseQueueRefund;
    }

    /**
     * @notice Constructor to initialize the contract
     * @param _baseURI Base URI for token metadata
     * @param usdc_ Address of the USDC token contract
     * @param signerAddress_ Address of the signer
     * @param feeRecipient_ Address to receive fees
     * @param royaltyFeeNumerator_ Royalty fee numerator
     * @param initialQueueFee Initial fee for joining the queue
     * @param initialLoseQueueRefund Initial refund if a user loses the queue
     * @param initialCreateFee Initial fee for creating a new drop
     * @param initialFee Initial fee amount for minting
     */
    constructor(
        string memory _baseURI,
        address usdc_,
        address signerAddress_,
        address feeRecipient_,
        uint96 royaltyFeeNumerator_,
        uint256 initialQueueFee,
        uint256 initialLoseQueueRefund,
        uint256 initialCreateFee,
        uint256 initialFee
    )
        ERC1155OpenZeppelin(_baseURI)
        BasicRoyalties(feeRecipient_, royaltyFeeNumerator_)
    {
        _initializeOwner(msg.sender);
        USDC = IERC20(usdc_);
        baseURI = _baseURI;
        signerAddress = signerAddress_;
        _feeRecipient = feeRecipient_;
        fee = initialFee;
        queueFee = initialQueueFee;
        loseQueueRefund = initialLoseQueueRefund;
        createFee = initialCreateFee;
    }

    /**
     * @notice Returns the name of the contract
     * @return The name of the contract
     */
    function name() external pure returns (string memory) {
        return "DYLI";
    }

    /**
     * @notice Returns the symbol of the contract
     * @return The symbol of the contract
     */
    function symbol() external pure returns (string memory) {
        return "DYLI";
    }

    /**
     * @notice Updates the base URI for token metadata
     * @param _URI New base URI
     */
    function setURI(string memory _URI) external onlyOwner {
        baseURI = _URI;
    }

    /**
     * @notice Updates the fee recipient address
     * @param newFeeRecipient Address of the new fee recipient
     */
    function setFeeRecipient(address newFeeRecipient) external onlyOwner {
        _feeRecipient = newFeeRecipient;
    }

    /**
     * @notice Updates the fee amount
     * @param newFee New fee amount
     */
    function setFee(uint256 newFee) external onlyOwner {
        fee = newFee;
    }

    /**
     * @notice Updates the queue fee amount and ensures loseQueueRefund is not greater than queueFee
     * @param newQueueFee New queue fee amount
     */
    function setQueueFee(uint256 newQueueFee) external onlyOwner {
        queueFee = newQueueFee;

        if (loseQueueRefund > queueFee) {
            loseQueueRefund = queueFee;
        }
    }

    /**
     * @notice Updates the refund you get back if you lose the queue
     * @param newLoseQueueRefund New refund you get back if you lose the queue
     */
    function setNewLoseQueueRefund(uint256 newLoseQueueRefund)
        external
        onlyOwner
    {
        if (newLoseQueueRefund > queueFee) {
            revert LoseQueueRefundExceedsQueueFee();
        }
        loseQueueRefund = newLoseQueueRefund;
    }

    /**
     * @notice Updates the create fee amount
     * @param newCreateFee New create fee amount
     */
    function setCreateFee(uint256 newCreateFee) external onlyOwner {
        createFee = newCreateFee;
    }

    /**
     * @notice Updates the signer address
     * @param newSigner Address of the new signer
     */
    function setSigner(address newSigner) external onlyOwner {
        signerAddress = newSigner;
    }

    /**
     * @notice Updates the refundable override status for a token ID
     * @param tokenId Token ID to update
     * @param refundable New refundable status
     */
    function setRefundableOverride(uint256 tokenId, bool refundable)
        external
        onlyOwner
    {
        isRefundableOverride.setTo(tokenId, refundable);
    }

    /**
     * @notice Creates a new drop
     * @param nonReserved Maximum number of tokens available for public minting, excluding reserved tokens.
     * @param price Price per token
     * @param _isOE Whether the drop is open edition
     * @param isStripe Whether the payment is made via Stripe
     * @param signature Cryptographic signature for verification
     * @param nonce Nonce for transaction validation
     * @param startTimestamp Start timestamp of the sale
     * @param endTimestamp End timestamp of the sale
     * @param minMint Minimum number of tokens to mint
     * @param reserved Number of tokens reserved
     * @return tokenId ID of the newly created drop
     */
    function createDrop(
        uint256 nonReserved,
        uint256 price,
        bool _isOE,
        bool isStripe,
        bytes memory signature,
        uint256 nonce,
        uint256 startTimestamp,
        uint256 endTimestamp,
        uint256 minMint,
        uint256 reserved
    ) external checkNonce(msg.sender, nonce) returns (uint256) {
        if (startTimestamp == 0) startTimestamp = block.timestamp;

        if (endTimestamp != 0 && endTimestamp <= startTimestamp)
            revert SaleEnded();

        bytes32 hash = ECDSA.toEthSignedMessageHash(
            keccak256(
                abi.encode(
                    msg.sender,
                    nonReserved,
                    price,
                    _isOE,
                    isStripe,
                    nonce,
                    startTimestamp,
                    endTimestamp,
                    minMint,
                    reserved
                )
            )
        );
        if (!_verify(hash, signature)) revert InvalidSignature();

        if (
            !isStripe &&
            !USDC.transferFrom(msg.sender, _feeRecipient, createFee)
        ) revert PaymentFailed();

        return
            _createDrop(
                msg.sender,
                nonReserved,
                price,
                _isOE,
                startTimestamp,
                endTimestamp,
                minMint,
                reserved
            );
    }

    /**
     * @notice Mints a token
     * @param tokenId ID of the token to mint
     * @param signature Cryptographic signature for verification
     * @param nonce Nonce for transaction validation
     * @param isStripe Whether the payment is made via Stripe
     * @param tax Additional tax amount
     */
    function mintToken(
        uint256 tokenId,
        bytes memory signature,
        uint256 nonce,
        bool isStripe,
        uint256 tax
    ) external checkNonce(msg.sender, nonce) {
        TokenData storage data = tokenData[tokenId];

        if (data.endTimestamp != 0 && block.timestamp > data.endTimestamp)
            revert SaleEnded();

        bytes32 hash = ECDSA.toEthSignedMessageHash(
            keccak256(abi.encode(msg.sender, tokenId, nonce, isStripe, tax))
        );
        if (!_verify(hash, signature)) revert InvalidSignature();

        if (!isStripe) {
            uint256 totalFee = fee + tax;
            if (!USDC.transferFrom(msg.sender, address(this), data.price))
                revert PaymentFailed();
            if (!USDC.transferFrom(msg.sender, _feeRecipient, totalFee))
                revert PaymentFailed();
        }

        _mintToken(msg.sender, tokenId, data, false);
    }

    /**
     * @notice Allows the creator or contract owner to mint tokens for a recipient before sale starts.
     * @dev Nonce is checked for replay protection. Payments handled based on the `isStripe` flag.
     * @param tokenId ID of the token to mint.
     * @param signature Signature for verifying the transaction.
     * @param recipient Address of the recipient to receive minted tokens.
     * @param nonce Unique transaction nonce.
     * @param isStripe Flag indicating whether the payment was made via Stripe.
     * @param tax Additional tax amount.
     */
    function mintTokenByCreator(
        uint256 tokenId,
        bytes memory signature,
        address recipient,
        uint256 nonce,
        bool isStripe,
        uint256 tax
    ) external checkNonce(msg.sender, nonce) {
        bytes32 hash = ECDSA.toEthSignedMessageHash(
            keccak256(abi.encode(msg.sender, tokenId, nonce, isStripe, tax))
        );

        if (!_verify(hash, signature)) revert InvalidSignature();

        TokenData storage data = tokenData[tokenId];
        if (msg.sender != data.creator && msg.sender != owner())
            revert SaleNotStarted();

        if (data.endTimestamp != 0 && block.timestamp > data.endTimestamp) {
            revert SaleEnded();
        }

        if (!isStripe) {
            uint256 totalFee = fee + tax;
            if (!USDC.transferFrom(recipient, address(this), data.price))
                revert PaymentFailed();
            if (!USDC.transferFrom(recipient, _feeRecipient, totalFee))
                revert PaymentFailed();
        }

        _mintToken(recipient, tokenId, data, false);
    }

    /**
     * @notice Redeems multiple tokens in a batch.
     * @dev Uses nonces for replay protection and checks the provided signature.
     * @param tokenIds Array of token IDs to redeem.
     * @param nonce Unique transaction nonce.
     * @param fees Array of additional fees for each token.
     * @param signature Signature for verifying the transaction.
     */
    function batchRedeem(
        uint256[] memory tokenIds,
        uint256 nonce,
        uint256[] memory fees,
        bytes memory signature
    ) external checkNonce(msg.sender, nonce) {
        bytes32 hash = ECDSA.toEthSignedMessageHash(
            keccak256(abi.encode(msg.sender, tokenIds, nonce, fees))
        );

        if (!_verify(hash, signature)) revert InvalidSignature();

        for (uint256 i = 0; i < tokenIds.length; i++) {
            if (fees[i] > 0) {
                if (!USDC.transferFrom(msg.sender, _feeRecipient, fees[i]))
                    revert PaymentFailed();
            }

            totalRedeemed[tokenIds[i]] += 1;

            _burn(msg.sender, tokenIds[i], 1);
            emit TokenRedeemed(tokenIds[i], msg.sender);
        }
    }

    /**
     * @notice Refunds tokens to the sender.
     * @dev Requires valid signature and verifies refund eligibility.
     * @param tokenId ID of the token to refund.
     * @param amount Number of tokens to refund.
     * @param nonce Unique transaction nonce.
     * @param signature Signature for verifying the transaction.
     */
    function refundToken(
        uint256 tokenId,
        uint256 amount,
        uint256 nonce,
        bytes memory signature
    ) external checkNonce(msg.sender, nonce) {
        bytes32 hash = ECDSA.toEthSignedMessageHash(
            keccak256(abi.encode(msg.sender, tokenId, amount, nonce))
        );

        if (!_verify(hash, signature)) revert InvalidSignature();

        TokenData storage data = tokenData[tokenId];

        if (!isRefundableOverride.get(tokenId)) {
            if (
                block.timestamp > data.endTimestamp &&
                totalMinted[tokenId] <= data.minMint
            ) {
                revert TokenNotRefundable();
            }
        }

        uint256 totalRefund;

        unchecked {
            totalRefund = data.price * amount;
        }

        if (totalRefund == 0) revert RefundTransferFailed();

        unchecked {
            totalRefunded[tokenId] += amount;
        }

        _burn(msg.sender, tokenId, amount);

        if (!USDC.transfer(msg.sender, totalRefund))
            revert RefundTransferFailed();

        emit TokenRefunded(tokenId, msg.sender, amount, totalRefund);
    }

    /**
     * @notice Allows a user to join a token's queue.
     * @dev Requires that the queue exists and the user is not already in it.
     * @param tokenId ID of the token queue to join.
     */
    function joinQueue(uint256 tokenId) external {
        TokenData storage data = tokenData[tokenId];

        if (data.reserved == 0) revert QueueEmpty();
        if (block.timestamp > data.startTimestamp) revert QueuePeriodEnded();
        if (enteredQueue[tokenId][msg.sender]) revert AlreadyInQueue();

        uint256 totalAmount = data.price + queueFee;

        enteredQueue[tokenId][msg.sender] = true;
        queue[tokenId].entries++;

        if (!USDC.transferFrom(msg.sender, address(this), totalAmount))
            revert PaymentFailed();

        emit QueueJoined(tokenId, msg.sender, totalAmount);
    }

    /**
     * @notice Allows a user to leave a token's queue.
     * @dev Refunds the user and removes them from the queue.
     * @param tokenId ID of the token queue to leave.
     */
    function leaveQueue(uint256 tokenId) external {
        if (!enteredQueue[tokenId][msg.sender]) revert NotInQueue();
        if (queue[tokenId].blockCommit != 0) revert QueueAlreadyCommitted();

        uint256 amount = queue[tokenId].cost + queue[tokenId].queueFee;
        enteredQueue[tokenId][msg.sender] = false;
        queue[tokenId].entries--;

        if (!USDC.transfer(msg.sender, amount)) revert RefundTransferFailed();
        emit QueueLeft(tokenId, msg.sender, amount);
    }

    /**
     * @notice Commits the queue for processing.
     * @dev Ensures the queue is ready for RNG calculation.
     * @param tokenId ID of the token queue to commit.
     */
    function commitQueue(uint256 tokenId) external {
        TokenData storage data = tokenData[tokenId];
        Queue storage queueData = queue[tokenId];

        if (block.timestamp < data.startTimestamp) revert QueueStillOpen();
        if (queueData.reserved == 0) revert QueueEmpty();

        if (block.number > queueData.blockCommit + 256 && queueData.rng == 0) {
            queueData.blockCommit = block.number + 5;
            return;
        }

        if (queueData.blockCommit != 0) revert QueueAlreadyProcessed();

        queueData.blockCommit = block.number + 5;
    }

    /**
     * @notice Reveals the RNG for a queue after the block is committed.
     * @dev Uses the blockhash to determine the RNG.
     * @param tokenId ID of the token queue to reveal.
     */
    function revealQueue(uint256 tokenId) external {
        Queue storage queueData = queue[tokenId];
        if (queueData.rng != 0) revert QueueAlreadyRevealed();
        if (block.number < queueData.blockCommit) revert BlockhashNotReady();

        bytes32 blockHash = blockhash(queueData.blockCommit);

        if (blockHash == 0) revert BlockhashNotFound();
        if (block.number >= queueData.blockCommit + 256)
            revert BlockhashExpired();

        queueData.rng = uint256(blockHash);
    }

    /**
     * @notice Claims a token from the queue if the user is a winner.
     * @dev Refunds the user if they are not a winner.
     * @param tokenId ID of the token to claim.
     */
    function claimFromQueue(uint256 tokenId) external {
        if (!enteredQueue[tokenId][msg.sender]) revert NotInQueue();

        bool isWinner = checkQueueResult(tokenId, msg.sender);
        enteredQueue[tokenId][msg.sender] = false;

        if (!isWinner) {
            if (
                !USDC.transfer(
                    msg.sender,
                    queue[tokenId].cost + queue[tokenId].loseQueueRefund
                )
            ) revert RefundTransferFailed();
            return;
        }

        TokenData storage data = tokenData[tokenId];
        _mintToken(msg.sender, tokenId, data, true);
    }

    /**
     * @notice Blacklists or removes a blacklist for a specific marketplace.
     * @param marketplace Address of the marketplace.
     * @param isBlacklisted Boolean indicating whether the marketplace is blacklisted.
     */
    function blacklistMarketplace(address marketplace, bool isBlacklisted)
        public
        onlyOwner
    {
        blacklistedMarketplaces[marketplace] = isBlacklisted;
    }

    /**
     * @notice Enables or disables minting for a specific token.
     * @param tokenId ID of the token to enable/disable.
     * @param disabled Boolean indicating whether minting is disabled.
     */
    function disableToken(uint256 tokenId, bool disabled) public onlyOwner {
        tokenDisabled[tokenId] = disabled;
    }

    /**
     * @notice Transfers a token from one address to another.
     * @dev Validates that the caller is either the owner or a non-blacklisted marketplace.
     * @param from Address of the sender.
     * @param to Address of the recipient.
     * @param id ID of the token to transfer.
     * @param amount Amount of tokens to transfer.
     * @param data Additional data for the transfer.
     */
    function safeTransferFrom(
        address from,
        address to,
        uint256 id,
        uint256 amount,
        bytes memory data
    ) public override {
        if (msg.sender != from && blacklistedMarketplaces[msg.sender])
            revert OnlyTokenOwnerOrMarketplaceCanTransfer();

        super.safeTransferFrom(from, to, id, amount, data);
    }

    /**
     * @notice Transfers multiple tokens in a batch from one address to another.
     * @dev Validates that the caller is either the owner or a non-blacklisted marketplace.
     * @param from Address of the sender.
     * @param to Address of the recipient.
     * @param ids Array of token IDs to transfer.
     * @param amounts Array of token amounts to transfer.
     * @param data Additional data for the transfer.
     */
    function safeBatchTransferFrom(
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) public override {
        if (msg.sender != from && blacklistedMarketplaces[msg.sender])
            revert PaymentFailed();

        super.safeBatchTransferFrom(from, to, ids, amounts, data);
    }

    /**
     * @notice Withdraws a specified amount of USDC from the contract.
     * @param amount Amount of USDC to withdraw.
     */
    function withdraw(uint256 amount) public onlyOwner {
        if (amount == 0) revert PaymentFailed();
        USDC.transfer(msg.sender, amount);
    }

    /**
     * @notice Withdraws the full USDC balance from the contract.
     */
    function fullWithdraw() public onlyOwner {
        USDC.transfer(msg.sender, USDC.balanceOf(address(this)));
    }

    /**
     * @notice Checks whether a user is a winner in a token's queue.
     * @dev The result of this function is dynamic and can change based on the following factors:
     * - The state of the `rng` (random number generator) for the queue.
     * - The number of `claimed` entries in the queue, which can increase over time.
     * Users should claim their tokens promptly if they are determined to be winners, as the result of this function
     * is not guaranteed to remain consistent.
     * @param tokenId ID of the token queue to check.
     * @param user Address of the user to check.
     * @return Boolean indicating whether the user is a winner.
     */
    function checkQueueResult(uint256 tokenId, address user)
        public
        view
        returns (bool)
    {
        Queue memory queueData = queue[tokenId];

        if (!enteredQueue[tokenId][user]) {
            return false;
        }

        uint256 rng = queueData.rng;
        uint256 entries = queueData.entries;
        uint256 reserved = queueData.reserved;

        if (rng == 0 || queueData.claimed >= queueData.reserved) {
            return false;
        }

        if (queueData.entries <= queueData.reserved) return true;

        uint256 rank = uint256(keccak256(abi.encode(rng, user)));

        return (rank % entries) < reserved;
    }

    /**
     * @notice Returns the URI for a specific token ID.
     * @param tokenId ID of the token to retrieve the URI for.
     * @return The URI of the token.
     */
    function uri(uint256 tokenId) public view override returns (string memory) {
        return
            string(abi.encodePacked(baseURI, "/", LibString.toString(tokenId)));
    }

    /**
     * @notice Checks if a given interface is supported.
     * @param interfaceId ID of the interface to check.
     * @return Boolean indicating whether the interface is supported.
     */
    function supportsInterface(bytes4 interfaceId)
        public
        view
        virtual
        override(ERC1155C, ERC2981)
        returns (bool)
    {
        return super.supportsInterface(interfaceId);
    }

    /**
     * @notice Internal function to create a new drop
     * @param creator Address of the creator
     * @param nonReserved Maximum number of tokens available for public minting, excluding reserved tokens.
     * @param price Price per token
     * @param _isOE Whether the drop is open edition
     * @param startTimestamp Start timestamp of the sale
     * @param endTimestamp End timestamp of the sale
     * @param minMint Minimum number of tokens to mint
     * @param reserved Number of tokens reserved
     * @return tokenId ID of the newly created drop
     */
    function _createDrop(
        address creator,
        uint256 nonReserved,
        uint256 price,
        bool _isOE,
        uint256 startTimestamp,
        uint256 endTimestamp,
        uint256 minMint,
        uint256 reserved
    ) internal returns (uint256) {
        unchecked {
            currentTokenId++;
        }

        tokenData[currentTokenId] = TokenData(
            nonReserved,
            price,
            startTimestamp,
            endTimestamp,
            minMint,
            creator,
            _isOE,
            reserved,
            0
        );

        emit DropCreated(currentTokenId, creator, price);

        if (reserved > 0) {
            queue[currentTokenId] = Queue(
                reserved,
                price,
                0,
                0,
                0,
                0,
                queueFee,
                loseQueueRefund
            );
        }

        return currentTokenId;
    }

    /**
     * @notice Internal function to mint a token to a user.
     * @dev Handles minting logic, including checks for open edition and maximum supply.
     * @param user Address of the user to mint the token to.
     * @param tokenId ID of the token to mint.
     * @param fromQueue bool to decide if the mint is coming from claiming or regular mint.
     * @param data Token data structure for the specified tokenId.
     */
    function _mintToken(
        address user,
        uint256 tokenId,
        TokenData storage data,
        bool fromQueue
    ) internal {
        if (tokenDisabled[tokenId]) revert TokenMintingDisabled();

        Queue storage queueData = queue[tokenId];

        uint256 availableSupply = 0;

        if (fromQueue) {
            availableSupply = queueData.reserved - queueData.claimed;
            queueData.claimed++;
        } else {
            uint256 realNonreserved = 0;

            if (queueData.entries < data.reserved) {
                realNonreserved = data.nonReserved + (data.reserved - queueData.entries);
            } else {
                realNonreserved = data.nonReserved;
            }
            
            availableSupply = data.isOE ? 0 : realNonreserved - data.purchased;
            data.purchased++;
        }

        if (!data.isOE && availableSupply <= 0) revert ExceedsMaxQuantity();

        totalMinted[tokenId] += 1;

        _mint(user, tokenId, 1, "");
        emit TokenMinted(tokenId, user, data.price, fee);
    }

    /**
     * @dev Internal function to enforce that the caller is the contract owner.
     */
    function _requireCallerIsContractOwner() internal view virtual override {
        if (msg.sender != owner()) revert SaleNotStarted();
    }

    /**
     * @notice Verifies the validity of a signature.
     * @dev Recovers the signer address and compares it with the stored signer address.
     * @param hash Hash of the data being signed.
     * @param signature Signature to verify.
     * @return Boolean indicating whether the signature is valid.
     */
    function _verify(bytes32 hash, bytes memory signature)
        internal
        view
        returns (bool)
    {
        address recovered = ECDSA.recover(hash, signature);
        return recovered == signerAddress;
    }

    /**
     * ---------------------------------------------
     *              TESTNET FUNCTIONS
     * ---------------------------------------------
     * @dev These functions are intended for use only
     *      on testnets and will be removed in production.
     * ---------------------------------------------
     */

    /**
     * @notice Testnet-only function to create a drop by the owner.
     * @dev This function will be removed before deployment to mainnet.
     * @param nonReserved Maximum number of tokens available for public minting, excluding reserved tokens.
     * @param price Price per token.
     * @param _isOE Indicates if the drop is open edition.
     * @param startTimestamp Start time of the sale.
     * @param endTimestamp End time of the sale.
     * @param minMint Minimum number of tokens to mint.
     * @param reserved Number of reserved tokens.
     * @return Token ID of the created drop.
     */
    function ownerCreateDrop(
        uint256 nonReserved,
        uint256 price,
        bool _isOE,
        uint256 startTimestamp,
        uint256 endTimestamp,
        uint256 minMint,
        uint256 reserved
    ) public onlyOwner returns (uint256) {
        return
            _createDrop(
                msg.sender,
                nonReserved,
                price,
                _isOE,
                startTimestamp,
                endTimestamp,
                minMint,
                reserved
            );
    }

    /**
     * @notice Testnet-only function to refund tokens by the owner.
     * @dev This function will be removed before deployment to mainnet.
     * @param tokenId ID of the token to refund.
     * @param recipient Address of the recipient receiving the refund.
     * @param amount Amount of tokens to refund.
     */
    function ownerRefund(
        uint256 tokenId,
        address recipient,
        uint256 amount
    ) public onlyOwner {
        if (balanceOf(recipient, tokenId) < amount)
            revert InsufficientTokensToRefund();

        TokenData memory data = tokenData[tokenId];
        uint256 refundAmount = data.price * amount;

        unchecked {
            totalRefunded[tokenId] += amount;
        }

        _burn(recipient, tokenId, amount);

        emit TokenRefunded(tokenId, recipient, amount, refundAmount);
    }

    /**
     * @notice Testnet-only function to mint tokens by the owner.
     * @dev This function will be removed before deployment to mainnet.
     * @param tokenId ID of the token to mint.
     * @param recipient Address of the recipient receiving the tokens.
     * @param amount Amount of tokens to mint.
     */
    function ownerMintToken(
        uint256 tokenId,
        address recipient,
        uint256 amount
    ) public onlyOwner {
        TokenData memory data = tokenData[tokenId];

        totalMinted[tokenId] += amount;
        _mint(recipient, tokenId, amount, "");

        emit TokenMinted(tokenId, recipient, data.price, fee);
    }

    /**
     * @notice Testnet-only function to redeem tokens by the owner.
     * @dev This function will be removed before deployment to mainnet.
     * @param tokenId ID of the token to redeem.
     * @param recipient Address of the recipient redeeming the tokens.
     * @param amount Amount of tokens to redeem.
     */
    function ownerRedeem(
        uint256 tokenId,
        address recipient,
        uint256 amount
    ) public onlyOwner {
        if (balanceOf(recipient, tokenId) < amount)
            revert InsufficientTokensToRedeem();
        totalRedeemed[tokenId] += amount;
        _burn(recipient, tokenId, amount);
        emit TokenRedeemed(tokenId, recipient);
    }
}

File 2 of 36 : console.sol
// SPDX-License-Identifier: MIT
pragma solidity >=0.4.22 <0.9.0;

library console {
    address constant CONSOLE_ADDRESS =
        0x000000000000000000636F6e736F6c652e6c6f67;

    function _sendLogPayloadImplementation(bytes memory payload) internal view {
        address consoleAddress = CONSOLE_ADDRESS;
        /// @solidity memory-safe-assembly
        assembly {
            pop(
                staticcall(
                    gas(),
                    consoleAddress,
                    add(payload, 32),
                    mload(payload),
                    0,
                    0
                )
            )
        }
    }

    function _castToPure(
      function(bytes memory) internal view fnIn
    ) internal pure returns (function(bytes memory) pure fnOut) {
        assembly {
            fnOut := fnIn
        }
    }

    function _sendLogPayload(bytes memory payload) internal pure {
        _castToPure(_sendLogPayloadImplementation)(payload);
    }

    function log() internal pure {
        _sendLogPayload(abi.encodeWithSignature("log()"));
    }

    function logInt(int256 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(int256)", p0));
    }

    function logUint(uint256 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256)", p0));
    }

    function logString(string memory p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string)", p0));
    }

    function logBool(bool p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool)", p0));
    }

    function logAddress(address p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address)", p0));
    }

    function logBytes(bytes memory p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes)", p0));
    }

    function logBytes1(bytes1 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes1)", p0));
    }

    function logBytes2(bytes2 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes2)", p0));
    }

    function logBytes3(bytes3 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes3)", p0));
    }

    function logBytes4(bytes4 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes4)", p0));
    }

    function logBytes5(bytes5 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes5)", p0));
    }

    function logBytes6(bytes6 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes6)", p0));
    }

    function logBytes7(bytes7 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes7)", p0));
    }

    function logBytes8(bytes8 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes8)", p0));
    }

    function logBytes9(bytes9 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes9)", p0));
    }

    function logBytes10(bytes10 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes10)", p0));
    }

    function logBytes11(bytes11 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes11)", p0));
    }

    function logBytes12(bytes12 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes12)", p0));
    }

    function logBytes13(bytes13 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes13)", p0));
    }

    function logBytes14(bytes14 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes14)", p0));
    }

    function logBytes15(bytes15 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes15)", p0));
    }

    function logBytes16(bytes16 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes16)", p0));
    }

    function logBytes17(bytes17 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes17)", p0));
    }

    function logBytes18(bytes18 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes18)", p0));
    }

    function logBytes19(bytes19 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes19)", p0));
    }

    function logBytes20(bytes20 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes20)", p0));
    }

    function logBytes21(bytes21 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes21)", p0));
    }

    function logBytes22(bytes22 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes22)", p0));
    }

    function logBytes23(bytes23 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes23)", p0));
    }

    function logBytes24(bytes24 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes24)", p0));
    }

    function logBytes25(bytes25 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes25)", p0));
    }

    function logBytes26(bytes26 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes26)", p0));
    }

    function logBytes27(bytes27 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes27)", p0));
    }

    function logBytes28(bytes28 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes28)", p0));
    }

    function logBytes29(bytes29 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes29)", p0));
    }

    function logBytes30(bytes30 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes30)", p0));
    }

    function logBytes31(bytes31 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes31)", p0));
    }

    function logBytes32(bytes32 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bytes32)", p0));
    }

    function log(uint256 p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256)", p0));
    }

    function log(string memory p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string)", p0));
    }

    function log(bool p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool)", p0));
    }

    function log(address p0) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address)", p0));
    }

    function log(uint256 p0, uint256 p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256)", p0, p1));
    }

    function log(uint256 p0, string memory p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string)", p0, p1));
    }

    function log(uint256 p0, bool p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool)", p0, p1));
    }

    function log(uint256 p0, address p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address)", p0, p1));
    }

    function log(string memory p0, uint256 p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256)", p0, p1));
    }

    function log(string memory p0, string memory p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string)", p0, p1));
    }

    function log(string memory p0, bool p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool)", p0, p1));
    }

    function log(string memory p0, address p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address)", p0, p1));
    }

    function log(bool p0, uint256 p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256)", p0, p1));
    }

    function log(bool p0, string memory p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string)", p0, p1));
    }

    function log(bool p0, bool p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool)", p0, p1));
    }

    function log(bool p0, address p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address)", p0, p1));
    }

    function log(address p0, uint256 p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256)", p0, p1));
    }

    function log(address p0, string memory p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string)", p0, p1));
    }

    function log(address p0, bool p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool)", p0, p1));
    }

    function log(address p0, address p1) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address)", p0, p1));
    }

    function log(uint256 p0, uint256 p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,uint256)", p0, p1, p2));
    }

    function log(uint256 p0, uint256 p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,string)", p0, p1, p2));
    }

    function log(uint256 p0, uint256 p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,bool)", p0, p1, p2));
    }

    function log(uint256 p0, uint256 p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,address)", p0, p1, p2));
    }

    function log(uint256 p0, string memory p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,uint256)", p0, p1, p2));
    }

    function log(uint256 p0, string memory p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,string)", p0, p1, p2));
    }

    function log(uint256 p0, string memory p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,bool)", p0, p1, p2));
    }

    function log(uint256 p0, string memory p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,address)", p0, p1, p2));
    }

    function log(uint256 p0, bool p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,uint256)", p0, p1, p2));
    }

    function log(uint256 p0, bool p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,string)", p0, p1, p2));
    }

    function log(uint256 p0, bool p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,bool)", p0, p1, p2));
    }

    function log(uint256 p0, bool p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,address)", p0, p1, p2));
    }

    function log(uint256 p0, address p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,uint256)", p0, p1, p2));
    }

    function log(uint256 p0, address p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,string)", p0, p1, p2));
    }

    function log(uint256 p0, address p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,bool)", p0, p1, p2));
    }

    function log(uint256 p0, address p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,address)", p0, p1, p2));
    }

    function log(string memory p0, uint256 p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,uint256)", p0, p1, p2));
    }

    function log(string memory p0, uint256 p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,string)", p0, p1, p2));
    }

    function log(string memory p0, uint256 p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,bool)", p0, p1, p2));
    }

    function log(string memory p0, uint256 p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,address)", p0, p1, p2));
    }

    function log(string memory p0, string memory p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,uint256)", p0, p1, p2));
    }

    function log(string memory p0, string memory p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,string)", p0, p1, p2));
    }

    function log(string memory p0, string memory p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,bool)", p0, p1, p2));
    }

    function log(string memory p0, string memory p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,address)", p0, p1, p2));
    }

    function log(string memory p0, bool p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,uint256)", p0, p1, p2));
    }

    function log(string memory p0, bool p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,string)", p0, p1, p2));
    }

    function log(string memory p0, bool p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,bool)", p0, p1, p2));
    }

    function log(string memory p0, bool p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,address)", p0, p1, p2));
    }

    function log(string memory p0, address p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,uint256)", p0, p1, p2));
    }

    function log(string memory p0, address p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,string)", p0, p1, p2));
    }

    function log(string memory p0, address p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,bool)", p0, p1, p2));
    }

    function log(string memory p0, address p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,address)", p0, p1, p2));
    }

    function log(bool p0, uint256 p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,uint256)", p0, p1, p2));
    }

    function log(bool p0, uint256 p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,string)", p0, p1, p2));
    }

    function log(bool p0, uint256 p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,bool)", p0, p1, p2));
    }

    function log(bool p0, uint256 p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,address)", p0, p1, p2));
    }

    function log(bool p0, string memory p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,uint256)", p0, p1, p2));
    }

    function log(bool p0, string memory p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,string)", p0, p1, p2));
    }

    function log(bool p0, string memory p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,bool)", p0, p1, p2));
    }

    function log(bool p0, string memory p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,address)", p0, p1, p2));
    }

    function log(bool p0, bool p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,uint256)", p0, p1, p2));
    }

    function log(bool p0, bool p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,string)", p0, p1, p2));
    }

    function log(bool p0, bool p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,bool)", p0, p1, p2));
    }

    function log(bool p0, bool p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,address)", p0, p1, p2));
    }

    function log(bool p0, address p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,uint256)", p0, p1, p2));
    }

    function log(bool p0, address p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,string)", p0, p1, p2));
    }

    function log(bool p0, address p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,bool)", p0, p1, p2));
    }

    function log(bool p0, address p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,address)", p0, p1, p2));
    }

    function log(address p0, uint256 p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,uint256)", p0, p1, p2));
    }

    function log(address p0, uint256 p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,string)", p0, p1, p2));
    }

    function log(address p0, uint256 p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,bool)", p0, p1, p2));
    }

    function log(address p0, uint256 p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,address)", p0, p1, p2));
    }

    function log(address p0, string memory p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,uint256)", p0, p1, p2));
    }

    function log(address p0, string memory p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,string)", p0, p1, p2));
    }

    function log(address p0, string memory p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,bool)", p0, p1, p2));
    }

    function log(address p0, string memory p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,address)", p0, p1, p2));
    }

    function log(address p0, bool p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,uint256)", p0, p1, p2));
    }

    function log(address p0, bool p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,string)", p0, p1, p2));
    }

    function log(address p0, bool p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,bool)", p0, p1, p2));
    }

    function log(address p0, bool p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,address)", p0, p1, p2));
    }

    function log(address p0, address p1, uint256 p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,uint256)", p0, p1, p2));
    }

    function log(address p0, address p1, string memory p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,string)", p0, p1, p2));
    }

    function log(address p0, address p1, bool p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,bool)", p0, p1, p2));
    }

    function log(address p0, address p1, address p2) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,address)", p0, p1, p2));
    }

    function log(uint256 p0, uint256 p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,uint256,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,uint256,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,uint256,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,string,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,string,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,string,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,string,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,bool,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,bool,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,bool,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,bool,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,address,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,address,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,address,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, uint256 p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,uint256,address,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,uint256,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,uint256,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,uint256,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,string,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,string,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,string,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,string,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,bool,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,bool,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,bool,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,bool,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,address,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,address,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,address,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, string memory p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,string,address,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,uint256,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,uint256,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,uint256,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,string,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,string,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,string,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,string,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,bool,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,bool,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,bool,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,bool,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,address,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,address,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,address,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, bool p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,bool,address,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,uint256,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,uint256,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,uint256,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,string,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,string,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,string,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,string,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,bool,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,bool,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,bool,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,bool,address)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,address,uint256)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,address,string)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,address,bool)", p0, p1, p2, p3));
    }

    function log(uint256 p0, address p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(uint256,address,address,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,uint256,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,uint256,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,uint256,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,string,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,string,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,string,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,string,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,bool,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,bool,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,bool,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,bool,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,address,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,address,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,address,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, uint256 p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,uint256,address,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,uint256,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,uint256,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,uint256,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,string,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,string,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,string,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,string,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,bool,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,bool,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,bool,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,bool,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,address,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,address,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,address,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, string memory p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,string,address,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,uint256,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,uint256,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,uint256,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,string,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,string,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,string,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,string,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,bool,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,bool,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,bool,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,bool,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,address,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,address,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,address,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, bool p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,bool,address,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,uint256,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,uint256,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,uint256,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,string,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,string,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,string,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,string,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,bool,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,bool,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,bool,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,bool,address)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,address,uint256)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,address,string)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,address,bool)", p0, p1, p2, p3));
    }

    function log(string memory p0, address p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(string,address,address,address)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,uint256,string)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,uint256,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,uint256,address)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,string,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,string,string)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,string,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,string,address)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,bool,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,bool,string)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,bool,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,bool,address)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,address,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,address,string)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,address,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, uint256 p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,uint256,address,address)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,uint256,string)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,uint256,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,uint256,address)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,string,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,string,string)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,string,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,string,address)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,bool,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,bool,string)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,bool,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,bool,address)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,address,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,address,string)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,address,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, string memory p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,string,address,address)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,uint256,string)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,uint256,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,uint256,address)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,string,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,string,string)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,string,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,string,address)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,bool,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,bool,string)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,bool,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,bool,address)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,address,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,address,string)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,address,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, bool p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,bool,address,address)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,uint256,string)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,uint256,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,uint256,address)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,string,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,string,string)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,string,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,string,address)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,bool,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,bool,string)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,bool,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,bool,address)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,address,uint256)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,address,string)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,address,bool)", p0, p1, p2, p3));
    }

    function log(bool p0, address p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(bool,address,address,address)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,uint256,string)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,uint256,bool)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,uint256,address)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,string,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,string,string)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,string,bool)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,string,address)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,bool,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,bool,string)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,bool,bool)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,bool,address)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,address,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,address,string)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,address,bool)", p0, p1, p2, p3));
    }

    function log(address p0, uint256 p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,uint256,address,address)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,uint256,string)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,uint256,bool)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,uint256,address)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,string,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,string,string)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,string,bool)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,string,address)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,bool,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,bool,string)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,bool,bool)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,bool,address)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,address,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,address,string)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,address,bool)", p0, p1, p2, p3));
    }

    function log(address p0, string memory p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,string,address,address)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,uint256,string)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,uint256,bool)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,uint256,address)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,string,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,string,string)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,string,bool)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,string,address)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,bool,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,bool,string)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,bool,bool)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,bool,address)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,address,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,address,string)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,address,bool)", p0, p1, p2, p3));
    }

    function log(address p0, bool p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,bool,address,address)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, uint256 p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,uint256,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, uint256 p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,uint256,string)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, uint256 p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,uint256,bool)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, uint256 p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,uint256,address)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, string memory p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,string,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, string memory p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,string,string)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, string memory p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,string,bool)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, string memory p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,string,address)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, bool p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,bool,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, bool p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,bool,string)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, bool p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,bool,bool)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, bool p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,bool,address)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, address p2, uint256 p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,address,uint256)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, address p2, string memory p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,address,string)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, address p2, bool p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,address,bool)", p0, p1, p2, p3));
    }

    function log(address p0, address p1, address p2, address p3) internal pure {
        _sendLogPayload(abi.encodeWithSignature("log(address,address,address,address)", p0, p1, p2, p3));
    }
}

File 3 of 36 : LibBitmap.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import {LibBit} from "./LibBit.sol";

/// @notice Library for storage of packed unsigned booleans.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/LibBitmap.sol)
/// @author Modified from Solmate (https://github.com/transmissions11/solmate/blob/main/src/utils/LibBitmap.sol)
/// @author Modified from Solidity-Bits (https://github.com/estarriolvetch/solidity-bits/blob/main/contracts/BitMaps.sol)
library LibBitmap {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         CONSTANTS                          */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The constant returned when a bitmap scan does not find a result.
    uint256 internal constant NOT_FOUND = type(uint256).max;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                          STRUCTS                           */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev A bitmap in storage.
    struct Bitmap {
        mapping(uint256 => uint256) map;
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         OPERATIONS                         */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns the boolean value of the bit at `index` in `bitmap`.
    function get(Bitmap storage bitmap, uint256 index) internal view returns (bool isSet) {
        // It is better to set `isSet` to either 0 or 1, than zero vs non-zero.
        // Both cost the same amount of gas, but the former allows the returned value
        // to be reused without cleaning the upper bits.
        uint256 b = (bitmap.map[index >> 8] >> (index & 0xff)) & 1;
        /// @solidity memory-safe-assembly
        assembly {
            isSet := b
        }
    }

    /// @dev Updates the bit at `index` in `bitmap` to true.
    function set(Bitmap storage bitmap, uint256 index) internal {
        bitmap.map[index >> 8] |= (1 << (index & 0xff));
    }

    /// @dev Updates the bit at `index` in `bitmap` to false.
    function unset(Bitmap storage bitmap, uint256 index) internal {
        bitmap.map[index >> 8] &= ~(1 << (index & 0xff));
    }

    /// @dev Flips the bit at `index` in `bitmap`.
    /// Returns the boolean result of the flipped bit.
    function toggle(Bitmap storage bitmap, uint256 index) internal returns (bool newIsSet) {
        /// @solidity memory-safe-assembly
        assembly {
            mstore(0x20, bitmap.slot)
            mstore(0x00, shr(8, index))
            let storageSlot := keccak256(0x00, 0x40)
            let shift := and(index, 0xff)
            let storageValue := xor(sload(storageSlot), shl(shift, 1))
            // It makes sense to return the `newIsSet`,
            // as it allow us to skip an additional warm `sload`,
            // and it costs minimal gas (about 15),
            // which may be optimized away if the returned value is unused.
            newIsSet := and(1, shr(shift, storageValue))
            sstore(storageSlot, storageValue)
        }
    }

    /// @dev Updates the bit at `index` in `bitmap` to `shouldSet`.
    function setTo(Bitmap storage bitmap, uint256 index, bool shouldSet) internal {
        /// @solidity memory-safe-assembly
        assembly {
            mstore(0x20, bitmap.slot)
            mstore(0x00, shr(8, index))
            let storageSlot := keccak256(0x00, 0x40)
            let storageValue := sload(storageSlot)
            let shift := and(index, 0xff)
            sstore(
                storageSlot,
                // Unsets the bit at `shift` via `and`, then sets its new value via `or`.
                or(and(storageValue, not(shl(shift, 1))), shl(shift, iszero(iszero(shouldSet))))
            )
        }
    }

    /// @dev Consecutively sets `amount` of bits starting from the bit at `start`.
    function setBatch(Bitmap storage bitmap, uint256 start, uint256 amount) internal {
        /// @solidity memory-safe-assembly
        assembly {
            let max := not(0)
            let shift := and(start, 0xff)
            mstore(0x20, bitmap.slot)
            mstore(0x00, shr(8, start))
            if iszero(lt(add(shift, amount), 257)) {
                let storageSlot := keccak256(0x00, 0x40)
                sstore(storageSlot, or(sload(storageSlot), shl(shift, max)))
                let bucket := add(mload(0x00), 1)
                let bucketEnd := add(mload(0x00), shr(8, add(amount, shift)))
                amount := and(add(amount, shift), 0xff)
                shift := 0
                for {} iszero(eq(bucket, bucketEnd)) { bucket := add(bucket, 1) } {
                    mstore(0x00, bucket)
                    sstore(keccak256(0x00, 0x40), max)
                }
                mstore(0x00, bucket)
            }
            let storageSlot := keccak256(0x00, 0x40)
            sstore(storageSlot, or(sload(storageSlot), shl(shift, shr(sub(256, amount), max))))
        }
    }

    /// @dev Consecutively unsets `amount` of bits starting from the bit at `start`.
    function unsetBatch(Bitmap storage bitmap, uint256 start, uint256 amount) internal {
        /// @solidity memory-safe-assembly
        assembly {
            let shift := and(start, 0xff)
            mstore(0x20, bitmap.slot)
            mstore(0x00, shr(8, start))
            if iszero(lt(add(shift, amount), 257)) {
                let storageSlot := keccak256(0x00, 0x40)
                sstore(storageSlot, and(sload(storageSlot), not(shl(shift, not(0)))))
                let bucket := add(mload(0x00), 1)
                let bucketEnd := add(mload(0x00), shr(8, add(amount, shift)))
                amount := and(add(amount, shift), 0xff)
                shift := 0
                for {} iszero(eq(bucket, bucketEnd)) { bucket := add(bucket, 1) } {
                    mstore(0x00, bucket)
                    sstore(keccak256(0x00, 0x40), 0)
                }
                mstore(0x00, bucket)
            }
            let storageSlot := keccak256(0x00, 0x40)
            sstore(
                storageSlot, and(sload(storageSlot), not(shl(shift, shr(sub(256, amount), not(0)))))
            )
        }
    }

    /// @dev Returns number of set bits within a range by
    /// scanning `amount` of bits starting from the bit at `start`.
    function popCount(Bitmap storage bitmap, uint256 start, uint256 amount)
        internal
        view
        returns (uint256 count)
    {
        unchecked {
            uint256 bucket = start >> 8;
            uint256 shift = start & 0xff;
            if (!(amount + shift < 257)) {
                count = LibBit.popCount(bitmap.map[bucket] >> shift);
                uint256 bucketEnd = bucket + ((amount + shift) >> 8);
                amount = (amount + shift) & 0xff;
                shift = 0;
                for (++bucket; bucket != bucketEnd; ++bucket) {
                    count += LibBit.popCount(bitmap.map[bucket]);
                }
            }
            count += LibBit.popCount((bitmap.map[bucket] >> shift) << (256 - amount));
        }
    }

    /// @dev Returns the index of the most significant set bit in `[0..upTo]`.
    /// If no set bit is found, returns `NOT_FOUND`.
    function findLastSet(Bitmap storage bitmap, uint256 upTo)
        internal
        view
        returns (uint256 setBitIndex)
    {
        setBitIndex = NOT_FOUND;
        uint256 bucket = upTo >> 8;
        uint256 bits;
        /// @solidity memory-safe-assembly
        assembly {
            mstore(0x00, bucket)
            mstore(0x20, bitmap.slot)
            let offset := and(0xff, not(upTo)) // `256 - (255 & upTo) - 1`.
            bits := shr(offset, shl(offset, sload(keccak256(0x00, 0x40))))
            if iszero(or(bits, iszero(bucket))) {
                for {} 1 {} {
                    bucket := add(bucket, setBitIndex) // `sub(bucket, 1)`.
                    mstore(0x00, bucket)
                    bits := sload(keccak256(0x00, 0x40))
                    if or(bits, iszero(bucket)) { break }
                }
            }
        }
        if (bits != 0) {
            setBitIndex = (bucket << 8) | LibBit.fls(bits);
            /// @solidity memory-safe-assembly
            assembly {
                setBitIndex := or(setBitIndex, sub(0, gt(setBitIndex, upTo)))
            }
        }
    }

    /// @dev Returns the index of the least significant unset bit in `[begin..upTo]`.
    /// If no unset bit is found, returns `NOT_FOUND`.
    function findFirstUnset(Bitmap storage bitmap, uint256 begin, uint256 upTo)
        internal
        view
        returns (uint256 unsetBitIndex)
    {
        unsetBitIndex = NOT_FOUND;
        uint256 bucket = begin >> 8;
        uint256 negBits;
        /// @solidity memory-safe-assembly
        assembly {
            mstore(0x00, bucket)
            mstore(0x20, bitmap.slot)
            let offset := and(0xff, begin)
            negBits := shl(offset, shr(offset, not(sload(keccak256(0x00, 0x40)))))
            if iszero(negBits) {
                let lastBucket := shr(8, upTo)
                for {} 1 {} {
                    bucket := add(bucket, 1)
                    mstore(0x00, bucket)
                    negBits := not(sload(keccak256(0x00, 0x40)))
                    if or(negBits, gt(bucket, lastBucket)) { break }
                }
                if gt(bucket, lastBucket) {
                    negBits := shl(and(0xff, not(upTo)), shr(and(0xff, not(upTo)), negBits))
                }
            }
        }
        if (negBits != 0) {
            uint256 r = (bucket << 8) | LibBit.ffs(negBits);
            /// @solidity memory-safe-assembly
            assembly {
                unsetBitIndex := or(r, sub(0, or(gt(r, upTo), lt(r, begin))))
            }
        }
    }
}

File 4 of 36 : LibString.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import {LibBytes} from "./LibBytes.sol";

/// @notice Library for converting numbers into strings and other string operations.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/LibString.sol)
/// @author Modified from Solmate (https://github.com/transmissions11/solmate/blob/main/src/utils/LibString.sol)
///
/// @dev Note:
/// For performance and bytecode compactness, most of the string operations are restricted to
/// byte strings (7-bit ASCII), except where otherwise specified.
/// Usage of byte string operations on charsets with runes spanning two or more bytes
/// can lead to undefined behavior.
library LibString {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                          STRUCTS                           */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Goated string storage struct that totally MOGs, no cap, fr.
    /// Uses less gas and bytecode than Solidity's native string storage. It's meta af.
    /// Packs length with the first 31 bytes if <255 bytes, so it’s mad tight.
    struct StringStorage {
        bytes32 _spacer;
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                        CUSTOM ERRORS                       */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The length of the output is too small to contain all the hex digits.
    error HexLengthInsufficient();

    /// @dev The length of the string is more than 32 bytes.
    error TooBigForSmallString();

    /// @dev The input string must be a 7-bit ASCII.
    error StringNot7BitASCII();

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         CONSTANTS                          */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The constant returned when the `search` is not found in the string.
    uint256 internal constant NOT_FOUND = type(uint256).max;

    /// @dev Lookup for '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'.
    uint128 internal constant ALPHANUMERIC_7_BIT_ASCII = 0x7fffffe07fffffe03ff000000000000;

    /// @dev Lookup for 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'.
    uint128 internal constant LETTERS_7_BIT_ASCII = 0x7fffffe07fffffe0000000000000000;

    /// @dev Lookup for 'abcdefghijklmnopqrstuvwxyz'.
    uint128 internal constant LOWERCASE_7_BIT_ASCII = 0x7fffffe000000000000000000000000;

    /// @dev Lookup for 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'.
    uint128 internal constant UPPERCASE_7_BIT_ASCII = 0x7fffffe0000000000000000;

    /// @dev Lookup for '0123456789'.
    uint128 internal constant DIGITS_7_BIT_ASCII = 0x3ff000000000000;

    /// @dev Lookup for '0123456789abcdefABCDEF'.
    uint128 internal constant HEXDIGITS_7_BIT_ASCII = 0x7e0000007e03ff000000000000;

    /// @dev Lookup for '01234567'.
    uint128 internal constant OCTDIGITS_7_BIT_ASCII = 0xff000000000000;

    /// @dev Lookup for '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!"#$%&\'()*+,-./:;<=>?@[\\]^_`{|}~ \t\n\r\x0b\x0c'.
    uint128 internal constant PRINTABLE_7_BIT_ASCII = 0x7fffffffffffffffffffffff00003e00;

    /// @dev Lookup for '!"#$%&\'()*+,-./:;<=>?@[\\]^_`{|}~'.
    uint128 internal constant PUNCTUATION_7_BIT_ASCII = 0x78000001f8000001fc00fffe00000000;

    /// @dev Lookup for ' \t\n\r\x0b\x0c'.
    uint128 internal constant WHITESPACE_7_BIT_ASCII = 0x100003e00;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                 STRING STORAGE OPERATIONS                  */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Sets the value of the string storage `$` to `s`.
    function set(StringStorage storage $, string memory s) internal {
        LibBytes.set(bytesStorage($), bytes(s));
    }

    /// @dev Sets the value of the string storage `$` to `s`.
    function setCalldata(StringStorage storage $, string calldata s) internal {
        LibBytes.setCalldata(bytesStorage($), bytes(s));
    }

    /// @dev Sets the value of the string storage `$` to the empty string.
    function clear(StringStorage storage $) internal {
        delete $._spacer;
    }

    /// @dev Returns whether the value stored is `$` is the empty string "".
    function isEmpty(StringStorage storage $) internal view returns (bool) {
        return uint256($._spacer) & 0xff == uint256(0);
    }

    /// @dev Returns the length of the value stored in `$`.
    function length(StringStorage storage $) internal view returns (uint256) {
        return LibBytes.length(bytesStorage($));
    }

    /// @dev Returns the value stored in `$`.
    function get(StringStorage storage $) internal view returns (string memory) {
        return string(LibBytes.get(bytesStorage($)));
    }

    /// @dev Helper to cast `$` to a `BytesStorage`.
    function bytesStorage(StringStorage storage $)
        internal
        pure
        returns (LibBytes.BytesStorage storage casted)
    {
        /// @solidity memory-safe-assembly
        assembly {
            casted.slot := $.slot
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                     DECIMAL OPERATIONS                     */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns the base 10 decimal representation of `value`.
    function toString(uint256 value) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            // The maximum value of a uint256 contains 78 digits (1 byte per digit), but
            // we allocate 0xa0 bytes to keep the free memory pointer 32-byte word aligned.
            // We will need 1 word for the trailing zeros padding, 1 word for the length,
            // and 3 words for a maximum of 78 digits.
            result := add(mload(0x40), 0x80)
            mstore(0x40, add(result, 0x20)) // Allocate memory.
            mstore(result, 0) // Zeroize the slot after the string.

            let end := result // Cache the end of the memory to calculate the length later.
            let w := not(0) // Tsk.
            // We write the string from rightmost digit to leftmost digit.
            // The following is essentially a do-while loop that also handles the zero case.
            for { let temp := value } 1 {} {
                result := add(result, w) // `sub(result, 1)`.
                // Store the character to the pointer.
                // The ASCII index of the '0' character is 48.
                mstore8(result, add(48, mod(temp, 10)))
                temp := div(temp, 10) // Keep dividing `temp` until zero.
                if iszero(temp) { break }
            }
            let n := sub(end, result)
            result := sub(result, 0x20) // Move the pointer 32 bytes back to make room for the length.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the base 10 decimal representation of `value`.
    function toString(int256 value) internal pure returns (string memory result) {
        if (value >= 0) return toString(uint256(value));
        unchecked {
            result = toString(~uint256(value) + 1);
        }
        /// @solidity memory-safe-assembly
        assembly {
            // We still have some spare memory space on the left,
            // as we have allocated 3 words (96 bytes) for up to 78 digits.
            let n := mload(result) // Load the string length.
            mstore(result, 0x2d) // Store the '-' character.
            result := sub(result, 1) // Move back the string pointer by a byte.
            mstore(result, add(n, 1)) // Update the string length.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   HEXADECIMAL OPERATIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns the hexadecimal representation of `value`,
    /// left-padded to an input length of `byteCount` bytes.
    /// The output is prefixed with "0x" encoded using 2 hexadecimal digits per byte,
    /// giving a total length of `byteCount * 2 + 2` bytes.
    /// Reverts if `byteCount` is too small for the output to contain all the digits.
    function toHexString(uint256 value, uint256 byteCount)
        internal
        pure
        returns (string memory result)
    {
        result = toHexStringNoPrefix(value, byteCount);
        /// @solidity memory-safe-assembly
        assembly {
            let n := add(mload(result), 2) // Compute the length.
            mstore(result, 0x3078) // Store the "0x" prefix.
            result := sub(result, 2) // Move the pointer.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`,
    /// left-padded to an input length of `byteCount` bytes.
    /// The output is not prefixed with "0x" and is encoded using 2 hexadecimal digits per byte,
    /// giving a total length of `byteCount * 2` bytes.
    /// Reverts if `byteCount` is too small for the output to contain all the digits.
    function toHexStringNoPrefix(uint256 value, uint256 byteCount)
        internal
        pure
        returns (string memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            // We need 0x20 bytes for the trailing zeros padding, `byteCount * 2` bytes
            // for the digits, 0x02 bytes for the prefix, and 0x20 bytes for the length.
            // We add 0x20 to the total and round down to a multiple of 0x20.
            // (0x20 + 0x20 + 0x02 + 0x20) = 0x62.
            result := add(mload(0x40), and(add(shl(1, byteCount), 0x42), not(0x1f)))
            mstore(0x40, add(result, 0x20)) // Allocate memory.
            mstore(result, 0) // Zeroize the slot after the string.

            let end := result // Cache the end to calculate the length later.
            // Store "0123456789abcdef" in scratch space.
            mstore(0x0f, 0x30313233343536373839616263646566)

            let start := sub(result, add(byteCount, byteCount))
            let w := not(1) // Tsk.
            let temp := value
            // We write the string from rightmost digit to leftmost digit.
            // The following is essentially a do-while loop that also handles the zero case.
            for {} 1 {} {
                result := add(result, w) // `sub(result, 2)`.
                mstore8(add(result, 1), mload(and(temp, 15)))
                mstore8(result, mload(and(shr(4, temp), 15)))
                temp := shr(8, temp)
                if iszero(xor(result, start)) { break }
            }
            if temp {
                mstore(0x00, 0x2194895a) // `HexLengthInsufficient()`.
                revert(0x1c, 0x04)
            }
            let n := sub(end, result)
            result := sub(result, 0x20)
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is prefixed with "0x" and encoded using 2 hexadecimal digits per byte.
    /// As address are 20 bytes long, the output will left-padded to have
    /// a length of `20 * 2 + 2` bytes.
    function toHexString(uint256 value) internal pure returns (string memory result) {
        result = toHexStringNoPrefix(value);
        /// @solidity memory-safe-assembly
        assembly {
            let n := add(mload(result), 2) // Compute the length.
            mstore(result, 0x3078) // Store the "0x" prefix.
            result := sub(result, 2) // Move the pointer.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is prefixed with "0x".
    /// The output excludes leading "0" from the `toHexString` output.
    /// `0x00: "0x0", 0x01: "0x1", 0x12: "0x12", 0x123: "0x123"`.
    function toMinimalHexString(uint256 value) internal pure returns (string memory result) {
        result = toHexStringNoPrefix(value);
        /// @solidity memory-safe-assembly
        assembly {
            let o := eq(byte(0, mload(add(result, 0x20))), 0x30) // Whether leading zero is present.
            let n := add(mload(result), 2) // Compute the length.
            mstore(add(result, o), 0x3078) // Store the "0x" prefix, accounting for leading zero.
            result := sub(add(result, o), 2) // Move the pointer, accounting for leading zero.
            mstore(result, sub(n, o)) // Store the length, accounting for leading zero.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output excludes leading "0" from the `toHexStringNoPrefix` output.
    /// `0x00: "0", 0x01: "1", 0x12: "12", 0x123: "123"`.
    function toMinimalHexStringNoPrefix(uint256 value)
        internal
        pure
        returns (string memory result)
    {
        result = toHexStringNoPrefix(value);
        /// @solidity memory-safe-assembly
        assembly {
            let o := eq(byte(0, mload(add(result, 0x20))), 0x30) // Whether leading zero is present.
            let n := mload(result) // Get the length.
            result := add(result, o) // Move the pointer, accounting for leading zero.
            mstore(result, sub(n, o)) // Store the length, accounting for leading zero.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is encoded using 2 hexadecimal digits per byte.
    /// As address are 20 bytes long, the output will left-padded to have
    /// a length of `20 * 2` bytes.
    function toHexStringNoPrefix(uint256 value) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            // We need 0x20 bytes for the trailing zeros padding, 0x20 bytes for the length,
            // 0x02 bytes for the prefix, and 0x40 bytes for the digits.
            // The next multiple of 0x20 above (0x20 + 0x20 + 0x02 + 0x40) is 0xa0.
            result := add(mload(0x40), 0x80)
            mstore(0x40, add(result, 0x20)) // Allocate memory.
            mstore(result, 0) // Zeroize the slot after the string.

            let end := result // Cache the end to calculate the length later.
            mstore(0x0f, 0x30313233343536373839616263646566) // Store the "0123456789abcdef" lookup.

            let w := not(1) // Tsk.
            // We write the string from rightmost digit to leftmost digit.
            // The following is essentially a do-while loop that also handles the zero case.
            for { let temp := value } 1 {} {
                result := add(result, w) // `sub(result, 2)`.
                mstore8(add(result, 1), mload(and(temp, 15)))
                mstore8(result, mload(and(shr(4, temp), 15)))
                temp := shr(8, temp)
                if iszero(temp) { break }
            }
            let n := sub(end, result)
            result := sub(result, 0x20)
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is prefixed with "0x", encoded using 2 hexadecimal digits per byte,
    /// and the alphabets are capitalized conditionally according to
    /// https://eips.ethereum.org/EIPS/eip-55
    function toHexStringChecksummed(address value) internal pure returns (string memory result) {
        result = toHexString(value);
        /// @solidity memory-safe-assembly
        assembly {
            let mask := shl(6, div(not(0), 255)) // `0b010000000100000000 ...`
            let o := add(result, 0x22)
            let hashed := and(keccak256(o, 40), mul(34, mask)) // `0b10001000 ... `
            let t := shl(240, 136) // `0b10001000 << 240`
            for { let i := 0 } 1 {} {
                mstore(add(i, i), mul(t, byte(i, hashed)))
                i := add(i, 1)
                if eq(i, 20) { break }
            }
            mstore(o, xor(mload(o), shr(1, and(mload(0x00), and(mload(o), mask)))))
            o := add(o, 0x20)
            mstore(o, xor(mload(o), shr(1, and(mload(0x20), and(mload(o), mask)))))
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is prefixed with "0x" and encoded using 2 hexadecimal digits per byte.
    function toHexString(address value) internal pure returns (string memory result) {
        result = toHexStringNoPrefix(value);
        /// @solidity memory-safe-assembly
        assembly {
            let n := add(mload(result), 2) // Compute the length.
            mstore(result, 0x3078) // Store the "0x" prefix.
            result := sub(result, 2) // Move the pointer.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hexadecimal representation of `value`.
    /// The output is encoded using 2 hexadecimal digits per byte.
    function toHexStringNoPrefix(address value) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            // Allocate memory.
            // We need 0x20 bytes for the trailing zeros padding, 0x20 bytes for the length,
            // 0x02 bytes for the prefix, and 0x28 bytes for the digits.
            // The next multiple of 0x20 above (0x20 + 0x20 + 0x02 + 0x28) is 0x80.
            mstore(0x40, add(result, 0x80))
            mstore(0x0f, 0x30313233343536373839616263646566) // Store the "0123456789abcdef" lookup.

            result := add(result, 2)
            mstore(result, 40) // Store the length.
            let o := add(result, 0x20)
            mstore(add(o, 40), 0) // Zeroize the slot after the string.
            value := shl(96, value)
            // We write the string from rightmost digit to leftmost digit.
            // The following is essentially a do-while loop that also handles the zero case.
            for { let i := 0 } 1 {} {
                let p := add(o, add(i, i))
                let temp := byte(i, value)
                mstore8(add(p, 1), mload(and(temp, 15)))
                mstore8(p, mload(shr(4, temp)))
                i := add(i, 1)
                if eq(i, 20) { break }
            }
        }
    }

    /// @dev Returns the hex encoded string from the raw bytes.
    /// The output is encoded using 2 hexadecimal digits per byte.
    function toHexString(bytes memory raw) internal pure returns (string memory result) {
        result = toHexStringNoPrefix(raw);
        /// @solidity memory-safe-assembly
        assembly {
            let n := add(mload(result), 2) // Compute the length.
            mstore(result, 0x3078) // Store the "0x" prefix.
            result := sub(result, 2) // Move the pointer.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the hex encoded string from the raw bytes.
    /// The output is encoded using 2 hexadecimal digits per byte.
    function toHexStringNoPrefix(bytes memory raw) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            let n := mload(raw)
            result := add(mload(0x40), 2) // Skip 2 bytes for the optional prefix.
            mstore(result, add(n, n)) // Store the length of the output.

            mstore(0x0f, 0x30313233343536373839616263646566) // Store the "0123456789abcdef" lookup.
            let o := add(result, 0x20)
            let end := add(raw, n)
            for {} iszero(eq(raw, end)) {} {
                raw := add(raw, 1)
                mstore8(add(o, 1), mload(and(mload(raw), 15)))
                mstore8(o, mload(and(shr(4, mload(raw)), 15)))
                o := add(o, 2)
            }
            mstore(o, 0) // Zeroize the slot after the string.
            mstore(0x40, add(o, 0x20)) // Allocate memory.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   RUNE STRING OPERATIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns the number of UTF characters in the string.
    function runeCount(string memory s) internal pure returns (uint256 result) {
        /// @solidity memory-safe-assembly
        assembly {
            if mload(s) {
                mstore(0x00, div(not(0), 255))
                mstore(0x20, 0x0202020202020202020202020202020202020202020202020303030304040506)
                let o := add(s, 0x20)
                let end := add(o, mload(s))
                for { result := 1 } 1 { result := add(result, 1) } {
                    o := add(o, byte(0, mload(shr(250, mload(o)))))
                    if iszero(lt(o, end)) { break }
                }
            }
        }
    }

    /// @dev Returns if this string is a 7-bit ASCII string.
    /// (i.e. all characters codes are in [0..127])
    function is7BitASCII(string memory s) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := 1
            let mask := shl(7, div(not(0), 255))
            let n := mload(s)
            if n {
                let o := add(s, 0x20)
                let end := add(o, n)
                let last := mload(end)
                mstore(end, 0)
                for {} 1 {} {
                    if and(mask, mload(o)) {
                        result := 0
                        break
                    }
                    o := add(o, 0x20)
                    if iszero(lt(o, end)) { break }
                }
                mstore(end, last)
            }
        }
    }

    /// @dev Returns if this string is a 7-bit ASCII string,
    /// AND all characters are in the `allowed` lookup.
    /// Note: If `s` is empty, returns true regardless of `allowed`.
    function is7BitASCII(string memory s, uint128 allowed) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := 1
            if mload(s) {
                let allowed_ := shr(128, shl(128, allowed))
                let o := add(s, 0x20)
                for { let end := add(o, mload(s)) } 1 {} {
                    result := and(result, shr(byte(0, mload(o)), allowed_))
                    o := add(o, 1)
                    if iszero(and(result, lt(o, end))) { break }
                }
            }
        }
    }

    /// @dev Converts the bytes in the 7-bit ASCII string `s` to
    /// an allowed lookup for use in `is7BitASCII(s, allowed)`.
    /// To save runtime gas, you can cache the result in an immutable variable.
    function to7BitASCIIAllowedLookup(string memory s) internal pure returns (uint128 result) {
        /// @solidity memory-safe-assembly
        assembly {
            if mload(s) {
                let o := add(s, 0x20)
                for { let end := add(o, mload(s)) } 1 {} {
                    result := or(result, shl(byte(0, mload(o)), 1))
                    o := add(o, 1)
                    if iszero(lt(o, end)) { break }
                }
                if shr(128, result) {
                    mstore(0x00, 0xc9807e0d) // `StringNot7BitASCII()`.
                    revert(0x1c, 0x04)
                }
            }
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   BYTE STRING OPERATIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    // For performance and bytecode compactness, byte string operations are restricted
    // to 7-bit ASCII strings. All offsets are byte offsets, not UTF character offsets.
    // Usage of byte string operations on charsets with runes spanning two or more bytes
    // can lead to undefined behavior.

    /// @dev Returns `subject` all occurrences of `needle` replaced with `replacement`.
    function replace(string memory subject, string memory needle, string memory replacement)
        internal
        pure
        returns (string memory)
    {
        return string(LibBytes.replace(bytes(subject), bytes(needle), bytes(replacement)));
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from left to right, starting from `from`.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function indexOf(string memory subject, string memory needle, uint256 from)
        internal
        pure
        returns (uint256)
    {
        return LibBytes.indexOf(bytes(subject), bytes(needle), from);
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from left to right.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function indexOf(string memory subject, string memory needle) internal pure returns (uint256) {
        return LibBytes.indexOf(bytes(subject), bytes(needle), 0);
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from right to left, starting from `from`.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function lastIndexOf(string memory subject, string memory needle, uint256 from)
        internal
        pure
        returns (uint256)
    {
        return LibBytes.lastIndexOf(bytes(subject), bytes(needle), from);
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from right to left.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function lastIndexOf(string memory subject, string memory needle)
        internal
        pure
        returns (uint256)
    {
        return LibBytes.lastIndexOf(bytes(subject), bytes(needle), type(uint256).max);
    }

    /// @dev Returns true if `needle` is found in `subject`, false otherwise.
    function contains(string memory subject, string memory needle) internal pure returns (bool) {
        return LibBytes.contains(bytes(subject), bytes(needle));
    }

    /// @dev Returns whether `subject` starts with `needle`.
    function startsWith(string memory subject, string memory needle) internal pure returns (bool) {
        return LibBytes.startsWith(bytes(subject), bytes(needle));
    }

    /// @dev Returns whether `subject` ends with `needle`.
    function endsWith(string memory subject, string memory needle) internal pure returns (bool) {
        return LibBytes.endsWith(bytes(subject), bytes(needle));
    }

    /// @dev Returns `subject` repeated `times`.
    function repeat(string memory subject, uint256 times) internal pure returns (string memory) {
        return string(LibBytes.repeat(bytes(subject), times));
    }

    /// @dev Returns a copy of `subject` sliced from `start` to `end` (exclusive).
    /// `start` and `end` are byte offsets.
    function slice(string memory subject, uint256 start, uint256 end)
        internal
        pure
        returns (string memory)
    {
        return string(LibBytes.slice(bytes(subject), start, end));
    }

    /// @dev Returns a copy of `subject` sliced from `start` to the end of the string.
    /// `start` is a byte offset.
    function slice(string memory subject, uint256 start) internal pure returns (string memory) {
        return string(LibBytes.slice(bytes(subject), start, type(uint256).max));
    }

    /// @dev Returns all the indices of `needle` in `subject`.
    /// The indices are byte offsets.
    function indicesOf(string memory subject, string memory needle)
        internal
        pure
        returns (uint256[] memory)
    {
        return LibBytes.indicesOf(bytes(subject), bytes(needle));
    }

    /// @dev Returns a arrays of strings based on the `delimiter` inside of the `subject` string.
    function split(string memory subject, string memory delimiter)
        internal
        pure
        returns (string[] memory result)
    {
        bytes[] memory a = LibBytes.split(bytes(subject), bytes(delimiter));
        /// @solidity memory-safe-assembly
        assembly {
            result := a
        }
    }

    /// @dev Returns a concatenated string of `a` and `b`.
    /// Cheaper than `string.concat()` and does not de-align the free memory pointer.
    function concat(string memory a, string memory b) internal pure returns (string memory) {
        return string(LibBytes.concat(bytes(a), bytes(b)));
    }

    /// @dev Returns a copy of the string in either lowercase or UPPERCASE.
    /// WARNING! This function is only compatible with 7-bit ASCII strings.
    function toCase(string memory subject, bool toUpper)
        internal
        pure
        returns (string memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let n := mload(subject)
            if n {
                result := mload(0x40)
                let o := add(result, 0x20)
                let d := sub(subject, result)
                let flags := shl(add(70, shl(5, toUpper)), 0x3ffffff)
                for { let end := add(o, n) } 1 {} {
                    let b := byte(0, mload(add(d, o)))
                    mstore8(o, xor(and(shr(b, flags), 0x20), b))
                    o := add(o, 1)
                    if eq(o, end) { break }
                }
                mstore(result, n) // Store the length.
                mstore(o, 0) // Zeroize the slot after the string.
                mstore(0x40, add(o, 0x20)) // Allocate memory.
            }
        }
    }

    /// @dev Returns a string from a small bytes32 string.
    /// `s` must be null-terminated, or behavior will be undefined.
    function fromSmallString(bytes32 s) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let n := 0
            for {} byte(n, s) { n := add(n, 1) } {} // Scan for '\0'.
            mstore(result, n) // Store the length.
            let o := add(result, 0x20)
            mstore(o, s) // Store the bytes of the string.
            mstore(add(o, n), 0) // Zeroize the slot after the string.
            mstore(0x40, add(result, 0x40)) // Allocate memory.
        }
    }

    /// @dev Returns the small string, with all bytes after the first null byte zeroized.
    function normalizeSmallString(bytes32 s) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            for {} byte(result, s) { result := add(result, 1) } {} // Scan for '\0'.
            mstore(0x00, s)
            mstore(result, 0x00)
            result := mload(0x00)
        }
    }

    /// @dev Returns the string as a normalized null-terminated small string.
    function toSmallString(string memory s) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(s)
            if iszero(lt(result, 33)) {
                mstore(0x00, 0xec92f9a3) // `TooBigForSmallString()`.
                revert(0x1c, 0x04)
            }
            result := shl(shl(3, sub(32, result)), mload(add(s, result)))
        }
    }

    /// @dev Returns a lowercased copy of the string.
    /// WARNING! This function is only compatible with 7-bit ASCII strings.
    function lower(string memory subject) internal pure returns (string memory result) {
        result = toCase(subject, false);
    }

    /// @dev Returns an UPPERCASED copy of the string.
    /// WARNING! This function is only compatible with 7-bit ASCII strings.
    function upper(string memory subject) internal pure returns (string memory result) {
        result = toCase(subject, true);
    }

    /// @dev Escapes the string to be used within HTML tags.
    function escapeHTML(string memory s) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let end := add(s, mload(s))
            let o := add(result, 0x20)
            // Store the bytes of the packed offsets and strides into the scratch space.
            // `packed = (stride << 5) | offset`. Max offset is 20. Max stride is 6.
            mstore(0x1f, 0x900094)
            mstore(0x08, 0xc0000000a6ab)
            // Store "&quot;&amp;&#39;&lt;&gt;" into the scratch space.
            mstore(0x00, shl(64, 0x2671756f743b26616d703b262333393b266c743b2667743b))
            for {} iszero(eq(s, end)) {} {
                s := add(s, 1)
                let c := and(mload(s), 0xff)
                // Not in `["\"","'","&","<",">"]`.
                if iszero(and(shl(c, 1), 0x500000c400000000)) {
                    mstore8(o, c)
                    o := add(o, 1)
                    continue
                }
                let t := shr(248, mload(c))
                mstore(o, mload(and(t, 0x1f)))
                o := add(o, shr(5, t))
            }
            mstore(o, 0) // Zeroize the slot after the string.
            mstore(result, sub(o, add(result, 0x20))) // Store the length.
            mstore(0x40, add(o, 0x20)) // Allocate memory.
        }
    }

    /// @dev Escapes the string to be used within double-quotes in a JSON.
    /// If `addDoubleQuotes` is true, the result will be enclosed in double-quotes.
    function escapeJSON(string memory s, bool addDoubleQuotes)
        internal
        pure
        returns (string memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let o := add(result, 0x20)
            if addDoubleQuotes {
                mstore8(o, 34)
                o := add(1, o)
            }
            // Store "\\u0000" in scratch space.
            // Store "0123456789abcdef" in scratch space.
            // Also, store `{0x08:"b", 0x09:"t", 0x0a:"n", 0x0c:"f", 0x0d:"r"}`.
            // into the scratch space.
            mstore(0x15, 0x5c75303030303031323334353637383961626364656662746e006672)
            // Bitmask for detecting `["\"","\\"]`.
            let e := or(shl(0x22, 1), shl(0x5c, 1))
            for { let end := add(s, mload(s)) } iszero(eq(s, end)) {} {
                s := add(s, 1)
                let c := and(mload(s), 0xff)
                if iszero(lt(c, 0x20)) {
                    if iszero(and(shl(c, 1), e)) {
                        // Not in `["\"","\\"]`.
                        mstore8(o, c)
                        o := add(o, 1)
                        continue
                    }
                    mstore8(o, 0x5c) // "\\".
                    mstore8(add(o, 1), c)
                    o := add(o, 2)
                    continue
                }
                if iszero(and(shl(c, 1), 0x3700)) {
                    // Not in `["\b","\t","\n","\f","\d"]`.
                    mstore8(0x1d, mload(shr(4, c))) // Hex value.
                    mstore8(0x1e, mload(and(c, 15))) // Hex value.
                    mstore(o, mload(0x19)) // "\\u00XX".
                    o := add(o, 6)
                    continue
                }
                mstore8(o, 0x5c) // "\\".
                mstore8(add(o, 1), mload(add(c, 8)))
                o := add(o, 2)
            }
            if addDoubleQuotes {
                mstore8(o, 34)
                o := add(1, o)
            }
            mstore(o, 0) // Zeroize the slot after the string.
            mstore(result, sub(o, add(result, 0x20))) // Store the length.
            mstore(0x40, add(o, 0x20)) // Allocate memory.
        }
    }

    /// @dev Escapes the string to be used within double-quotes in a JSON.
    function escapeJSON(string memory s) internal pure returns (string memory result) {
        result = escapeJSON(s, false);
    }

    /// @dev Encodes `s` so that it can be safely used in a URI,
    /// just like `encodeURIComponent` in JavaScript.
    /// See: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent
    /// See: https://datatracker.ietf.org/doc/html/rfc2396
    /// See: https://datatracker.ietf.org/doc/html/rfc3986
    function encodeURIComponent(string memory s) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            // Store "0123456789ABCDEF" in scratch space.
            // Uppercased to be consistent with JavaScript's implementation.
            mstore(0x0f, 0x30313233343536373839414243444546)
            let o := add(result, 0x20)
            for { let end := add(s, mload(s)) } iszero(eq(s, end)) {} {
                s := add(s, 1)
                let c := and(mload(s), 0xff)
                // If not in `[0-9A-Z-a-z-_.!~*'()]`.
                if iszero(and(1, shr(c, 0x47fffffe87fffffe03ff678200000000))) {
                    mstore8(o, 0x25) // '%'.
                    mstore8(add(o, 1), mload(and(shr(4, c), 15)))
                    mstore8(add(o, 2), mload(and(c, 15)))
                    o := add(o, 3)
                    continue
                }
                mstore8(o, c)
                o := add(o, 1)
            }
            mstore(result, sub(o, add(result, 0x20))) // Store the length.
            mstore(o, 0) // Zeroize the slot after the string.
            mstore(0x40, add(o, 0x20)) // Allocate memory.
        }
    }

    /// @dev Returns whether `a` equals `b`.
    function eq(string memory a, string memory b) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := eq(keccak256(add(a, 0x20), mload(a)), keccak256(add(b, 0x20), mload(b)))
        }
    }

    /// @dev Returns whether `a` equals `b`, where `b` is a null-terminated small string.
    function eqs(string memory a, bytes32 b) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            // These should be evaluated on compile time, as far as possible.
            let m := not(shl(7, div(not(iszero(b)), 255))) // `0x7f7f ...`.
            let x := not(or(m, or(b, add(m, and(b, m)))))
            let r := shl(7, iszero(iszero(shr(128, x))))
            r := or(r, shl(6, iszero(iszero(shr(64, shr(r, x))))))
            r := or(r, shl(5, lt(0xffffffff, shr(r, x))))
            r := or(r, shl(4, lt(0xffff, shr(r, x))))
            r := or(r, shl(3, lt(0xff, shr(r, x))))
            // forgefmt: disable-next-item
            result := gt(eq(mload(a), add(iszero(x), xor(31, shr(3, r)))),
                xor(shr(add(8, r), b), shr(add(8, r), mload(add(a, 0x20)))))
        }
    }

    /// @dev Returns 0 if `a == b`, -1 if `a < b`, +1 if `a > b`.
    /// If `a` == b[:a.length]`, and `a.length < b.length`, returns -1.
    function cmp(string memory a, string memory b) internal pure returns (int256) {
        return LibBytes.cmp(bytes(a), bytes(b));
    }

    /// @dev Packs a single string with its length into a single word.
    /// Returns `bytes32(0)` if the length is zero or greater than 31.
    function packOne(string memory a) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            // We don't need to zero right pad the string,
            // since this is our own custom non-standard packing scheme.
            result :=
                mul(
                    // Load the length and the bytes.
                    mload(add(a, 0x1f)),
                    // `length != 0 && length < 32`. Abuses underflow.
                    // Assumes that the length is valid and within the block gas limit.
                    lt(sub(mload(a), 1), 0x1f)
                )
        }
    }

    /// @dev Unpacks a string packed using {packOne}.
    /// Returns the empty string if `packed` is `bytes32(0)`.
    /// If `packed` is not an output of {packOne}, the output behavior is undefined.
    function unpackOne(bytes32 packed) internal pure returns (string memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40) // Grab the free memory pointer.
            mstore(0x40, add(result, 0x40)) // Allocate 2 words (1 for the length, 1 for the bytes).
            mstore(result, 0) // Zeroize the length slot.
            mstore(add(result, 0x1f), packed) // Store the length and bytes.
            mstore(add(add(result, 0x20), mload(result)), 0) // Right pad with zeroes.
        }
    }

    /// @dev Packs two strings with their lengths into a single word.
    /// Returns `bytes32(0)` if combined length is zero or greater than 30.
    function packTwo(string memory a, string memory b) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            let aLen := mload(a)
            // We don't need to zero right pad the strings,
            // since this is our own custom non-standard packing scheme.
            result :=
                mul(
                    or( // Load the length and the bytes of `a` and `b`.
                    shl(shl(3, sub(0x1f, aLen)), mload(add(a, aLen))), mload(sub(add(b, 0x1e), aLen))),
                    // `totalLen != 0 && totalLen < 31`. Abuses underflow.
                    // Assumes that the lengths are valid and within the block gas limit.
                    lt(sub(add(aLen, mload(b)), 1), 0x1e)
                )
        }
    }

    /// @dev Unpacks strings packed using {packTwo}.
    /// Returns the empty strings if `packed` is `bytes32(0)`.
    /// If `packed` is not an output of {packTwo}, the output behavior is undefined.
    function unpackTwo(bytes32 packed)
        internal
        pure
        returns (string memory resultA, string memory resultB)
    {
        /// @solidity memory-safe-assembly
        assembly {
            resultA := mload(0x40) // Grab the free memory pointer.
            resultB := add(resultA, 0x40)
            // Allocate 2 words for each string (1 for the length, 1 for the byte). Total 4 words.
            mstore(0x40, add(resultB, 0x40))
            // Zeroize the length slots.
            mstore(resultA, 0)
            mstore(resultB, 0)
            // Store the lengths and bytes.
            mstore(add(resultA, 0x1f), packed)
            mstore(add(resultB, 0x1f), mload(add(add(resultA, 0x20), mload(resultA))))
            // Right pad with zeroes.
            mstore(add(add(resultA, 0x20), mload(resultA)), 0)
            mstore(add(add(resultB, 0x20), mload(resultB)), 0)
        }
    }

    /// @dev Directly returns `a` without copying.
    function directReturn(string memory a) internal pure {
        assembly {
            // Assumes that the string does not start from the scratch space.
            let retStart := sub(a, 0x20)
            let retUnpaddedSize := add(mload(a), 0x40)
            // Right pad with zeroes. Just in case the string is produced
            // by a method that doesn't zero right pad.
            mstore(add(retStart, retUnpaddedSize), 0)
            mstore(retStart, 0x20) // Store the return offset.
            // End the transaction, returning the string.
            return(retStart, and(not(0x1f), add(0x1f, retUnpaddedSize)))
        }
    }
}

File 5 of 36 : Ownable.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

/// @notice Simple single owner authorization mixin.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/auth/Ownable.sol)
///
/// @dev Note:
/// This implementation does NOT auto-initialize the owner to `msg.sender`.
/// You MUST call the `_initializeOwner` in the constructor / initializer.
///
/// While the ownable portion follows
/// [EIP-173](https://eips.ethereum.org/EIPS/eip-173) for compatibility,
/// the nomenclature for the 2-step ownership handover may be unique to this codebase.
abstract contract Ownable {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                       CUSTOM ERRORS                        */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The caller is not authorized to call the function.
    error Unauthorized();

    /// @dev The `newOwner` cannot be the zero address.
    error NewOwnerIsZeroAddress();

    /// @dev The `pendingOwner` does not have a valid handover request.
    error NoHandoverRequest();

    /// @dev Cannot double-initialize.
    error AlreadyInitialized();

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                           EVENTS                           */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The ownership is transferred from `oldOwner` to `newOwner`.
    /// This event is intentionally kept the same as OpenZeppelin's Ownable to be
    /// compatible with indexers and [EIP-173](https://eips.ethereum.org/EIPS/eip-173),
    /// despite it not being as lightweight as a single argument event.
    event OwnershipTransferred(address indexed oldOwner, address indexed newOwner);

    /// @dev An ownership handover to `pendingOwner` has been requested.
    event OwnershipHandoverRequested(address indexed pendingOwner);

    /// @dev The ownership handover to `pendingOwner` has been canceled.
    event OwnershipHandoverCanceled(address indexed pendingOwner);

    /// @dev `keccak256(bytes("OwnershipTransferred(address,address)"))`.
    uint256 private constant _OWNERSHIP_TRANSFERRED_EVENT_SIGNATURE =
        0x8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0;

    /// @dev `keccak256(bytes("OwnershipHandoverRequested(address)"))`.
    uint256 private constant _OWNERSHIP_HANDOVER_REQUESTED_EVENT_SIGNATURE =
        0xdbf36a107da19e49527a7176a1babf963b4b0ff8cde35ee35d6cd8f1f9ac7e1d;

    /// @dev `keccak256(bytes("OwnershipHandoverCanceled(address)"))`.
    uint256 private constant _OWNERSHIP_HANDOVER_CANCELED_EVENT_SIGNATURE =
        0xfa7b8eab7da67f412cc9575ed43464468f9bfbae89d1675917346ca6d8fe3c92;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                          STORAGE                           */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The owner slot is given by:
    /// `bytes32(~uint256(uint32(bytes4(keccak256("_OWNER_SLOT_NOT")))))`.
    /// It is intentionally chosen to be a high value
    /// to avoid collision with lower slots.
    /// The choice of manual storage layout is to enable compatibility
    /// with both regular and upgradeable contracts.
    bytes32 internal constant _OWNER_SLOT =
        0xffffffffffffffffffffffffffffffffffffffffffffffffffffffff74873927;

    /// The ownership handover slot of `newOwner` is given by:
    /// ```
    ///     mstore(0x00, or(shl(96, user), _HANDOVER_SLOT_SEED))
    ///     let handoverSlot := keccak256(0x00, 0x20)
    /// ```
    /// It stores the expiry timestamp of the two-step ownership handover.
    uint256 private constant _HANDOVER_SLOT_SEED = 0x389a75e1;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                     INTERNAL FUNCTIONS                     */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Override to return true to make `_initializeOwner` prevent double-initialization.
    function _guardInitializeOwner() internal pure virtual returns (bool guard) {}

    /// @dev Initializes the owner directly without authorization guard.
    /// This function must be called upon initialization,
    /// regardless of whether the contract is upgradeable or not.
    /// This is to enable generalization to both regular and upgradeable contracts,
    /// and to save gas in case the initial owner is not the caller.
    /// For performance reasons, this function will not check if there
    /// is an existing owner.
    function _initializeOwner(address newOwner) internal virtual {
        if (_guardInitializeOwner()) {
            /// @solidity memory-safe-assembly
            assembly {
                let ownerSlot := _OWNER_SLOT
                if sload(ownerSlot) {
                    mstore(0x00, 0x0dc149f0) // `AlreadyInitialized()`.
                    revert(0x1c, 0x04)
                }
                // Clean the upper 96 bits.
                newOwner := shr(96, shl(96, newOwner))
                // Store the new value.
                sstore(ownerSlot, or(newOwner, shl(255, iszero(newOwner))))
                // Emit the {OwnershipTransferred} event.
                log3(0, 0, _OWNERSHIP_TRANSFERRED_EVENT_SIGNATURE, 0, newOwner)
            }
        } else {
            /// @solidity memory-safe-assembly
            assembly {
                // Clean the upper 96 bits.
                newOwner := shr(96, shl(96, newOwner))
                // Store the new value.
                sstore(_OWNER_SLOT, newOwner)
                // Emit the {OwnershipTransferred} event.
                log3(0, 0, _OWNERSHIP_TRANSFERRED_EVENT_SIGNATURE, 0, newOwner)
            }
        }
    }

    /// @dev Sets the owner directly without authorization guard.
    function _setOwner(address newOwner) internal virtual {
        if (_guardInitializeOwner()) {
            /// @solidity memory-safe-assembly
            assembly {
                let ownerSlot := _OWNER_SLOT
                // Clean the upper 96 bits.
                newOwner := shr(96, shl(96, newOwner))
                // Emit the {OwnershipTransferred} event.
                log3(0, 0, _OWNERSHIP_TRANSFERRED_EVENT_SIGNATURE, sload(ownerSlot), newOwner)
                // Store the new value.
                sstore(ownerSlot, or(newOwner, shl(255, iszero(newOwner))))
            }
        } else {
            /// @solidity memory-safe-assembly
            assembly {
                let ownerSlot := _OWNER_SLOT
                // Clean the upper 96 bits.
                newOwner := shr(96, shl(96, newOwner))
                // Emit the {OwnershipTransferred} event.
                log3(0, 0, _OWNERSHIP_TRANSFERRED_EVENT_SIGNATURE, sload(ownerSlot), newOwner)
                // Store the new value.
                sstore(ownerSlot, newOwner)
            }
        }
    }

    /// @dev Throws if the sender is not the owner.
    function _checkOwner() internal view virtual {
        /// @solidity memory-safe-assembly
        assembly {
            // If the caller is not the stored owner, revert.
            if iszero(eq(caller(), sload(_OWNER_SLOT))) {
                mstore(0x00, 0x82b42900) // `Unauthorized()`.
                revert(0x1c, 0x04)
            }
        }
    }

    /// @dev Returns how long a two-step ownership handover is valid for in seconds.
    /// Override to return a different value if needed.
    /// Made internal to conserve bytecode. Wrap it in a public function if needed.
    function _ownershipHandoverValidFor() internal view virtual returns (uint64) {
        return 48 * 3600;
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                  PUBLIC UPDATE FUNCTIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Allows the owner to transfer the ownership to `newOwner`.
    function transferOwnership(address newOwner) public payable virtual onlyOwner {
        /// @solidity memory-safe-assembly
        assembly {
            if iszero(shl(96, newOwner)) {
                mstore(0x00, 0x7448fbae) // `NewOwnerIsZeroAddress()`.
                revert(0x1c, 0x04)
            }
        }
        _setOwner(newOwner);
    }

    /// @dev Allows the owner to renounce their ownership.
    function renounceOwnership() public payable virtual onlyOwner {
        _setOwner(address(0));
    }

    /// @dev Request a two-step ownership handover to the caller.
    /// The request will automatically expire in 48 hours (172800 seconds) by default.
    function requestOwnershipHandover() public payable virtual {
        unchecked {
            uint256 expires = block.timestamp + _ownershipHandoverValidFor();
            /// @solidity memory-safe-assembly
            assembly {
                // Compute and set the handover slot to `expires`.
                mstore(0x0c, _HANDOVER_SLOT_SEED)
                mstore(0x00, caller())
                sstore(keccak256(0x0c, 0x20), expires)
                // Emit the {OwnershipHandoverRequested} event.
                log2(0, 0, _OWNERSHIP_HANDOVER_REQUESTED_EVENT_SIGNATURE, caller())
            }
        }
    }

    /// @dev Cancels the two-step ownership handover to the caller, if any.
    function cancelOwnershipHandover() public payable virtual {
        /// @solidity memory-safe-assembly
        assembly {
            // Compute and set the handover slot to 0.
            mstore(0x0c, _HANDOVER_SLOT_SEED)
            mstore(0x00, caller())
            sstore(keccak256(0x0c, 0x20), 0)
            // Emit the {OwnershipHandoverCanceled} event.
            log2(0, 0, _OWNERSHIP_HANDOVER_CANCELED_EVENT_SIGNATURE, caller())
        }
    }

    /// @dev Allows the owner to complete the two-step ownership handover to `pendingOwner`.
    /// Reverts if there is no existing ownership handover requested by `pendingOwner`.
    function completeOwnershipHandover(address pendingOwner) public payable virtual onlyOwner {
        /// @solidity memory-safe-assembly
        assembly {
            // Compute and set the handover slot to 0.
            mstore(0x0c, _HANDOVER_SLOT_SEED)
            mstore(0x00, pendingOwner)
            let handoverSlot := keccak256(0x0c, 0x20)
            // If the handover does not exist, or has expired.
            if gt(timestamp(), sload(handoverSlot)) {
                mstore(0x00, 0x6f5e8818) // `NoHandoverRequest()`.
                revert(0x1c, 0x04)
            }
            // Set the handover slot to 0.
            sstore(handoverSlot, 0)
        }
        _setOwner(pendingOwner);
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   PUBLIC READ FUNCTIONS                    */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns the owner of the contract.
    function owner() public view virtual returns (address result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := sload(_OWNER_SLOT)
        }
    }

    /// @dev Returns the expiry timestamp for the two-step ownership handover to `pendingOwner`.
    function ownershipHandoverExpiresAt(address pendingOwner)
        public
        view
        virtual
        returns (uint256 result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            // Compute the handover slot.
            mstore(0x0c, _HANDOVER_SLOT_SEED)
            mstore(0x00, pendingOwner)
            // Load the handover slot.
            result := sload(keccak256(0x0c, 0x20))
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         MODIFIERS                          */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Marks a function as only callable by the owner.
    modifier onlyOwner() virtual {
        _checkOwner();
        _;
    }
}

File 6 of 36 : AccessControl.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (access/AccessControl.sol)

pragma solidity ^0.8.0;

import "./IAccessControl.sol";
import "../utils/Context.sol";
import "../utils/Strings.sol";
import "../utils/introspection/ERC165.sol";

/**
 * @dev Contract module that allows children to implement role-based access
 * control mechanisms. This is a lightweight version that doesn't allow enumerating role
 * members except through off-chain means by accessing the contract event logs. Some
 * applications may benefit from on-chain enumerability, for those cases see
 * {AccessControlEnumerable}.
 *
 * Roles are referred to by their `bytes32` identifier. These should be exposed
 * in the external API and be unique. The best way to achieve this is by
 * using `public constant` hash digests:
 *
 * ```
 * bytes32 public constant MY_ROLE = keccak256("MY_ROLE");
 * ```
 *
 * Roles can be used to represent a set of permissions. To restrict access to a
 * function call, use {hasRole}:
 *
 * ```
 * function foo() public {
 *     require(hasRole(MY_ROLE, msg.sender));
 *     ...
 * }
 * ```
 *
 * Roles can be granted and revoked dynamically via the {grantRole} and
 * {revokeRole} functions. Each role has an associated admin role, and only
 * accounts that have a role's admin role can call {grantRole} and {revokeRole}.
 *
 * By default, the admin role for all roles is `DEFAULT_ADMIN_ROLE`, which means
 * that only accounts with this role will be able to grant or revoke other
 * roles. More complex role relationships can be created by using
 * {_setRoleAdmin}.
 *
 * WARNING: The `DEFAULT_ADMIN_ROLE` is also its own admin: it has permission to
 * grant and revoke this role. Extra precautions should be taken to secure
 * accounts that have been granted it.
 */
abstract contract AccessControl is Context, IAccessControl, ERC165 {
    struct RoleData {
        mapping(address => bool) members;
        bytes32 adminRole;
    }

    mapping(bytes32 => RoleData) private _roles;

    bytes32 public constant DEFAULT_ADMIN_ROLE = 0x00;

    /**
     * @dev Modifier that checks that an account has a specific role. Reverts
     * with a standardized message including the required role.
     *
     * The format of the revert reason is given by the following regular expression:
     *
     *  /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
     *
     * _Available since v4.1._
     */
    modifier onlyRole(bytes32 role) {
        _checkRole(role);
        _;
    }

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

    /**
     * @dev Returns `true` if `account` has been granted `role`.
     */
    function hasRole(bytes32 role, address account) public view virtual override returns (bool) {
        return _roles[role].members[account];
    }

    /**
     * @dev Revert with a standard message if `_msgSender()` is missing `role`.
     * Overriding this function changes the behavior of the {onlyRole} modifier.
     *
     * Format of the revert message is described in {_checkRole}.
     *
     * _Available since v4.6._
     */
    function _checkRole(bytes32 role) internal view virtual {
        _checkRole(role, _msgSender());
    }

    /**
     * @dev Revert with a standard message if `account` is missing `role`.
     *
     * The format of the revert reason is given by the following regular expression:
     *
     *  /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
     */
    function _checkRole(bytes32 role, address account) internal view virtual {
        if (!hasRole(role, account)) {
            revert(
                string(
                    abi.encodePacked(
                        "AccessControl: account ",
                        Strings.toHexString(account),
                        " is missing role ",
                        Strings.toHexString(uint256(role), 32)
                    )
                )
            );
        }
    }

    /**
     * @dev Returns the admin role that controls `role`. See {grantRole} and
     * {revokeRole}.
     *
     * To change a role's admin, use {_setRoleAdmin}.
     */
    function getRoleAdmin(bytes32 role) public view virtual override returns (bytes32) {
        return _roles[role].adminRole;
    }

    /**
     * @dev Grants `role` to `account`.
     *
     * If `account` had not been already granted `role`, emits a {RoleGranted}
     * event.
     *
     * Requirements:
     *
     * - the caller must have ``role``'s admin role.
     *
     * May emit a {RoleGranted} event.
     */
    function grantRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) {
        _grantRole(role, account);
    }

    /**
     * @dev Revokes `role` from `account`.
     *
     * If `account` had been granted `role`, emits a {RoleRevoked} event.
     *
     * Requirements:
     *
     * - the caller must have ``role``'s admin role.
     *
     * May emit a {RoleRevoked} event.
     */
    function revokeRole(bytes32 role, address account) public virtual override onlyRole(getRoleAdmin(role)) {
        _revokeRole(role, account);
    }

    /**
     * @dev Revokes `role` from the calling account.
     *
     * Roles are often managed via {grantRole} and {revokeRole}: this function's
     * purpose is to provide a mechanism for accounts to lose their privileges
     * if they are compromised (such as when a trusted device is misplaced).
     *
     * If the calling account had been revoked `role`, emits a {RoleRevoked}
     * event.
     *
     * Requirements:
     *
     * - the caller must be `account`.
     *
     * May emit a {RoleRevoked} event.
     */
    function renounceRole(bytes32 role, address account) public virtual override {
        require(account == _msgSender(), "AccessControl: can only renounce roles for self");

        _revokeRole(role, account);
    }

    /**
     * @dev Grants `role` to `account`.
     *
     * If `account` had not been already granted `role`, emits a {RoleGranted}
     * event. Note that unlike {grantRole}, this function doesn't perform any
     * checks on the calling account.
     *
     * May emit a {RoleGranted} event.
     *
     * [WARNING]
     * ====
     * This function should only be called from the constructor when setting
     * up the initial roles for the system.
     *
     * Using this function in any other way is effectively circumventing the admin
     * system imposed by {AccessControl}.
     * ====
     *
     * NOTE: This function is deprecated in favor of {_grantRole}.
     */
    function _setupRole(bytes32 role, address account) internal virtual {
        _grantRole(role, account);
    }

    /**
     * @dev Sets `adminRole` as ``role``'s admin role.
     *
     * Emits a {RoleAdminChanged} event.
     */
    function _setRoleAdmin(bytes32 role, bytes32 adminRole) internal virtual {
        bytes32 previousAdminRole = getRoleAdmin(role);
        _roles[role].adminRole = adminRole;
        emit RoleAdminChanged(role, previousAdminRole, adminRole);
    }

    /**
     * @dev Grants `role` to `account`.
     *
     * Internal function without access restriction.
     *
     * May emit a {RoleGranted} event.
     */
    function _grantRole(bytes32 role, address account) internal virtual {
        if (!hasRole(role, account)) {
            _roles[role].members[account] = true;
            emit RoleGranted(role, account, _msgSender());
        }
    }

    /**
     * @dev Revokes `role` from `account`.
     *
     * Internal function without access restriction.
     *
     * May emit a {RoleRevoked} event.
     */
    function _revokeRole(bytes32 role, address account) internal virtual {
        if (hasRole(role, account)) {
            _roles[role].members[account] = false;
            emit RoleRevoked(role, account, _msgSender());
        }
    }
}

File 7 of 36 : IERC20.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)

pragma solidity ^0.8.0;

/**
 * @dev Interface of the ERC20 standard as defined in the EIP.
 */
interface IERC20 {
    /**
     * @dev Emitted when `value` tokens are moved from one account (`from`) to
     * another (`to`).
     *
     * Note that `value` may be zero.
     */
    event Transfer(address indexed from, address indexed to, uint256 value);

    /**
     * @dev Emitted when the allowance of a `spender` for an `owner` is set by
     * a call to {approve}. `value` is the new allowance.
     */
    event Approval(address indexed owner, address indexed spender, uint256 value);

    /**
     * @dev Returns the amount of tokens in existence.
     */
    function totalSupply() external view returns (uint256);

    /**
     * @dev Returns the amount of tokens owned by `account`.
     */
    function balanceOf(address account) external view returns (uint256);

    /**
     * @dev Moves `amount` tokens from the caller's account to `to`.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * Emits a {Transfer} event.
     */
    function transfer(address to, uint256 amount) external returns (bool);

    /**
     * @dev Returns the remaining number of tokens that `spender` will be
     * allowed to spend on behalf of `owner` through {transferFrom}. This is
     * zero by default.
     *
     * This value changes when {approve} or {transferFrom} are called.
     */
    function allowance(address owner, address spender) external view returns (uint256);

    /**
     * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * IMPORTANT: Beware that changing an allowance with this method brings the risk
     * that someone may use both the old and the new allowance by unfortunate
     * transaction ordering. One possible solution to mitigate this race
     * condition is to first reduce the spender's allowance to 0 and set the
     * desired value afterwards:
     * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729
     *
     * Emits an {Approval} event.
     */
    function approve(address spender, uint256 amount) external returns (bool);

    /**
     * @dev Moves `amount` tokens from `from` to `to` using the
     * allowance mechanism. `amount` is then deducted from the caller's
     * allowance.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * Emits a {Transfer} event.
     */
    function transferFrom(
        address from,
        address to,
        uint256 amount
    ) external returns (bool);
}

File 8 of 36 : ECDSA.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

/// @notice Gas optimized ECDSA wrapper.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/ECDSA.sol)
/// @author Modified from Solmate (https://github.com/transmissions11/solmate/blob/main/src/utils/ECDSA.sol)
/// @author Modified from OpenZeppelin (https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/utils/cryptography/ECDSA.sol)
///
/// @dev Note:
/// - The recovery functions use the ecrecover precompile (0x1).
/// - As of Solady version 0.0.68, the `recover` variants will revert upon recovery failure.
///   This is for more safety by default.
///   Use the `tryRecover` variants if you need to get the zero address back
///   upon recovery failure instead.
/// - As of Solady version 0.0.134, all `bytes signature` variants accept both
///   regular 65-byte `(r, s, v)` and EIP-2098 `(r, vs)` short form signatures.
///   See: https://eips.ethereum.org/EIPS/eip-2098
///   This is for calldata efficiency on smart accounts prevalent on L2s.
///
/// WARNING! Do NOT directly use signatures as unique identifiers:
/// - The recovery operations do NOT check if a signature is non-malleable.
/// - Use a nonce in the digest to prevent replay attacks on the same contract.
/// - Use EIP-712 for the digest to prevent replay attacks across different chains and contracts.
///   EIP-712 also enables readable signing of typed data for better user safety.
/// - If you need a unique hash from a signature, please use the `canonicalHash` functions.
library ECDSA {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         CONSTANTS                          */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The order of the secp256k1 elliptic curve.
    uint256 internal constant N = 0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141;

    /// @dev `N/2 + 1`. Used for checking the malleability of the signature.
    uint256 private constant _HALF_N_PLUS_1 =
        0x7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a1;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                        CUSTOM ERRORS                       */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The signature is invalid.
    error InvalidSignature();

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                    RECOVERY OPERATIONS                     */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Recovers the signer's address from a message digest `hash`, and the `signature`.
    function recover(bytes32 hash, bytes memory signature) internal view returns (address result) {
        /// @solidity memory-safe-assembly
        assembly {
            for { let m := mload(0x40) } 1 {
                mstore(0x00, 0x8baa579f) // `InvalidSignature()`.
                revert(0x1c, 0x04)
            } {
                switch mload(signature)
                case 64 {
                    let vs := mload(add(signature, 0x40))
                    mstore(0x20, add(shr(255, vs), 27)) // `v`.
                    mstore(0x60, shr(1, shl(1, vs))) // `s`.
                }
                case 65 {
                    mstore(0x20, byte(0, mload(add(signature, 0x60)))) // `v`.
                    mstore(0x60, mload(add(signature, 0x40))) // `s`.
                }
                default { continue }
                mstore(0x00, hash)
                mstore(0x40, mload(add(signature, 0x20))) // `r`.
                result := mload(staticcall(gas(), 1, 0x00, 0x80, 0x01, 0x20))
                mstore(0x60, 0) // Restore the zero slot.
                mstore(0x40, m) // Restore the free memory pointer.
                // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
                if returndatasize() { break }
            }
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`, and the `signature`.
    function recoverCalldata(bytes32 hash, bytes calldata signature)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            for { let m := mload(0x40) } 1 {
                mstore(0x00, 0x8baa579f) // `InvalidSignature()`.
                revert(0x1c, 0x04)
            } {
                switch signature.length
                case 64 {
                    let vs := calldataload(add(signature.offset, 0x20))
                    mstore(0x20, add(shr(255, vs), 27)) // `v`.
                    mstore(0x40, calldataload(signature.offset)) // `r`.
                    mstore(0x60, shr(1, shl(1, vs))) // `s`.
                }
                case 65 {
                    mstore(0x20, byte(0, calldataload(add(signature.offset, 0x40)))) // `v`.
                    calldatacopy(0x40, signature.offset, 0x40) // Copy `r` and `s`.
                }
                default { continue }
                mstore(0x00, hash)
                result := mload(staticcall(gas(), 1, 0x00, 0x80, 0x01, 0x20))
                mstore(0x60, 0) // Restore the zero slot.
                mstore(0x40, m) // Restore the free memory pointer.
                // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
                if returndatasize() { break }
            }
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`,
    /// and the EIP-2098 short form signature defined by `r` and `vs`.
    function recover(bytes32 hash, bytes32 r, bytes32 vs) internal view returns (address result) {
        /// @solidity memory-safe-assembly
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x00, hash)
            mstore(0x20, add(shr(255, vs), 27)) // `v`.
            mstore(0x40, r)
            mstore(0x60, shr(1, shl(1, vs))) // `s`.
            result := mload(staticcall(gas(), 1, 0x00, 0x80, 0x01, 0x20))
            // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
            if iszero(returndatasize()) {
                mstore(0x00, 0x8baa579f) // `InvalidSignature()`.
                revert(0x1c, 0x04)
            }
            mstore(0x60, 0) // Restore the zero slot.
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`,
    /// and the signature defined by `v`, `r`, `s`.
    function recover(bytes32 hash, uint8 v, bytes32 r, bytes32 s)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x00, hash)
            mstore(0x20, and(v, 0xff))
            mstore(0x40, r)
            mstore(0x60, s)
            result := mload(staticcall(gas(), 1, 0x00, 0x80, 0x01, 0x20))
            // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
            if iszero(returndatasize()) {
                mstore(0x00, 0x8baa579f) // `InvalidSignature()`.
                revert(0x1c, 0x04)
            }
            mstore(0x60, 0) // Restore the zero slot.
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   TRY-RECOVER OPERATIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    // WARNING!
    // These functions will NOT revert upon recovery failure.
    // Instead, they will return the zero address upon recovery failure.
    // It is critical that the returned address is NEVER compared against
    // a zero address (e.g. an uninitialized address variable).

    /// @dev Recovers the signer's address from a message digest `hash`, and the `signature`.
    function tryRecover(bytes32 hash, bytes memory signature)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            for { let m := mload(0x40) } 1 {} {
                switch mload(signature)
                case 64 {
                    let vs := mload(add(signature, 0x40))
                    mstore(0x20, add(shr(255, vs), 27)) // `v`.
                    mstore(0x60, shr(1, shl(1, vs))) // `s`.
                }
                case 65 {
                    mstore(0x20, byte(0, mload(add(signature, 0x60)))) // `v`.
                    mstore(0x60, mload(add(signature, 0x40))) // `s`.
                }
                default { break }
                mstore(0x00, hash)
                mstore(0x40, mload(add(signature, 0x20))) // `r`.
                pop(staticcall(gas(), 1, 0x00, 0x80, 0x40, 0x20))
                mstore(0x60, 0) // Restore the zero slot.
                // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
                result := mload(xor(0x60, returndatasize()))
                mstore(0x40, m) // Restore the free memory pointer.
                break
            }
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`, and the `signature`.
    function tryRecoverCalldata(bytes32 hash, bytes calldata signature)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            for { let m := mload(0x40) } 1 {} {
                switch signature.length
                case 64 {
                    let vs := calldataload(add(signature.offset, 0x20))
                    mstore(0x20, add(shr(255, vs), 27)) // `v`.
                    mstore(0x40, calldataload(signature.offset)) // `r`.
                    mstore(0x60, shr(1, shl(1, vs))) // `s`.
                }
                case 65 {
                    mstore(0x20, byte(0, calldataload(add(signature.offset, 0x40)))) // `v`.
                    calldatacopy(0x40, signature.offset, 0x40) // Copy `r` and `s`.
                }
                default { break }
                mstore(0x00, hash)
                pop(staticcall(gas(), 1, 0x00, 0x80, 0x40, 0x20))
                mstore(0x60, 0) // Restore the zero slot.
                // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
                result := mload(xor(0x60, returndatasize()))
                mstore(0x40, m) // Restore the free memory pointer.
                break
            }
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`,
    /// and the EIP-2098 short form signature defined by `r` and `vs`.
    function tryRecover(bytes32 hash, bytes32 r, bytes32 vs)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x00, hash)
            mstore(0x20, add(shr(255, vs), 27)) // `v`.
            mstore(0x40, r)
            mstore(0x60, shr(1, shl(1, vs))) // `s`.
            pop(staticcall(gas(), 1, 0x00, 0x80, 0x40, 0x20))
            mstore(0x60, 0) // Restore the zero slot.
            // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
            result := mload(xor(0x60, returndatasize()))
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /// @dev Recovers the signer's address from a message digest `hash`,
    /// and the signature defined by `v`, `r`, `s`.
    function tryRecover(bytes32 hash, uint8 v, bytes32 r, bytes32 s)
        internal
        view
        returns (address result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x00, hash)
            mstore(0x20, and(v, 0xff))
            mstore(0x40, r)
            mstore(0x60, s)
            pop(staticcall(gas(), 1, 0x00, 0x80, 0x40, 0x20))
            mstore(0x60, 0) // Restore the zero slot.
            // `returndatasize()` will be `0x20` upon success, and `0x00` otherwise.
            result := mload(xor(0x60, returndatasize()))
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                     HASHING OPERATIONS                     */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns an Ethereum Signed Message, created from a `hash`.
    /// This produces a hash corresponding to the one signed with the
    /// [`eth_sign`](https://ethereum.org/en/developers/docs/apis/json-rpc/#eth_sign)
    /// JSON-RPC method as part of EIP-191.
    function toEthSignedMessageHash(bytes32 hash) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            mstore(0x20, hash) // Store into scratch space for keccak256.
            mstore(0x00, "\x00\x00\x00\x00\x19Ethereum Signed Message:\n32") // 28 bytes.
            result := keccak256(0x04, 0x3c) // `32 * 2 - (32 - 28) = 60 = 0x3c`.
        }
    }

    /// @dev Returns an Ethereum Signed Message, created from `s`.
    /// This produces a hash corresponding to the one signed with the
    /// [`eth_sign`](https://ethereum.org/en/developers/docs/apis/json-rpc/#eth_sign)
    /// JSON-RPC method as part of EIP-191.
    /// Note: Supports lengths of `s` up to 999999 bytes.
    function toEthSignedMessageHash(bytes memory s) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            let sLength := mload(s)
            let o := 0x20
            mstore(o, "\x19Ethereum Signed Message:\n") // 26 bytes, zero-right-padded.
            mstore(0x00, 0x00)
            // Convert the `s.length` to ASCII decimal representation: `base10(s.length)`.
            for { let temp := sLength } 1 {} {
                o := sub(o, 1)
                mstore8(o, add(48, mod(temp, 10)))
                temp := div(temp, 10)
                if iszero(temp) { break }
            }
            let n := sub(0x3a, o) // Header length: `26 + 32 - o`.
            // Throw an out-of-offset error (consumes all gas) if the header exceeds 32 bytes.
            returndatacopy(returndatasize(), returndatasize(), gt(n, 0x20))
            mstore(s, or(mload(0x00), mload(n))) // Temporarily store the header.
            result := keccak256(add(s, sub(0x20, n)), add(n, sLength))
            mstore(s, sLength) // Restore the length.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                  CANONICAL HASH FUNCTIONS                  */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    // The following functions returns the hash of the signature in it's canonicalized format,
    // which is the 65-byte `abi.encodePacked(r, s, uint8(v))`, where `v` is either 27 or 28.
    // If `s` is greater than `N / 2` then it will be converted to `N - s`
    // and the `v` value will be flipped.
    // If the signature has an invalid length, or if `v` is invalid,
    // a uniquely corrupt hash will be returned.
    // These functions are useful for "poor-mans-VRF".

    /// @dev Returns the canonical hash of `signature`.
    function canonicalHash(bytes memory signature) internal pure returns (bytes32 result) {
        // @solidity memory-safe-assembly
        assembly {
            let l := mload(signature)
            for {} 1 {} {
                mstore(0x00, mload(add(signature, 0x20))) // `r`.
                let s := mload(add(signature, 0x40))
                let v := mload(add(signature, 0x41))
                if eq(l, 64) {
                    v := add(shr(255, s), 27)
                    s := shr(1, shl(1, s))
                }
                if iszero(lt(s, _HALF_N_PLUS_1)) {
                    v := xor(v, 7)
                    s := sub(N, s)
                }
                mstore(0x21, v)
                mstore(0x20, s)
                result := keccak256(0x00, 0x41)
                mstore(0x21, 0) // Restore the overwritten part of the free memory pointer.
                break
            }

            // If the length is neither 64 nor 65, return a uniquely corrupted hash.
            if iszero(lt(sub(l, 64), 2)) {
                // `bytes4(keccak256("InvalidSignatureLength"))`.
                result := xor(keccak256(add(signature, 0x20), l), 0xd62f1ab2)
            }
        }
    }

    /// @dev Returns the canonical hash of `signature`.
    function canonicalHashCalldata(bytes calldata signature)
        internal
        pure
        returns (bytes32 result)
    {
        // @solidity memory-safe-assembly
        assembly {
            for {} 1 {} {
                mstore(0x00, calldataload(signature.offset)) // `r`.
                let s := calldataload(add(signature.offset, 0x20))
                let v := calldataload(add(signature.offset, 0x21))
                if eq(signature.length, 64) {
                    v := add(shr(255, s), 27)
                    s := shr(1, shl(1, s))
                }
                if iszero(lt(s, _HALF_N_PLUS_1)) {
                    v := xor(v, 7)
                    s := sub(N, s)
                }
                mstore(0x21, v)
                mstore(0x20, s)
                result := keccak256(0x00, 0x41)
                mstore(0x21, 0) // Restore the overwritten part of the free memory pointer.
                break
            }
            // If the length is neither 64 nor 65, return a uniquely corrupted hash.
            if iszero(lt(sub(signature.length, 64), 2)) {
                calldatacopy(mload(0x40), signature.offset, signature.length)
                // `bytes4(keccak256("InvalidSignatureLength"))`.
                result := xor(keccak256(mload(0x40), signature.length), 0xd62f1ab2)
            }
        }
    }

    /// @dev Returns the canonical hash of `signature`.
    function canonicalHash(bytes32 r, bytes32 vs) internal pure returns (bytes32 result) {
        // @solidity memory-safe-assembly
        assembly {
            mstore(0x00, r) // `r`.
            let v := add(shr(255, vs), 27)
            let s := shr(1, shl(1, vs))
            mstore(0x21, v)
            mstore(0x20, s)
            result := keccak256(0x00, 0x41)
            mstore(0x21, 0) // Restore the overwritten part of the free memory pointer.
        }
    }

    /// @dev Returns the canonical hash of `signature`.
    function canonicalHash(uint8 v, bytes32 r, bytes32 s) internal pure returns (bytes32 result) {
        // @solidity memory-safe-assembly
        assembly {
            mstore(0x00, r) // `r`.
            if iszero(lt(s, _HALF_N_PLUS_1)) {
                v := xor(v, 7)
                s := sub(N, s)
            }
            mstore(0x21, v)
            mstore(0x20, s)
            result := keccak256(0x00, 0x41)
            mstore(0x21, 0) // Restore the overwritten part of the free memory pointer.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                   EMPTY CALLDATA HELPERS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns an empty calldata bytes.
    function emptySignature() internal pure returns (bytes calldata signature) {
        /// @solidity memory-safe-assembly
        assembly {
            signature.length := 0
        }
    }
}

File 9 of 36 : BasicRoyalties.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "@openzeppelin/contracts/token/common/ERC2981.sol";

/**
 * @title BasicRoyaltiesBase
 * @author Limit Break, Inc.
 * @dev Base functionality of an NFT mix-in contract implementing the most basic form of programmable royalties.
 */
abstract contract BasicRoyaltiesBase is ERC2981 {

    event DefaultRoyaltySet(address indexed receiver, uint96 feeNumerator);
    event TokenRoyaltySet(uint256 indexed tokenId, address indexed receiver, uint96 feeNumerator);

    function _setDefaultRoyalty(address receiver, uint96 feeNumerator) internal virtual override {
        super._setDefaultRoyalty(receiver, feeNumerator);
        emit DefaultRoyaltySet(receiver, feeNumerator);
    }

    function _setTokenRoyalty(uint256 tokenId, address receiver, uint96 feeNumerator) internal virtual override {
        super._setTokenRoyalty(tokenId, receiver, feeNumerator);
        emit TokenRoyaltySet(tokenId, receiver, feeNumerator);
    }
}

/**
 * @title BasicRoyalties
 * @author Limit Break, Inc.
 * @notice Constructable BasicRoyalties Contract implementation.
 */
abstract contract BasicRoyalties is BasicRoyaltiesBase {
    constructor(address receiver, uint96 feeNumerator) {
        _setDefaultRoyalty(receiver, feeNumerator);
    }
}

/**
 * @title BasicRoyaltiesInitializable
 * @author Limit Break, Inc.
 * @notice Initializable BasicRoyalties Contract implementation to allow for EIP-1167 clones. 
 */
abstract contract BasicRoyaltiesInitializable is BasicRoyaltiesBase {}

File 10 of 36 : ERC1155C.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "../utils/CreatorTokenBase.sol";
import "../token/erc1155/ERC1155OpenZeppelin.sol";

/**
 * @title ERC1155C
 * @author Limit Break, Inc.
 * @notice Extends OpenZeppelin's ERC1155 implementation with Creator Token functionality, which
 *         allows the contract owner to update the transfer validation logic by managing a security policy in
 *         an external transfer validation security policy registry.  See {CreatorTokenTransferValidator}.
 */
abstract contract ERC1155C is ERC1155OpenZeppelin, CreatorTokenBase {

    function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
        return interfaceId == type(ICreatorToken).interfaceId || super.supportsInterface(interfaceId);
    }

    /// @dev Ties the open-zeppelin _beforeTokenTransfer hook to more granular transfer validation logic
    function _beforeTokenTransfer(
        address /*operator*/,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory /*amounts*/,
        bytes memory /*data*/
    ) internal virtual override {
        uint256 idsArrayLength = ids.length;
        for (uint256 i = 0; i < idsArrayLength;) {
            _validateBeforeTransfer(from, to, ids[i]);

            unchecked {
                ++i;
            }
        }
    }

    /// @dev Ties the open-zeppelin _afterTokenTransfer hook to more granular transfer validation logic
    function _afterTokenTransfer(
        address /*operator*/,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory /*amounts*/,
        bytes memory /*data*/
    ) internal virtual override {
        uint256 idsArrayLength = ids.length;
        for (uint256 i = 0; i < idsArrayLength;) {
            _validateAfterTransfer(from, to, ids[i]);

            unchecked {
                ++i;
            }
        }
    }
}

/**
 * @title ERC1155CInitializable
 * @author Limit Break, Inc.
 * @notice Initializable implementation of ERC1155C to allow for EIP-1167 proxy clones.
 */
abstract contract ERC1155CInitializable is ERC1155OpenZeppelinInitializable, CreatorTokenBase {

    function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
        return interfaceId == type(ICreatorToken).interfaceId || super.supportsInterface(interfaceId);
    }

    /// @dev Ties the open-zeppelin _beforeTokenTransfer hook to more granular transfer validation logic
    function _beforeTokenTransfer(
        address /*operator*/,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory /*amounts*/,
        bytes memory /*data*/
    ) internal virtual override {
        uint256 idsArrayLength = ids.length;
        for (uint256 i = 0; i < idsArrayLength;) {
            _validateBeforeTransfer(from, to, ids[i]);

            unchecked {
                ++i;
            }
        }
    }

    /// @dev Ties the open-zeppelin _afterTokenTransfer hook to more granular transfer validation logic
    function _afterTokenTransfer(
        address /*operator*/,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory /*amounts*/,
        bytes memory /*data*/
    ) internal virtual override {
        uint256 idsArrayLength = ids.length;
        for (uint256 i = 0; i < idsArrayLength;) {
            _validateAfterTransfer(from, to, ids[i]);

            unchecked {
                ++i;
            }
        }
    }
}

File 11 of 36 : LibBytes.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

/// @notice Library for byte related operations.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/LibBytes.sol)
library LibBytes {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                          STRUCTS                           */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Goated bytes storage struct that totally MOGs, no cap, fr.
    /// Uses less gas and bytecode than Solidity's native bytes storage. It's meta af.
    /// Packs length with the first 31 bytes if <255 bytes, so it’s mad tight.
    struct BytesStorage {
        bytes32 _spacer;
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                         CONSTANTS                          */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev The constant returned when the `search` is not found in the bytes.
    uint256 internal constant NOT_FOUND = type(uint256).max;

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                  BYTE STORAGE OPERATIONS                   */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Sets the value of the bytes storage `$` to `s`.
    function set(BytesStorage storage $, bytes memory s) internal {
        /// @solidity memory-safe-assembly
        assembly {
            let n := mload(s)
            let packed := or(0xff, shl(8, n))
            for { let i := 0 } 1 {} {
                if iszero(gt(n, 0xfe)) {
                    i := 0x1f
                    packed := or(n, shl(8, mload(add(s, i))))
                    if iszero(gt(n, i)) { break }
                }
                let o := add(s, 0x20)
                mstore(0x00, $.slot)
                for { let p := keccak256(0x00, 0x20) } 1 {} {
                    sstore(add(p, shr(5, i)), mload(add(o, i)))
                    i := add(i, 0x20)
                    if iszero(lt(i, n)) { break }
                }
                break
            }
            sstore($.slot, packed)
        }
    }

    /// @dev Sets the value of the bytes storage `$` to `s`.
    function setCalldata(BytesStorage storage $, bytes calldata s) internal {
        /// @solidity memory-safe-assembly
        assembly {
            let packed := or(0xff, shl(8, s.length))
            for { let i := 0 } 1 {} {
                if iszero(gt(s.length, 0xfe)) {
                    i := 0x1f
                    packed := or(s.length, shl(8, shr(8, calldataload(s.offset))))
                    if iszero(gt(s.length, i)) { break }
                }
                mstore(0x00, $.slot)
                for { let p := keccak256(0x00, 0x20) } 1 {} {
                    sstore(add(p, shr(5, i)), calldataload(add(s.offset, i)))
                    i := add(i, 0x20)
                    if iszero(lt(i, s.length)) { break }
                }
                break
            }
            sstore($.slot, packed)
        }
    }

    /// @dev Sets the value of the bytes storage `$` to the empty bytes.
    function clear(BytesStorage storage $) internal {
        delete $._spacer;
    }

    /// @dev Returns whether the value stored is `$` is the empty bytes "".
    function isEmpty(BytesStorage storage $) internal view returns (bool) {
        return uint256($._spacer) & 0xff == uint256(0);
    }

    /// @dev Returns the length of the value stored in `$`.
    function length(BytesStorage storage $) internal view returns (uint256 result) {
        result = uint256($._spacer);
        /// @solidity memory-safe-assembly
        assembly {
            let n := and(0xff, result)
            result := or(mul(shr(8, result), eq(0xff, n)), mul(n, iszero(eq(0xff, n))))
        }
    }

    /// @dev Returns the value stored in `$`.
    function get(BytesStorage storage $) internal view returns (bytes memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let o := add(result, 0x20)
            let packed := sload($.slot)
            let n := shr(8, packed)
            for { let i := 0 } 1 {} {
                if iszero(eq(or(packed, 0xff), packed)) {
                    mstore(o, packed)
                    n := and(0xff, packed)
                    i := 0x1f
                    if iszero(gt(n, i)) { break }
                }
                mstore(0x00, $.slot)
                for { let p := keccak256(0x00, 0x20) } 1 {} {
                    mstore(add(o, i), sload(add(p, shr(5, i))))
                    i := add(i, 0x20)
                    if iszero(lt(i, n)) { break }
                }
                break
            }
            mstore(result, n) // Store the length of the memory.
            mstore(add(o, n), 0) // Zeroize the slot after the bytes.
            mstore(0x40, add(add(o, n), 0x20)) // Allocate memory.
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                      BYTES OPERATIONS                      */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Returns `subject` all occurrences of `needle` replaced with `replacement`.
    function replace(bytes memory subject, bytes memory needle, bytes memory replacement)
        internal
        pure
        returns (bytes memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let needleLen := mload(needle)
            let replacementLen := mload(replacement)
            let d := sub(result, subject) // Memory difference.
            let i := add(subject, 0x20) // Subject bytes pointer.
            mstore(0x00, add(i, mload(subject))) // End of subject.
            if iszero(gt(needleLen, mload(subject))) {
                let subjectSearchEnd := add(sub(mload(0x00), needleLen), 1)
                let h := 0 // The hash of `needle`.
                if iszero(lt(needleLen, 0x20)) { h := keccak256(add(needle, 0x20), needleLen) }
                let s := mload(add(needle, 0x20))
                for { let m := shl(3, sub(0x20, and(needleLen, 0x1f))) } 1 {} {
                    let t := mload(i)
                    // Whether the first `needleLen % 32` bytes of `subject` and `needle` matches.
                    if iszero(shr(m, xor(t, s))) {
                        if h {
                            if iszero(eq(keccak256(i, needleLen), h)) {
                                mstore(add(i, d), t)
                                i := add(i, 1)
                                if iszero(lt(i, subjectSearchEnd)) { break }
                                continue
                            }
                        }
                        // Copy the `replacement` one word at a time.
                        for { let j := 0 } 1 {} {
                            mstore(add(add(i, d), j), mload(add(add(replacement, 0x20), j)))
                            j := add(j, 0x20)
                            if iszero(lt(j, replacementLen)) { break }
                        }
                        d := sub(add(d, replacementLen), needleLen)
                        if needleLen {
                            i := add(i, needleLen)
                            if iszero(lt(i, subjectSearchEnd)) { break }
                            continue
                        }
                    }
                    mstore(add(i, d), t)
                    i := add(i, 1)
                    if iszero(lt(i, subjectSearchEnd)) { break }
                }
            }
            let end := mload(0x00)
            let n := add(sub(d, add(result, 0x20)), end)
            // Copy the rest of the bytes one word at a time.
            for {} lt(i, end) { i := add(i, 0x20) } { mstore(add(i, d), mload(i)) }
            let o := add(i, d)
            mstore(o, 0) // Zeroize the slot after the bytes.
            mstore(0x40, add(o, 0x20)) // Allocate memory.
            mstore(result, n) // Store the length.
        }
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from left to right, starting from `from`.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function indexOf(bytes memory subject, bytes memory needle, uint256 from)
        internal
        pure
        returns (uint256 result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result := not(0) // Initialize to `NOT_FOUND`.
            for { let subjectLen := mload(subject) } 1 {} {
                if iszero(mload(needle)) {
                    result := from
                    if iszero(gt(from, subjectLen)) { break }
                    result := subjectLen
                    break
                }
                let needleLen := mload(needle)
                let subjectStart := add(subject, 0x20)

                subject := add(subjectStart, from)
                let end := add(sub(add(subjectStart, subjectLen), needleLen), 1)
                let m := shl(3, sub(0x20, and(needleLen, 0x1f)))
                let s := mload(add(needle, 0x20))

                if iszero(and(lt(subject, end), lt(from, subjectLen))) { break }

                if iszero(lt(needleLen, 0x20)) {
                    for { let h := keccak256(add(needle, 0x20), needleLen) } 1 {} {
                        if iszero(shr(m, xor(mload(subject), s))) {
                            if eq(keccak256(subject, needleLen), h) {
                                result := sub(subject, subjectStart)
                                break
                            }
                        }
                        subject := add(subject, 1)
                        if iszero(lt(subject, end)) { break }
                    }
                    break
                }
                for {} 1 {} {
                    if iszero(shr(m, xor(mload(subject), s))) {
                        result := sub(subject, subjectStart)
                        break
                    }
                    subject := add(subject, 1)
                    if iszero(lt(subject, end)) { break }
                }
                break
            }
        }
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from left to right.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function indexOf(bytes memory subject, bytes memory needle) internal pure returns (uint256) {
        return indexOf(subject, needle, 0);
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from right to left, starting from `from`.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function lastIndexOf(bytes memory subject, bytes memory needle, uint256 from)
        internal
        pure
        returns (uint256 result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            for {} 1 {} {
                result := not(0) // Initialize to `NOT_FOUND`.
                let needleLen := mload(needle)
                if gt(needleLen, mload(subject)) { break }
                let w := result

                let fromMax := sub(mload(subject), needleLen)
                if iszero(gt(fromMax, from)) { from := fromMax }

                let end := add(add(subject, 0x20), w)
                subject := add(add(subject, 0x20), from)
                if iszero(gt(subject, end)) { break }
                // As this function is not too often used,
                // we shall simply use keccak256 for smaller bytecode size.
                for { let h := keccak256(add(needle, 0x20), needleLen) } 1 {} {
                    if eq(keccak256(subject, needleLen), h) {
                        result := sub(subject, add(end, 1))
                        break
                    }
                    subject := add(subject, w) // `sub(subject, 1)`.
                    if iszero(gt(subject, end)) { break }
                }
                break
            }
        }
    }

    /// @dev Returns the byte index of the first location of `needle` in `subject`,
    /// needleing from right to left.
    /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `needle` is not found.
    function lastIndexOf(bytes memory subject, bytes memory needle)
        internal
        pure
        returns (uint256)
    {
        return lastIndexOf(subject, needle, type(uint256).max);
    }

    /// @dev Returns true if `needle` is found in `subject`, false otherwise.
    function contains(bytes memory subject, bytes memory needle) internal pure returns (bool) {
        return indexOf(subject, needle) != NOT_FOUND;
    }

    /// @dev Returns whether `subject` starts with `needle`.
    function startsWith(bytes memory subject, bytes memory needle)
        internal
        pure
        returns (bool result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let n := mload(needle)
            // Just using keccak256 directly is actually cheaper.
            let t := eq(keccak256(add(subject, 0x20), n), keccak256(add(needle, 0x20), n))
            result := lt(gt(n, mload(subject)), t)
        }
    }

    /// @dev Returns whether `subject` ends with `needle`.
    function endsWith(bytes memory subject, bytes memory needle)
        internal
        pure
        returns (bool result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let n := mload(needle)
            let notInRange := gt(n, mload(subject))
            // `subject + 0x20 + max(subject.length - needle.length, 0)`.
            let t := add(add(subject, 0x20), mul(iszero(notInRange), sub(mload(subject), n)))
            // Just using keccak256 directly is actually cheaper.
            result := gt(eq(keccak256(t, n), keccak256(add(needle, 0x20), n)), notInRange)
        }
    }

    /// @dev Returns `subject` repeated `times`.
    function repeat(bytes memory subject, uint256 times)
        internal
        pure
        returns (bytes memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let l := mload(subject) // Subject length.
            if iszero(or(iszero(times), iszero(l))) {
                result := mload(0x40)
                subject := add(subject, 0x20)
                let o := add(result, 0x20)
                for {} 1 {} {
                    // Copy the `subject` one word at a time.
                    for { let j := 0 } 1 {} {
                        mstore(add(o, j), mload(add(subject, j)))
                        j := add(j, 0x20)
                        if iszero(lt(j, l)) { break }
                    }
                    o := add(o, l)
                    times := sub(times, 1)
                    if iszero(times) { break }
                }
                mstore(o, 0) // Zeroize the slot after the bytes.
                mstore(0x40, add(o, 0x20)) // Allocate memory.
                mstore(result, sub(o, add(result, 0x20))) // Store the length.
            }
        }
    }

    /// @dev Returns a copy of `subject` sliced from `start` to `end` (exclusive).
    /// `start` and `end` are byte offsets.
    function slice(bytes memory subject, uint256 start, uint256 end)
        internal
        pure
        returns (bytes memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let l := mload(subject) // Subject length.
            if iszero(gt(l, end)) { end := l }
            if iszero(gt(l, start)) { start := l }
            if lt(start, end) {
                result := mload(0x40)
                let n := sub(end, start)
                let i := add(subject, start)
                let w := not(0x1f)
                // Copy the `subject` one word at a time, backwards.
                for { let j := and(add(n, 0x1f), w) } 1 {} {
                    mstore(add(result, j), mload(add(i, j)))
                    j := add(j, w) // `sub(j, 0x20)`.
                    if iszero(j) { break }
                }
                let o := add(add(result, 0x20), n)
                mstore(o, 0) // Zeroize the slot after the bytes.
                mstore(0x40, add(o, 0x20)) // Allocate memory.
                mstore(result, n) // Store the length.
            }
        }
    }

    /// @dev Returns a copy of `subject` sliced from `start` to the end of the bytes.
    /// `start` is a byte offset.
    function slice(bytes memory subject, uint256 start)
        internal
        pure
        returns (bytes memory result)
    {
        result = slice(subject, start, type(uint256).max);
    }

    /// @dev Returns a copy of `subject` sliced from `start` to `end` (exclusive).
    /// `start` and `end` are byte offsets. Faster than Solidity's native slicing.
    function sliceCalldata(bytes calldata subject, uint256 start, uint256 end)
        internal
        pure
        returns (bytes calldata result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            end := xor(end, mul(xor(end, subject.length), lt(subject.length, end)))
            start := xor(start, mul(xor(start, subject.length), lt(subject.length, start)))
            result.offset := add(subject.offset, start)
            result.length := mul(lt(start, end), sub(end, start))
        }
    }

    /// @dev Returns a copy of `subject` sliced from `start` to the end of the bytes.
    /// `start` is a byte offset. Faster than Solidity's native slicing.
    function sliceCalldata(bytes calldata subject, uint256 start)
        internal
        pure
        returns (bytes calldata result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            start := xor(start, mul(xor(start, subject.length), lt(subject.length, start)))
            result.offset := add(subject.offset, start)
            result.length := mul(lt(start, subject.length), sub(subject.length, start))
        }
    }

    /// @dev Reduces the size of `subject` to `n`.
    /// If `n` is greater than the size of `subject`, this will be a no-op.
    function truncate(bytes memory subject, uint256 n)
        internal
        pure
        returns (bytes memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result := subject
            mstore(mul(lt(n, mload(result)), result), n)
        }
    }

    /// @dev Returns a copy of `subject`, with the length reduced to `n`.
    /// If `n` is greater than the size of `subject`, this will be a no-op.
    function truncatedCalldata(bytes calldata subject, uint256 n)
        internal
        pure
        returns (bytes calldata result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result.offset := subject.offset
            result.length := xor(n, mul(xor(n, subject.length), lt(subject.length, n)))
        }
    }

    /// @dev Returns all the indices of `needle` in `subject`.
    /// The indices are byte offsets.
    function indicesOf(bytes memory subject, bytes memory needle)
        internal
        pure
        returns (uint256[] memory result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            let searchLen := mload(needle)
            if iszero(gt(searchLen, mload(subject))) {
                result := mload(0x40)
                let i := add(subject, 0x20)
                let o := add(result, 0x20)
                let subjectSearchEnd := add(sub(add(i, mload(subject)), searchLen), 1)
                let h := 0 // The hash of `needle`.
                if iszero(lt(searchLen, 0x20)) { h := keccak256(add(needle, 0x20), searchLen) }
                let s := mload(add(needle, 0x20))
                for { let m := shl(3, sub(0x20, and(searchLen, 0x1f))) } 1 {} {
                    let t := mload(i)
                    // Whether the first `searchLen % 32` bytes of `subject` and `needle` matches.
                    if iszero(shr(m, xor(t, s))) {
                        if h {
                            if iszero(eq(keccak256(i, searchLen), h)) {
                                i := add(i, 1)
                                if iszero(lt(i, subjectSearchEnd)) { break }
                                continue
                            }
                        }
                        mstore(o, sub(i, add(subject, 0x20))) // Append to `result`.
                        o := add(o, 0x20)
                        i := add(i, searchLen) // Advance `i` by `searchLen`.
                        if searchLen {
                            if iszero(lt(i, subjectSearchEnd)) { break }
                            continue
                        }
                    }
                    i := add(i, 1)
                    if iszero(lt(i, subjectSearchEnd)) { break }
                }
                mstore(result, shr(5, sub(o, add(result, 0x20)))) // Store the length of `result`.
                // Allocate memory for result.
                // We allocate one more word, so this array can be recycled for {split}.
                mstore(0x40, add(o, 0x20))
            }
        }
    }

    /// @dev Returns a arrays of bytess based on the `delimiter` inside of the `subject` bytes.
    function split(bytes memory subject, bytes memory delimiter)
        internal
        pure
        returns (bytes[] memory result)
    {
        uint256[] memory indices = indicesOf(subject, delimiter);
        /// @solidity memory-safe-assembly
        assembly {
            let w := not(0x1f)
            let indexPtr := add(indices, 0x20)
            let indicesEnd := add(indexPtr, shl(5, add(mload(indices), 1)))
            mstore(add(indicesEnd, w), mload(subject))
            mstore(indices, add(mload(indices), 1))
            for { let prevIndex := 0 } 1 {} {
                let index := mload(indexPtr)
                mstore(indexPtr, 0x60)
                if iszero(eq(index, prevIndex)) {
                    let element := mload(0x40)
                    let l := sub(index, prevIndex)
                    mstore(element, l) // Store the length of the element.
                    // Copy the `subject` one word at a time, backwards.
                    for { let o := and(add(l, 0x1f), w) } 1 {} {
                        mstore(add(element, o), mload(add(add(subject, prevIndex), o)))
                        o := add(o, w) // `sub(o, 0x20)`.
                        if iszero(o) { break }
                    }
                    mstore(add(add(element, 0x20), l), 0) // Zeroize the slot after the bytes.
                    // Allocate memory for the length and the bytes, rounded up to a multiple of 32.
                    mstore(0x40, add(element, and(add(l, 0x3f), w)))
                    mstore(indexPtr, element) // Store the `element` into the array.
                }
                prevIndex := add(index, mload(delimiter))
                indexPtr := add(indexPtr, 0x20)
                if iszero(lt(indexPtr, indicesEnd)) { break }
            }
            result := indices
            if iszero(mload(delimiter)) {
                result := add(indices, 0x20)
                mstore(result, sub(mload(indices), 2))
            }
        }
    }

    /// @dev Returns a concatenated bytes of `a` and `b`.
    /// Cheaper than `bytes.concat()` and does not de-align the free memory pointer.
    function concat(bytes memory a, bytes memory b) internal pure returns (bytes memory result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(0x40)
            let w := not(0x1f)
            let aLen := mload(a)
            // Copy `a` one word at a time, backwards.
            for { let o := and(add(aLen, 0x20), w) } 1 {} {
                mstore(add(result, o), mload(add(a, o)))
                o := add(o, w) // `sub(o, 0x20)`.
                if iszero(o) { break }
            }
            let bLen := mload(b)
            let output := add(result, aLen)
            // Copy `b` one word at a time, backwards.
            for { let o := and(add(bLen, 0x20), w) } 1 {} {
                mstore(add(output, o), mload(add(b, o)))
                o := add(o, w) // `sub(o, 0x20)`.
                if iszero(o) { break }
            }
            let totalLen := add(aLen, bLen)
            let last := add(add(result, 0x20), totalLen)
            mstore(last, 0) // Zeroize the slot after the bytes.
            mstore(result, totalLen) // Store the length.
            mstore(0x40, add(last, 0x20)) // Allocate memory.
        }
    }

    /// @dev Returns whether `a` equals `b`.
    function eq(bytes memory a, bytes memory b) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := eq(keccak256(add(a, 0x20), mload(a)), keccak256(add(b, 0x20), mload(b)))
        }
    }

    /// @dev Returns whether `a` equals `b`, where `b` is a null-terminated small bytes.
    function eqs(bytes memory a, bytes32 b) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            // These should be evaluated on compile time, as far as possible.
            let m := not(shl(7, div(not(iszero(b)), 255))) // `0x7f7f ...`.
            let x := not(or(m, or(b, add(m, and(b, m)))))
            let r := shl(7, iszero(iszero(shr(128, x))))
            r := or(r, shl(6, iszero(iszero(shr(64, shr(r, x))))))
            r := or(r, shl(5, lt(0xffffffff, shr(r, x))))
            r := or(r, shl(4, lt(0xffff, shr(r, x))))
            r := or(r, shl(3, lt(0xff, shr(r, x))))
            // forgefmt: disable-next-item
            result := gt(eq(mload(a), add(iszero(x), xor(31, shr(3, r)))),
                xor(shr(add(8, r), b), shr(add(8, r), mload(add(a, 0x20)))))
        }
    }

    /// @dev Returns 0 if `a == b`, -1 if `a < b`, +1 if `a > b`.
    /// If `a` == b[:a.length]`, and `a.length < b.length`, returns -1.
    function cmp(bytes memory a, bytes memory b) internal pure returns (int256 result) {
        /// @solidity memory-safe-assembly
        assembly {
            let aLen := mload(a)
            let bLen := mload(b)
            let n := and(xor(aLen, mul(xor(aLen, bLen), lt(bLen, aLen))), not(0x1f))
            if n {
                for { let i := 0x20 } 1 {} {
                    let x := mload(add(a, i))
                    let y := mload(add(b, i))
                    if iszero(or(xor(x, y), eq(i, n))) {
                        i := add(i, 0x20)
                        continue
                    }
                    result := sub(gt(x, y), lt(x, y))
                    break
                }
            }
            // forgefmt: disable-next-item
            if iszero(result) {
                let l := 0x201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a090807060504030201
                let x := and(mload(add(add(a, 0x20), n)), shl(shl(3, byte(sub(aLen, n), l)), not(0)))
                let y := and(mload(add(add(b, 0x20), n)), shl(shl(3, byte(sub(bLen, n), l)), not(0)))
                result := sub(gt(x, y), lt(x, y))
                if iszero(result) { result := sub(gt(aLen, bLen), lt(aLen, bLen)) }
            }
        }
    }

    /// @dev Directly returns `a` without copying.
    function directReturn(bytes memory a) internal pure {
        assembly {
            // Assumes that the bytes does not start from the scratch space.
            let retStart := sub(a, 0x20)
            let retUnpaddedSize := add(mload(a), 0x40)
            // Right pad with zeroes. Just in case the bytes is produced
            // by a method that doesn't zero right pad.
            mstore(add(retStart, retUnpaddedSize), 0)
            mstore(retStart, 0x20) // Store the return offset.
            // End the transaction, returning the bytes.
            return(retStart, and(not(0x1f), add(0x1f, retUnpaddedSize)))
        }
    }

    /// @dev Directly returns `a` with minimal copying.
    function directReturn(bytes[] memory a) internal pure {
        assembly {
            let n := mload(a) // `a.length`.
            let o := add(a, 0x20) // Start of elements in `a`.
            let u := a // Highest memory slot.
            let w := not(0x1f)
            for { let i := 0 } iszero(eq(i, n)) { i := add(i, 1) } {
                let c := add(o, shl(5, i)) // Location of pointer to `a[i]`.
                let s := mload(c) // `a[i]`.
                let l := mload(s) // `a[i].length`.
                let r := and(l, 0x1f) // `a[i].length % 32`.
                let z := add(0x20, and(l, w)) // Offset of last word in `a[i]` from `s`.
                // If `s` comes before `o`, or `s` is not zero right padded.
                if iszero(lt(lt(s, o), or(iszero(r), iszero(shl(shl(3, r), mload(add(s, z))))))) {
                    let m := mload(0x40)
                    mstore(m, l) // Copy `a[i].length`.
                    for {} 1 {} {
                        mstore(add(m, z), mload(add(s, z))) // Copy `a[i]`, backwards.
                        z := add(z, w) // `sub(z, 0x20)`.
                        if iszero(z) { break }
                    }
                    let e := add(add(m, 0x20), l)
                    mstore(e, 0) // Zeroize the slot after the copied bytes.
                    mstore(0x40, add(e, 0x20)) // Allocate memory.
                    s := m
                }
                mstore(c, sub(s, o)) // Convert to calldata offset.
                let t := add(l, add(s, 0x20))
                if iszero(lt(t, u)) { u := t }
            }
            let retStart := add(a, w) // Assumes `a` doesn't start from scratch space.
            mstore(retStart, 0x20) // Store the return offset.
            return(retStart, add(0x40, sub(u, retStart))) // End the transaction.
        }
    }

    /// @dev Returns the word at `offset`, without any bounds checks.
    /// To load an address, you can use `address(bytes20(load(a, offset)))`.
    function load(bytes memory a, uint256 offset) internal pure returns (bytes32 result) {
        /// @solidity memory-safe-assembly
        assembly {
            result := mload(add(add(a, 0x20), offset))
        }
    }

    /// @dev Returns the word at `offset`, without any bounds checks.
    /// To load an address, you can use `address(bytes20(loadCalldata(a, offset)))`.
    function loadCalldata(bytes calldata a, uint256 offset)
        internal
        pure
        returns (bytes32 result)
    {
        /// @solidity memory-safe-assembly
        assembly {
            result := calldataload(add(a.offset, offset))
        }
    }

    /// @dev Returns empty calldata bytes. For silencing the compiler.
    function emptyCalldata() internal pure returns (bytes calldata result) {
        /// @solidity memory-safe-assembly
        assembly {
            result.length := 0
        }
    }
}

File 12 of 36 : LibBit.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

/// @notice Library for bit twiddling and boolean operations.
/// @author Solady (https://github.com/vectorized/solady/blob/main/src/utils/LibBit.sol)
/// @author Inspired by (https://graphics.stanford.edu/~seander/bithacks.html)
library LibBit {
    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                  BIT TWIDDLING OPERATIONS                  */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    /// @dev Find last set.
    /// Returns the index of the most significant bit of `x`,
    /// counting from the least significant bit position.
    /// If `x` is zero, returns 256.
    function fls(uint256 x) internal pure returns (uint256 r) {
        /// @solidity memory-safe-assembly
        assembly {
            r := or(shl(8, iszero(x)), shl(7, lt(0xffffffffffffffffffffffffffffffff, x)))
            r := or(r, shl(6, lt(0xffffffffffffffff, shr(r, x))))
            r := or(r, shl(5, lt(0xffffffff, shr(r, x))))
            r := or(r, shl(4, lt(0xffff, shr(r, x))))
            r := or(r, shl(3, lt(0xff, shr(r, x))))
            // forgefmt: disable-next-item
            r := or(r, byte(and(0x1f, shr(shr(r, x), 0x8421084210842108cc6318c6db6d54be)),
                0x0706060506020504060203020504030106050205030304010505030400000000))
        }
    }

    /// @dev Count leading zeros.
    /// Returns the number of zeros preceding the most significant one bit.
    /// If `x` is zero, returns 256.
    function clz(uint256 x) internal pure returns (uint256 r) {
        /// @solidity memory-safe-assembly
        assembly {
            r := shl(7, lt(0xffffffffffffffffffffffffffffffff, x))
            r := or(r, shl(6, lt(0xffffffffffffffff, shr(r, x))))
            r := or(r, shl(5, lt(0xffffffff, shr(r, x))))
            r := or(r, shl(4, lt(0xffff, shr(r, x))))
            r := or(r, shl(3, lt(0xff, shr(r, x))))
            // forgefmt: disable-next-item
            r := add(xor(r, byte(and(0x1f, shr(shr(r, x), 0x8421084210842108cc6318c6db6d54be)),
                0xf8f9f9faf9fdfafbf9fdfcfdfafbfcfef9fafdfafcfcfbfefafafcfbffffffff)), iszero(x))
        }
    }

    /// @dev Find first set.
    /// Returns the index of the least significant bit of `x`,
    /// counting from the least significant bit position.
    /// If `x` is zero, returns 256.
    /// Equivalent to `ctz` (count trailing zeros), which gives
    /// the number of zeros following the least significant one bit.
    function ffs(uint256 x) internal pure returns (uint256 r) {
        /// @solidity memory-safe-assembly
        assembly {
            // Isolate the least significant bit.
            x := and(x, add(not(x), 1))
            // For the upper 3 bits of the result, use a De Bruijn-like lookup.
            // Credit to adhusson: https://blog.adhusson.com/cheap-find-first-set-evm/
            // forgefmt: disable-next-item
            r := shl(5, shr(252, shl(shl(2, shr(250, mul(x,
                0xb6db6db6ddddddddd34d34d349249249210842108c6318c639ce739cffffffff))),
                0x8040405543005266443200005020610674053026020000107506200176117077)))
            // For the lower 5 bits of the result, use a De Bruijn lookup.
            // forgefmt: disable-next-item
            r := or(r, byte(and(div(0xd76453e0, shr(r, x)), 0x1f),
                0x001f0d1e100c1d070f090b19131c1706010e11080a1a141802121b1503160405))
        }
    }

    /// @dev Returns the number of set bits in `x`.
    function popCount(uint256 x) internal pure returns (uint256 c) {
        /// @solidity memory-safe-assembly
        assembly {
            let max := not(0)
            let isMax := eq(x, max)
            x := sub(x, and(shr(1, x), div(max, 3)))
            x := add(and(x, div(max, 5)), and(shr(2, x), div(max, 5)))
            x := and(add(x, shr(4, x)), div(max, 17))
            c := or(shl(8, isMax), shr(248, mul(x, div(max, 255))))
        }
    }

    /// @dev Returns whether `x` is a power of 2.
    function isPo2(uint256 x) internal pure returns (bool result) {
        /// @solidity memory-safe-assembly
        assembly {
            // Equivalent to `x && !(x & (x - 1))`.
            result := iszero(add(and(x, sub(x, 1)), iszero(x)))
        }
    }

    /// @dev Returns `x` reversed at the bit level.
    function reverseBits(uint256 x) internal pure returns (uint256 r) {
        uint256 m0 = 0x0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f0f;
        uint256 m1 = m0 ^ (m0 << 2);
        uint256 m2 = m1 ^ (m1 << 1);
        r = reverseBytes(x);
        r = (m2 & (r >> 1)) | ((m2 & r) << 1);
        r = (m1 & (r >> 2)) | ((m1 & r) << 2);
        r = (m0 & (r >> 4)) | ((m0 & r) << 4);
    }

    /// @dev Returns `x` reversed at the byte level.
    function reverseBytes(uint256 x) internal pure returns (uint256 r) {
        unchecked {
            // Computing masks on-the-fly reduces bytecode size by about 200 bytes.
            uint256 m0 = 0x100000000000000000000000000000001 * (~toUint(x == uint256(0)) >> 192);
            uint256 m1 = m0 ^ (m0 << 32);
            uint256 m2 = m1 ^ (m1 << 16);
            uint256 m3 = m2 ^ (m2 << 8);
            r = (m3 & (x >> 8)) | ((m3 & x) << 8);
            r = (m2 & (r >> 16)) | ((m2 & r) << 16);
            r = (m1 & (r >> 32)) | ((m1 & r) << 32);
            r = (m0 & (r >> 64)) | ((m0 & r) << 64);
            r = (r >> 128) | (r << 128);
        }
    }

    /// @dev Returns the common prefix of `x` and `y` at the bit level.
    function commonBitPrefix(uint256 x, uint256 y) internal pure returns (uint256) {
        unchecked {
            uint256 s = 256 - clz(x ^ y);
            return (x >> s) << s;
        }
    }

    /// @dev Returns the common prefix of `x` and `y` at the nibble level.
    function commonNibblePrefix(uint256 x, uint256 y) internal pure returns (uint256) {
        unchecked {
            uint256 s = (64 - (clz(x ^ y) >> 2)) << 2;
            return (x >> s) << s;
        }
    }

    /// @dev Returns the common prefix of `x` and `y` at the byte level.
    function commonBytePrefix(uint256 x, uint256 y) internal pure returns (uint256) {
        unchecked {
            uint256 s = (32 - (clz(x ^ y) >> 3)) << 3;
            return (x >> s) << s;
        }
    }

    /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
    /*                     BOOLEAN OPERATIONS                     */
    /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/

    // A Solidity bool on the stack or memory is represented as a 256-bit word.
    // Non-zero values are true, zero is false.
    // A clean bool is either 0 (false) or 1 (true) under the hood.
    // Usually, if not always, the bool result of a regular Solidity expression,
    // or the argument of a public/external function will be a clean bool.
    // You can usually use the raw variants for more performance.
    // If uncertain, test (best with exact compiler settings).
    // Or use the non-raw variants (compiler can sometimes optimize out the double `iszero`s).

    /// @dev Returns `x & y`. Inputs must be clean.
    function rawAnd(bool x, bool y) internal pure returns (bool z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := and(x, y)
        }
    }

    /// @dev Returns `x & y`.
    function and(bool x, bool y) internal pure returns (bool z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := and(iszero(iszero(x)), iszero(iszero(y)))
        }
    }

    /// @dev Returns `x | y`. Inputs must be clean.
    function rawOr(bool x, bool y) internal pure returns (bool z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := or(x, y)
        }
    }

    /// @dev Returns `x | y`.
    function or(bool x, bool y) internal pure returns (bool z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := or(iszero(iszero(x)), iszero(iszero(y)))
        }
    }

    /// @dev Returns 1 if `b` is true, else 0. Input must be clean.
    function rawToUint(bool b) internal pure returns (uint256 z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := b
        }
    }

    /// @dev Returns 1 if `b` is true, else 0.
    function toUint(bool b) internal pure returns (uint256 z) {
        /// @solidity memory-safe-assembly
        assembly {
            z := iszero(iszero(b))
        }
    }
}

File 13 of 36 : Strings.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (utils/Strings.sol)

pragma solidity ^0.8.0;

import "./math/Math.sol";

/**
 * @dev String operations.
 */
library Strings {
    bytes16 private constant _SYMBOLS = "0123456789abcdef";
    uint8 private constant _ADDRESS_LENGTH = 20;

    /**
     * @dev Converts a `uint256` to its ASCII `string` decimal representation.
     */
    function toString(uint256 value) internal pure returns (string memory) {
        unchecked {
            uint256 length = Math.log10(value) + 1;
            string memory buffer = new string(length);
            uint256 ptr;
            /// @solidity memory-safe-assembly
            assembly {
                ptr := add(buffer, add(32, length))
            }
            while (true) {
                ptr--;
                /// @solidity memory-safe-assembly
                assembly {
                    mstore8(ptr, byte(mod(value, 10), _SYMBOLS))
                }
                value /= 10;
                if (value == 0) break;
            }
            return buffer;
        }
    }

    /**
     * @dev Converts a `uint256` to its ASCII `string` hexadecimal representation.
     */
    function toHexString(uint256 value) internal pure returns (string memory) {
        unchecked {
            return toHexString(value, Math.log256(value) + 1);
        }
    }

    /**
     * @dev Converts a `uint256` to its ASCII `string` hexadecimal representation with fixed length.
     */
    function toHexString(uint256 value, uint256 length) internal pure returns (string memory) {
        bytes memory buffer = new bytes(2 * length + 2);
        buffer[0] = "0";
        buffer[1] = "x";
        for (uint256 i = 2 * length + 1; i > 1; --i) {
            buffer[i] = _SYMBOLS[value & 0xf];
            value >>= 4;
        }
        require(value == 0, "Strings: hex length insufficient");
        return string(buffer);
    }

    /**
     * @dev Converts an `address` with fixed length of 20 bytes to its not checksummed ASCII `string` hexadecimal representation.
     */
    function toHexString(address addr) internal pure returns (string memory) {
        return toHexString(uint256(uint160(addr)), _ADDRESS_LENGTH);
    }
}

File 14 of 36 : IAccessControl.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (access/IAccessControl.sol)

pragma solidity ^0.8.0;

/**
 * @dev External interface of AccessControl declared to support ERC165 detection.
 */
interface IAccessControl {
    /**
     * @dev Emitted when `newAdminRole` is set as ``role``'s admin role, replacing `previousAdminRole`
     *
     * `DEFAULT_ADMIN_ROLE` is the starting admin for all roles, despite
     * {RoleAdminChanged} not being emitted signaling this.
     *
     * _Available since v3.1._
     */
    event RoleAdminChanged(bytes32 indexed role, bytes32 indexed previousAdminRole, bytes32 indexed newAdminRole);

    /**
     * @dev Emitted when `account` is granted `role`.
     *
     * `sender` is the account that originated the contract call, an admin role
     * bearer except when using {AccessControl-_setupRole}.
     */
    event RoleGranted(bytes32 indexed role, address indexed account, address indexed sender);

    /**
     * @dev Emitted when `account` is revoked `role`.
     *
     * `sender` is the account that originated the contract call:
     *   - if using `revokeRole`, it is the admin role bearer
     *   - if using `renounceRole`, it is the role bearer (i.e. `account`)
     */
    event RoleRevoked(bytes32 indexed role, address indexed account, address indexed sender);

    /**
     * @dev Returns `true` if `account` has been granted `role`.
     */
    function hasRole(bytes32 role, address account) external view returns (bool);

    /**
     * @dev Returns the admin role that controls `role`. See {grantRole} and
     * {revokeRole}.
     *
     * To change a role's admin, use {AccessControl-_setRoleAdmin}.
     */
    function getRoleAdmin(bytes32 role) external view returns (bytes32);

    /**
     * @dev Grants `role` to `account`.
     *
     * If `account` had not been already granted `role`, emits a {RoleGranted}
     * event.
     *
     * Requirements:
     *
     * - the caller must have ``role``'s admin role.
     */
    function grantRole(bytes32 role, address account) external;

    /**
     * @dev Revokes `role` from `account`.
     *
     * If `account` had been granted `role`, emits a {RoleRevoked} event.
     *
     * Requirements:
     *
     * - the caller must have ``role``'s admin role.
     */
    function revokeRole(bytes32 role, address account) external;

    /**
     * @dev Revokes `role` from the calling account.
     *
     * Roles are often managed via {grantRole} and {revokeRole}: this function's
     * purpose is to provide a mechanism for accounts to lose their privileges
     * if they are compromised (such as when a trusted device is misplaced).
     *
     * If the calling account had been granted `role`, emits a {RoleRevoked}
     * event.
     *
     * Requirements:
     *
     * - the caller must be `account`.
     */
    function renounceRole(bytes32 role, address account) external;
}

File 15 of 36 : Context.sol
// 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;
    }
}

File 16 of 36 : ERC165.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/introspection/ERC165.sol)

pragma solidity ^0.8.0;

import "./IERC165.sol";

/**
 * @dev Implementation of the {IERC165} interface.
 *
 * Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check
 * for the additional interface id that will be supported. For example:
 *
 * ```solidity
 * function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
 *     return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId);
 * }
 * ```
 *
 * Alternatively, {ERC165Storage} provides an easier to use but more expensive implementation.
 */
abstract contract ERC165 is IERC165 {
    /**
     * @dev See {IERC165-supportsInterface}.
     */
    function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
        return interfaceId == type(IERC165).interfaceId;
    }
}

File 17 of 36 : ERC2981.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.7.0) (token/common/ERC2981.sol)

pragma solidity ^0.8.0;

import "../../interfaces/IERC2981.sol";
import "../../utils/introspection/ERC165.sol";

/**
 * @dev Implementation of the NFT Royalty Standard, a standardized way to retrieve royalty payment information.
 *
 * Royalty information can be specified globally for all token ids via {_setDefaultRoyalty}, and/or individually for
 * specific token ids via {_setTokenRoyalty}. The latter takes precedence over the first.
 *
 * Royalty is specified as a fraction of sale price. {_feeDenominator} is overridable but defaults to 10000, meaning the
 * fee is specified in basis points by default.
 *
 * IMPORTANT: ERC-2981 only specifies a way to signal royalty information and does not enforce its payment. See
 * https://eips.ethereum.org/EIPS/eip-2981#optional-royalty-payments[Rationale] in the EIP. Marketplaces are expected to
 * voluntarily pay royalties together with sales, but note that this standard is not yet widely supported.
 *
 * _Available since v4.5._
 */
abstract contract ERC2981 is IERC2981, ERC165 {
    struct RoyaltyInfo {
        address receiver;
        uint96 royaltyFraction;
    }

    RoyaltyInfo private _defaultRoyaltyInfo;
    mapping(uint256 => RoyaltyInfo) private _tokenRoyaltyInfo;

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

    /**
     * @inheritdoc IERC2981
     */
    function royaltyInfo(uint256 _tokenId, uint256 _salePrice) public view virtual override returns (address, uint256) {
        RoyaltyInfo memory royalty = _tokenRoyaltyInfo[_tokenId];

        if (royalty.receiver == address(0)) {
            royalty = _defaultRoyaltyInfo;
        }

        uint256 royaltyAmount = (_salePrice * royalty.royaltyFraction) / _feeDenominator();

        return (royalty.receiver, royaltyAmount);
    }

    /**
     * @dev The denominator with which to interpret the fee set in {_setTokenRoyalty} and {_setDefaultRoyalty} as a
     * fraction of the sale price. Defaults to 10000 so fees are expressed in basis points, but may be customized by an
     * override.
     */
    function _feeDenominator() internal pure virtual returns (uint96) {
        return 10000;
    }

    /**
     * @dev Sets the royalty information that all ids in this contract will default to.
     *
     * Requirements:
     *
     * - `receiver` cannot be the zero address.
     * - `feeNumerator` cannot be greater than the fee denominator.
     */
    function _setDefaultRoyalty(address receiver, uint96 feeNumerator) internal virtual {
        require(feeNumerator <= _feeDenominator(), "ERC2981: royalty fee will exceed salePrice");
        require(receiver != address(0), "ERC2981: invalid receiver");

        _defaultRoyaltyInfo = RoyaltyInfo(receiver, feeNumerator);
    }

    /**
     * @dev Removes default royalty information.
     */
    function _deleteDefaultRoyalty() internal virtual {
        delete _defaultRoyaltyInfo;
    }

    /**
     * @dev Sets the royalty information for a specific token id, overriding the global default.
     *
     * Requirements:
     *
     * - `receiver` cannot be the zero address.
     * - `feeNumerator` cannot be greater than the fee denominator.
     */
    function _setTokenRoyalty(
        uint256 tokenId,
        address receiver,
        uint96 feeNumerator
    ) internal virtual {
        require(feeNumerator <= _feeDenominator(), "ERC2981: royalty fee will exceed salePrice");
        require(receiver != address(0), "ERC2981: Invalid parameters");

        _tokenRoyaltyInfo[tokenId] = RoyaltyInfo(receiver, feeNumerator);
    }

    /**
     * @dev Resets royalty information for the token id back to the global default.
     */
    function _resetTokenRoyalty(uint256 tokenId) internal virtual {
        delete _tokenRoyaltyInfo[tokenId];
    }
}

File 18 of 36 : ERC1155OpenZeppelin.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.4;

import "../../access/OwnablePermissions.sol";
import "@openzeppelin/contracts/token/ERC1155/ERC1155.sol";

abstract contract ERC1155OpenZeppelinBase is ERC1155 {

}

abstract contract ERC1155OpenZeppelin is ERC1155OpenZeppelinBase {
    constructor(string memory uri_) ERC1155(uri_) {}
}

abstract contract ERC1155OpenZeppelinInitializable is OwnablePermissions, ERC1155OpenZeppelinBase {

    error ERC1155OpenZeppelinInitializable__AlreadyInitializedERC1155();

    bool private _erc1155Initialized;

    function initializeERC1155(string memory uri_) public {
        _requireCallerIsContractOwner();

        if(_erc1155Initialized) {
            revert ERC1155OpenZeppelinInitializable__AlreadyInitializedERC1155();
        }

        _erc1155Initialized = true;

        _setURI(uri_);
    }
}

File 19 of 36 : CreatorTokenBase.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "../access/OwnablePermissions.sol";
import "../interfaces/ICreatorToken.sol";
import "../interfaces/ICreatorTokenTransferValidator.sol";
import "../utils/TransferValidation.sol";
import "@openzeppelin/contracts/interfaces/IERC165.sol";

/**
 * @title CreatorTokenBase
 * @author Limit Break, Inc.
 * @notice CreatorTokenBase is an abstract contract that provides basic functionality for managing token 
 * transfer policies through an implementation of ICreatorTokenTransferValidator. This contract is intended to be used
 * as a base for creator-specific token contracts, enabling customizable transfer restrictions and security policies.
 *
 * <h4>Features:</h4>
 * <ul>Ownable: This contract can have an owner who can set and update the transfer validator.</ul>
 * <ul>TransferValidation: Implements the basic token transfer validation interface.</ul>
 * <ul>ICreatorToken: Implements the interface for creator tokens, providing view functions for token security policies.</ul>
 *
 * <h4>Benefits:</h4>
 * <ul>Provides a flexible and modular way to implement custom token transfer restrictions and security policies.</ul>
 * <ul>Allows creators to enforce policies such as whitelisted operators and permitted contract receivers.</ul>
 * <ul>Can be easily integrated into other token contracts as a base contract.</ul>
 *
 * <h4>Intended Usage:</h4>
 * <ul>Use as a base contract for creator token implementations that require advanced transfer restrictions and 
 *   security policies.</ul>
 * <ul>Set and update the ICreatorTokenTransferValidator implementation contract to enforce desired policies for the 
 *   creator token.</ul>
 */
abstract contract CreatorTokenBase is OwnablePermissions, TransferValidation, ICreatorToken {
    
    error CreatorTokenBase__InvalidTransferValidatorContract();
    error CreatorTokenBase__SetTransferValidatorFirst();

    address public constant DEFAULT_TRANSFER_VALIDATOR = address(0x0000721C310194CcfC01E523fc93C9cCcFa2A0Ac);
    TransferSecurityLevels public constant DEFAULT_TRANSFER_SECURITY_LEVEL = TransferSecurityLevels.One;
    uint120 public constant DEFAULT_OPERATOR_WHITELIST_ID = uint120(1);

    ICreatorTokenTransferValidator private transferValidator;

    /**
     * @notice Allows the contract owner to set the transfer validator to the official validator contract
     *         and set the security policy to the recommended default settings.
     * @dev    May be overridden to change the default behavior of an individual collection.
     */
    function setToDefaultSecurityPolicy() public virtual {
        _requireCallerIsContractOwner();
        setTransferValidator(DEFAULT_TRANSFER_VALIDATOR);
        ICreatorTokenTransferValidator(DEFAULT_TRANSFER_VALIDATOR).setTransferSecurityLevelOfCollection(address(this), DEFAULT_TRANSFER_SECURITY_LEVEL);
        ICreatorTokenTransferValidator(DEFAULT_TRANSFER_VALIDATOR).setOperatorWhitelistOfCollection(address(this), DEFAULT_OPERATOR_WHITELIST_ID);
    }

    /**
     * @notice Allows the contract owner to set the transfer validator to a custom validator contract
     *         and set the security policy to their own custom settings.
     */
    function setToCustomValidatorAndSecurityPolicy(
        address validator, 
        TransferSecurityLevels level, 
        uint120 operatorWhitelistId, 
        uint120 permittedContractReceiversAllowlistId) public {
        _requireCallerIsContractOwner();

        setTransferValidator(validator);

        ICreatorTokenTransferValidator(validator).
            setTransferSecurityLevelOfCollection(address(this), level);

        ICreatorTokenTransferValidator(validator).
            setOperatorWhitelistOfCollection(address(this), operatorWhitelistId);

        ICreatorTokenTransferValidator(validator).
            setPermittedContractReceiverAllowlistOfCollection(address(this), permittedContractReceiversAllowlistId);
    }

    /**
     * @notice Allows the contract owner to set the security policy to their own custom settings.
     * @dev    Reverts if the transfer validator has not been set.
     */
    function setToCustomSecurityPolicy(
        TransferSecurityLevels level, 
        uint120 operatorWhitelistId, 
        uint120 permittedContractReceiversAllowlistId) public {
        _requireCallerIsContractOwner();

        ICreatorTokenTransferValidator validator = getTransferValidator();
        if (address(validator) == address(0)) {
            revert CreatorTokenBase__SetTransferValidatorFirst();
        }

        validator.setTransferSecurityLevelOfCollection(address(this), level);
        validator.setOperatorWhitelistOfCollection(address(this), operatorWhitelistId);
        validator.setPermittedContractReceiverAllowlistOfCollection(address(this), permittedContractReceiversAllowlistId);
    }

    /**
     * @notice Sets the transfer validator for the token contract.
     *
     * @dev    Throws when provided validator contract is not the zero address and doesn't support 
     *         the ICreatorTokenTransferValidator interface. 
     * @dev    Throws when the caller is not the contract owner.
     *
     * @dev    <h4>Postconditions:</h4>
     *         1. The transferValidator address is updated.
     *         2. The `TransferValidatorUpdated` event is emitted.
     *
     * @param transferValidator_ The address of the transfer validator contract.
     */
    function setTransferValidator(address transferValidator_) public {
        _requireCallerIsContractOwner();

        bool isValidTransferValidator = false;

        if(transferValidator_.code.length > 0) {
            try IERC165(transferValidator_).supportsInterface(type(ICreatorTokenTransferValidator).interfaceId) 
                returns (bool supportsInterface) {
                isValidTransferValidator = supportsInterface;
            } catch {}
        }

        if(transferValidator_ != address(0) && !isValidTransferValidator) {
            revert CreatorTokenBase__InvalidTransferValidatorContract();
        }

        emit TransferValidatorUpdated(address(transferValidator), transferValidator_);

        transferValidator = ICreatorTokenTransferValidator(transferValidator_);
    }

    /**
     * @notice Returns the transfer validator contract address for this token contract.
     */
    function getTransferValidator() public view override returns (ICreatorTokenTransferValidator) {
        return transferValidator;
    }

    /**
     * @notice Returns the security policy for this token contract, which includes:
     *         Transfer security level, operator whitelist id, permitted contract receiver allowlist id.
     */
    function getSecurityPolicy() public view override returns (CollectionSecurityPolicy memory) {
        if (address(transferValidator) != address(0)) {
            return transferValidator.getCollectionSecurityPolicy(address(this));
        }

        return CollectionSecurityPolicy({
            transferSecurityLevel: TransferSecurityLevels.Zero,
            operatorWhitelistId: 0,
            permittedContractReceiversId: 0
        });
    }

    /**
     * @notice Returns the list of all whitelisted operators for this token contract.
     * @dev    This can be an expensive call and should only be used in view-only functions.
     */
    function getWhitelistedOperators() public view override returns (address[] memory) {
        if (address(transferValidator) != address(0)) {
            return transferValidator.getWhitelistedOperators(
                transferValidator.getCollectionSecurityPolicy(address(this)).operatorWhitelistId);
        }

        return new address[](0);
    }

    /**
     * @notice Returns the list of permitted contract receivers for this token contract.
     * @dev    This can be an expensive call and should only be used in view-only functions.
     */
    function getPermittedContractReceivers() public view override returns (address[] memory) {
        if (address(transferValidator) != address(0)) {
            return transferValidator.getPermittedContractReceivers(
                transferValidator.getCollectionSecurityPolicy(address(this)).permittedContractReceiversId);
        }

        return new address[](0);
    }

    /**
     * @notice Checks if an operator is whitelisted for this token contract.
     * @param operator The address of the operator to check.
     */
    function isOperatorWhitelisted(address operator) public view override returns (bool) {
        if (address(transferValidator) != address(0)) {
            return transferValidator.isOperatorWhitelisted(
                transferValidator.getCollectionSecurityPolicy(address(this)).operatorWhitelistId, operator);
        }

        return false;
    }

    /**
     * @notice Checks if a contract receiver is permitted for this token contract.
     * @param receiver The address of the receiver to check.
     */
    function isContractReceiverPermitted(address receiver) public view override returns (bool) {
        if (address(transferValidator) != address(0)) {
            return transferValidator.isContractReceiverPermitted(
                transferValidator.getCollectionSecurityPolicy(address(this)).permittedContractReceiversId, receiver);
        }

        return false;
    }

    /**
     * @notice Determines if a transfer is allowed based on the token contract's security policy.  Use this function
     *         to simulate whether or not a transfer made by the specified `caller` from the `from` address to the `to`
     *         address would be allowed by this token's security policy.
     *
     * @notice This function only checks the security policy restrictions and does not check whether token ownership
     *         or approvals are in place. 
     *
     * @param caller The address of the simulated caller.
     * @param from   The address of the sender.
     * @param to     The address of the receiver.
     * @return       True if the transfer is allowed, false otherwise.
     */
    function isTransferAllowed(address caller, address from, address to) public view override returns (bool) {
        if (address(transferValidator) != address(0)) {
            try transferValidator.applyCollectionTransferPolicy(caller, from, to) {
                return true;
            } catch {
                return false;
            }
        }
        return true;
    }

    /**
     * @dev Pre-validates a token transfer, reverting if the transfer is not allowed by this token's security policy.
     *      Inheriting contracts are responsible for overriding the _beforeTokenTransfer function, or its equivalent
     *      and calling _validateBeforeTransfer so that checks can be properly applied during token transfers.
     *
     * @dev Throws when the transfer doesn't comply with the collection's transfer policy, if the transferValidator is
     *      set to a non-zero address.
     *
     * @param caller  The address of the caller.
     * @param from    The address of the sender.
     * @param to      The address of the receiver.
     */
    function _preValidateTransfer(
        address caller, 
        address from, 
        address to, 
        uint256 /*tokenId*/, 
        uint256 /*value*/) internal virtual override {
        if (address(transferValidator) != address(0)) {
            transferValidator.applyCollectionTransferPolicy(caller, from, to);
        }
    }
}

File 20 of 36 : Math.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (utils/math/Math.sol)

pragma solidity ^0.8.0;

/**
 * @dev Standard math utilities missing in the Solidity language.
 */
library Math {
    enum Rounding {
        Down, // Toward negative infinity
        Up, // Toward infinity
        Zero // Toward zero
    }

    /**
     * @dev Returns the largest of two numbers.
     */
    function max(uint256 a, uint256 b) internal pure returns (uint256) {
        return a > b ? a : b;
    }

    /**
     * @dev Returns the smallest of two numbers.
     */
    function min(uint256 a, uint256 b) internal pure returns (uint256) {
        return a < b ? a : b;
    }

    /**
     * @dev Returns the average of two numbers. The result is rounded towards
     * zero.
     */
    function average(uint256 a, uint256 b) internal pure returns (uint256) {
        // (a + b) / 2 can overflow.
        return (a & b) + (a ^ b) / 2;
    }

    /**
     * @dev Returns the ceiling of the division of two numbers.
     *
     * This differs from standard division with `/` in that it rounds up instead
     * of rounding down.
     */
    function ceilDiv(uint256 a, uint256 b) internal pure returns (uint256) {
        // (a + b - 1) / b can overflow on addition, so we distribute.
        return a == 0 ? 0 : (a - 1) / b + 1;
    }

    /**
     * @notice Calculates floor(x * y / denominator) with full precision. Throws if result overflows a uint256 or denominator == 0
     * @dev Original credit to Remco Bloemen under MIT license (https://xn--2-umb.com/21/muldiv)
     * with further edits by Uniswap Labs also under MIT license.
     */
    function mulDiv(
        uint256 x,
        uint256 y,
        uint256 denominator
    ) internal pure returns (uint256 result) {
        unchecked {
            // 512-bit multiply [prod1 prod0] = x * y. Compute the product mod 2^256 and mod 2^256 - 1, then use
            // use the Chinese Remainder Theorem to reconstruct the 512 bit result. The result is stored in two 256
            // variables such that product = prod1 * 2^256 + prod0.
            uint256 prod0; // Least significant 256 bits of the product
            uint256 prod1; // Most significant 256 bits of the product
            assembly {
                let mm := mulmod(x, y, not(0))
                prod0 := mul(x, y)
                prod1 := sub(sub(mm, prod0), lt(mm, prod0))
            }

            // Handle non-overflow cases, 256 by 256 division.
            if (prod1 == 0) {
                return prod0 / denominator;
            }

            // Make sure the result is less than 2^256. Also prevents denominator == 0.
            require(denominator > prod1);

            ///////////////////////////////////////////////
            // 512 by 256 division.
            ///////////////////////////////////////////////

            // Make division exact by subtracting the remainder from [prod1 prod0].
            uint256 remainder;
            assembly {
                // Compute remainder using mulmod.
                remainder := mulmod(x, y, denominator)

                // Subtract 256 bit number from 512 bit number.
                prod1 := sub(prod1, gt(remainder, prod0))
                prod0 := sub(prod0, remainder)
            }

            // Factor powers of two out of denominator and compute largest power of two divisor of denominator. Always >= 1.
            // See https://cs.stackexchange.com/q/138556/92363.

            // Does not overflow because the denominator cannot be zero at this stage in the function.
            uint256 twos = denominator & (~denominator + 1);
            assembly {
                // Divide denominator by twos.
                denominator := div(denominator, twos)

                // Divide [prod1 prod0] by twos.
                prod0 := div(prod0, twos)

                // Flip twos such that it is 2^256 / twos. If twos is zero, then it becomes one.
                twos := add(div(sub(0, twos), twos), 1)
            }

            // Shift in bits from prod1 into prod0.
            prod0 |= prod1 * twos;

            // Invert denominator mod 2^256. Now that denominator is an odd number, it has an inverse modulo 2^256 such
            // that denominator * inv = 1 mod 2^256. Compute the inverse by starting with a seed that is correct for
            // four bits. That is, denominator * inv = 1 mod 2^4.
            uint256 inverse = (3 * denominator) ^ 2;

            // Use the Newton-Raphson iteration to improve the precision. Thanks to Hensel's lifting lemma, this also works
            // in modular arithmetic, doubling the correct bits in each step.
            inverse *= 2 - denominator * inverse; // inverse mod 2^8
            inverse *= 2 - denominator * inverse; // inverse mod 2^16
            inverse *= 2 - denominator * inverse; // inverse mod 2^32
            inverse *= 2 - denominator * inverse; // inverse mod 2^64
            inverse *= 2 - denominator * inverse; // inverse mod 2^128
            inverse *= 2 - denominator * inverse; // inverse mod 2^256

            // Because the division is now exact we can divide by multiplying with the modular inverse of denominator.
            // This will give us the correct result modulo 2^256. Since the preconditions guarantee that the outcome is
            // less than 2^256, this is the final result. We don't need to compute the high bits of the result and prod1
            // is no longer required.
            result = prod0 * inverse;
            return result;
        }
    }

    /**
     * @notice Calculates x * y / denominator with full precision, following the selected rounding direction.
     */
    function mulDiv(
        uint256 x,
        uint256 y,
        uint256 denominator,
        Rounding rounding
    ) internal pure returns (uint256) {
        uint256 result = mulDiv(x, y, denominator);
        if (rounding == Rounding.Up && mulmod(x, y, denominator) > 0) {
            result += 1;
        }
        return result;
    }

    /**
     * @dev Returns the square root of a number. If the number is not a perfect square, the value is rounded down.
     *
     * Inspired by Henry S. Warren, Jr.'s "Hacker's Delight" (Chapter 11).
     */
    function sqrt(uint256 a) internal pure returns (uint256) {
        if (a == 0) {
            return 0;
        }

        // For our first guess, we get the biggest power of 2 which is smaller than the square root of the target.
        //
        // We know that the "msb" (most significant bit) of our target number `a` is a power of 2 such that we have
        // `msb(a) <= a < 2*msb(a)`. This value can be written `msb(a)=2**k` with `k=log2(a)`.
        //
        // This can be rewritten `2**log2(a) <= a < 2**(log2(a) + 1)`
        // → `sqrt(2**k) <= sqrt(a) < sqrt(2**(k+1))`
        // → `2**(k/2) <= sqrt(a) < 2**((k+1)/2) <= 2**(k/2 + 1)`
        //
        // Consequently, `2**(log2(a) / 2)` is a good first approximation of `sqrt(a)` with at least 1 correct bit.
        uint256 result = 1 << (log2(a) >> 1);

        // At this point `result` is an estimation with one bit of precision. We know the true value is a uint128,
        // since it is the square root of a uint256. Newton's method converges quadratically (precision doubles at
        // every iteration). We thus need at most 7 iteration to turn our partial result with one bit of precision
        // into the expected uint128 result.
        unchecked {
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            result = (result + a / result) >> 1;
            return min(result, a / result);
        }
    }

    /**
     * @notice Calculates sqrt(a), following the selected rounding direction.
     */
    function sqrt(uint256 a, Rounding rounding) internal pure returns (uint256) {
        unchecked {
            uint256 result = sqrt(a);
            return result + (rounding == Rounding.Up && result * result < a ? 1 : 0);
        }
    }

    /**
     * @dev Return the log in base 2, rounded down, of a positive value.
     * Returns 0 if given 0.
     */
    function log2(uint256 value) internal pure returns (uint256) {
        uint256 result = 0;
        unchecked {
            if (value >> 128 > 0) {
                value >>= 128;
                result += 128;
            }
            if (value >> 64 > 0) {
                value >>= 64;
                result += 64;
            }
            if (value >> 32 > 0) {
                value >>= 32;
                result += 32;
            }
            if (value >> 16 > 0) {
                value >>= 16;
                result += 16;
            }
            if (value >> 8 > 0) {
                value >>= 8;
                result += 8;
            }
            if (value >> 4 > 0) {
                value >>= 4;
                result += 4;
            }
            if (value >> 2 > 0) {
                value >>= 2;
                result += 2;
            }
            if (value >> 1 > 0) {
                result += 1;
            }
        }
        return result;
    }

    /**
     * @dev Return the log in base 2, following the selected rounding direction, of a positive value.
     * Returns 0 if given 0.
     */
    function log2(uint256 value, Rounding rounding) internal pure returns (uint256) {
        unchecked {
            uint256 result = log2(value);
            return result + (rounding == Rounding.Up && 1 << result < value ? 1 : 0);
        }
    }

    /**
     * @dev Return the log in base 10, rounded down, of a positive value.
     * Returns 0 if given 0.
     */
    function log10(uint256 value) internal pure returns (uint256) {
        uint256 result = 0;
        unchecked {
            if (value >= 10**64) {
                value /= 10**64;
                result += 64;
            }
            if (value >= 10**32) {
                value /= 10**32;
                result += 32;
            }
            if (value >= 10**16) {
                value /= 10**16;
                result += 16;
            }
            if (value >= 10**8) {
                value /= 10**8;
                result += 8;
            }
            if (value >= 10**4) {
                value /= 10**4;
                result += 4;
            }
            if (value >= 10**2) {
                value /= 10**2;
                result += 2;
            }
            if (value >= 10**1) {
                result += 1;
            }
        }
        return result;
    }

    /**
     * @dev Return the log in base 10, following the selected rounding direction, of a positive value.
     * Returns 0 if given 0.
     */
    function log10(uint256 value, Rounding rounding) internal pure returns (uint256) {
        unchecked {
            uint256 result = log10(value);
            return result + (rounding == Rounding.Up && 10**result < value ? 1 : 0);
        }
    }

    /**
     * @dev Return the log in base 256, rounded down, of a positive value.
     * Returns 0 if given 0.
     *
     * Adding one to the result gives the number of pairs of hex symbols needed to represent `value` as a hex string.
     */
    function log256(uint256 value) internal pure returns (uint256) {
        uint256 result = 0;
        unchecked {
            if (value >> 128 > 0) {
                value >>= 128;
                result += 16;
            }
            if (value >> 64 > 0) {
                value >>= 64;
                result += 8;
            }
            if (value >> 32 > 0) {
                value >>= 32;
                result += 4;
            }
            if (value >> 16 > 0) {
                value >>= 16;
                result += 2;
            }
            if (value >> 8 > 0) {
                result += 1;
            }
        }
        return result;
    }

    /**
     * @dev Return the log in base 10, following the selected rounding direction, of a positive value.
     * Returns 0 if given 0.
     */
    function log256(uint256 value, Rounding rounding) internal pure returns (uint256) {
        unchecked {
            uint256 result = log256(value);
            return result + (rounding == Rounding.Up && 1 << (result * 8) < value ? 1 : 0);
        }
    }
}

File 21 of 36 : IERC165.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol)

pragma solidity ^0.8.0;

/**
 * @dev Interface of the ERC165 standard, as defined in the
 * https://eips.ethereum.org/EIPS/eip-165[EIP].
 *
 * Implementers can declare support of contract interfaces, which can then be
 * queried by others ({ERC165Checker}).
 *
 * For an implementation, see {ERC165}.
 */
interface IERC165 {
    /**
     * @dev Returns true if this contract implements the interface defined by
     * `interfaceId`. See the corresponding
     * https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]
     * to learn more about how these ids are created.
     *
     * This function call must use less than 30 000 gas.
     */
    function supportsInterface(bytes4 interfaceId) external view returns (bool);
}

File 22 of 36 : IERC2981.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.6.0) (interfaces/IERC2981.sol)

pragma solidity ^0.8.0;

import "../utils/introspection/IERC165.sol";

/**
 * @dev Interface for the NFT Royalty Standard.
 *
 * A standardized way to retrieve royalty payment information for non-fungible tokens (NFTs) to enable universal
 * support for royalty payments across all NFT marketplaces and ecosystem participants.
 *
 * _Available since v4.5._
 */
interface IERC2981 is IERC165 {
    /**
     * @dev Returns how much royalty is owed and to whom, based on a sale price that may be denominated in any unit of
     * exchange. The royalty amount is denominated and should be paid in that same unit of exchange.
     */
    function royaltyInfo(uint256 tokenId, uint256 salePrice)
        external
        view
        returns (address receiver, uint256 royaltyAmount);
}

File 23 of 36 : OwnablePermissions.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "@openzeppelin/contracts/utils/Context.sol";

abstract contract OwnablePermissions is Context {
    function _requireCallerIsContractOwner() internal view virtual;
}

File 24 of 36 : ERC1155.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (token/ERC1155/ERC1155.sol)

pragma solidity ^0.8.0;

import "./IERC1155.sol";
import "./IERC1155Receiver.sol";
import "./extensions/IERC1155MetadataURI.sol";
import "../../utils/Address.sol";
import "../../utils/Context.sol";
import "../../utils/introspection/ERC165.sol";

/**
 * @dev Implementation of the basic standard multi-token.
 * See https://eips.ethereum.org/EIPS/eip-1155
 * Originally based on code by Enjin: https://github.com/enjin/erc-1155
 *
 * _Available since v3.1._
 */
contract ERC1155 is Context, ERC165, IERC1155, IERC1155MetadataURI {
    using Address for address;

    // Mapping from token ID to account balances
    mapping(uint256 => mapping(address => uint256)) private _balances;

    // Mapping from account to operator approvals
    mapping(address => mapping(address => bool)) private _operatorApprovals;

    // Used as the URI for all token types by relying on ID substitution, e.g. https://token-cdn-domain/{id}.json
    string private _uri;

    /**
     * @dev See {_setURI}.
     */
    constructor(string memory uri_) {
        _setURI(uri_);
    }

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

    /**
     * @dev See {IERC1155MetadataURI-uri}.
     *
     * This implementation returns the same URI for *all* token types. It relies
     * on the token type ID substitution mechanism
     * https://eips.ethereum.org/EIPS/eip-1155#metadata[defined in the EIP].
     *
     * Clients calling this function must replace the `\{id\}` substring with the
     * actual token type ID.
     */
    function uri(uint256) public view virtual override returns (string memory) {
        return _uri;
    }

    /**
     * @dev See {IERC1155-balanceOf}.
     *
     * Requirements:
     *
     * - `account` cannot be the zero address.
     */
    function balanceOf(address account, uint256 id) public view virtual override returns (uint256) {
        require(account != address(0), "ERC1155: address zero is not a valid owner");
        return _balances[id][account];
    }

    /**
     * @dev See {IERC1155-balanceOfBatch}.
     *
     * Requirements:
     *
     * - `accounts` and `ids` must have the same length.
     */
    function balanceOfBatch(address[] memory accounts, uint256[] memory ids)
        public
        view
        virtual
        override
        returns (uint256[] memory)
    {
        require(accounts.length == ids.length, "ERC1155: accounts and ids length mismatch");

        uint256[] memory batchBalances = new uint256[](accounts.length);

        for (uint256 i = 0; i < accounts.length; ++i) {
            batchBalances[i] = balanceOf(accounts[i], ids[i]);
        }

        return batchBalances;
    }

    /**
     * @dev See {IERC1155-setApprovalForAll}.
     */
    function setApprovalForAll(address operator, bool approved) public virtual override {
        _setApprovalForAll(_msgSender(), operator, approved);
    }

    /**
     * @dev See {IERC1155-isApprovedForAll}.
     */
    function isApprovedForAll(address account, address operator) public view virtual override returns (bool) {
        return _operatorApprovals[account][operator];
    }

    /**
     * @dev See {IERC1155-safeTransferFrom}.
     */
    function safeTransferFrom(
        address from,
        address to,
        uint256 id,
        uint256 amount,
        bytes memory data
    ) public virtual override {
        require(
            from == _msgSender() || isApprovedForAll(from, _msgSender()),
            "ERC1155: caller is not token owner or approved"
        );
        _safeTransferFrom(from, to, id, amount, data);
    }

    /**
     * @dev See {IERC1155-safeBatchTransferFrom}.
     */
    function safeBatchTransferFrom(
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) public virtual override {
        require(
            from == _msgSender() || isApprovedForAll(from, _msgSender()),
            "ERC1155: caller is not token owner or approved"
        );
        _safeBatchTransferFrom(from, to, ids, amounts, data);
    }

    /**
     * @dev Transfers `amount` tokens of token type `id` from `from` to `to`.
     *
     * Emits a {TransferSingle} event.
     *
     * Requirements:
     *
     * - `to` cannot be the zero address.
     * - `from` must have a balance of tokens of type `id` of at least `amount`.
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the
     * acceptance magic value.
     */
    function _safeTransferFrom(
        address from,
        address to,
        uint256 id,
        uint256 amount,
        bytes memory data
    ) internal virtual {
        require(to != address(0), "ERC1155: transfer to the zero address");

        address operator = _msgSender();
        uint256[] memory ids = _asSingletonArray(id);
        uint256[] memory amounts = _asSingletonArray(amount);

        _beforeTokenTransfer(operator, from, to, ids, amounts, data);

        uint256 fromBalance = _balances[id][from];
        require(fromBalance >= amount, "ERC1155: insufficient balance for transfer");
        unchecked {
            _balances[id][from] = fromBalance - amount;
        }
        _balances[id][to] += amount;

        emit TransferSingle(operator, from, to, id, amount);

        _afterTokenTransfer(operator, from, to, ids, amounts, data);

        _doSafeTransferAcceptanceCheck(operator, from, to, id, amount, data);
    }

    /**
     * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {_safeTransferFrom}.
     *
     * Emits a {TransferBatch} event.
     *
     * Requirements:
     *
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the
     * acceptance magic value.
     */
    function _safeBatchTransferFrom(
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) internal virtual {
        require(ids.length == amounts.length, "ERC1155: ids and amounts length mismatch");
        require(to != address(0), "ERC1155: transfer to the zero address");

        address operator = _msgSender();

        _beforeTokenTransfer(operator, from, to, ids, amounts, data);

        for (uint256 i = 0; i < ids.length; ++i) {
            uint256 id = ids[i];
            uint256 amount = amounts[i];

            uint256 fromBalance = _balances[id][from];
            require(fromBalance >= amount, "ERC1155: insufficient balance for transfer");
            unchecked {
                _balances[id][from] = fromBalance - amount;
            }
            _balances[id][to] += amount;
        }

        emit TransferBatch(operator, from, to, ids, amounts);

        _afterTokenTransfer(operator, from, to, ids, amounts, data);

        _doSafeBatchTransferAcceptanceCheck(operator, from, to, ids, amounts, data);
    }

    /**
     * @dev Sets a new URI for all token types, by relying on the token type ID
     * substitution mechanism
     * https://eips.ethereum.org/EIPS/eip-1155#metadata[defined in the EIP].
     *
     * By this mechanism, any occurrence of the `\{id\}` substring in either the
     * URI or any of the amounts in the JSON file at said URI will be replaced by
     * clients with the token type ID.
     *
     * For example, the `https://token-cdn-domain/\{id\}.json` URI would be
     * interpreted by clients as
     * `https://token-cdn-domain/000000000000000000000000000000000000000000000000000000000004cce0.json`
     * for token type ID 0x4cce0.
     *
     * See {uri}.
     *
     * Because these URIs cannot be meaningfully represented by the {URI} event,
     * this function emits no events.
     */
    function _setURI(string memory newuri) internal virtual {
        _uri = newuri;
    }

    /**
     * @dev Creates `amount` tokens of token type `id`, and assigns them to `to`.
     *
     * Emits a {TransferSingle} event.
     *
     * Requirements:
     *
     * - `to` cannot be the zero address.
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the
     * acceptance magic value.
     */
    function _mint(
        address to,
        uint256 id,
        uint256 amount,
        bytes memory data
    ) internal virtual {
        require(to != address(0), "ERC1155: mint to the zero address");

        address operator = _msgSender();
        uint256[] memory ids = _asSingletonArray(id);
        uint256[] memory amounts = _asSingletonArray(amount);

        _beforeTokenTransfer(operator, address(0), to, ids, amounts, data);

        _balances[id][to] += amount;
        emit TransferSingle(operator, address(0), to, id, amount);

        _afterTokenTransfer(operator, address(0), to, ids, amounts, data);

        _doSafeTransferAcceptanceCheck(operator, address(0), to, id, amount, data);
    }

    /**
     * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {_mint}.
     *
     * Emits a {TransferBatch} event.
     *
     * Requirements:
     *
     * - `ids` and `amounts` must have the same length.
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the
     * acceptance magic value.
     */
    function _mintBatch(
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) internal virtual {
        require(to != address(0), "ERC1155: mint to the zero address");
        require(ids.length == amounts.length, "ERC1155: ids and amounts length mismatch");

        address operator = _msgSender();

        _beforeTokenTransfer(operator, address(0), to, ids, amounts, data);

        for (uint256 i = 0; i < ids.length; i++) {
            _balances[ids[i]][to] += amounts[i];
        }

        emit TransferBatch(operator, address(0), to, ids, amounts);

        _afterTokenTransfer(operator, address(0), to, ids, amounts, data);

        _doSafeBatchTransferAcceptanceCheck(operator, address(0), to, ids, amounts, data);
    }

    /**
     * @dev Destroys `amount` tokens of token type `id` from `from`
     *
     * Emits a {TransferSingle} event.
     *
     * Requirements:
     *
     * - `from` cannot be the zero address.
     * - `from` must have at least `amount` tokens of token type `id`.
     */
    function _burn(
        address from,
        uint256 id,
        uint256 amount
    ) internal virtual {
        require(from != address(0), "ERC1155: burn from the zero address");

        address operator = _msgSender();
        uint256[] memory ids = _asSingletonArray(id);
        uint256[] memory amounts = _asSingletonArray(amount);

        _beforeTokenTransfer(operator, from, address(0), ids, amounts, "");

        uint256 fromBalance = _balances[id][from];
        require(fromBalance >= amount, "ERC1155: burn amount exceeds balance");
        unchecked {
            _balances[id][from] = fromBalance - amount;
        }

        emit TransferSingle(operator, from, address(0), id, amount);

        _afterTokenTransfer(operator, from, address(0), ids, amounts, "");
    }

    /**
     * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {_burn}.
     *
     * Emits a {TransferBatch} event.
     *
     * Requirements:
     *
     * - `ids` and `amounts` must have the same length.
     */
    function _burnBatch(
        address from,
        uint256[] memory ids,
        uint256[] memory amounts
    ) internal virtual {
        require(from != address(0), "ERC1155: burn from the zero address");
        require(ids.length == amounts.length, "ERC1155: ids and amounts length mismatch");

        address operator = _msgSender();

        _beforeTokenTransfer(operator, from, address(0), ids, amounts, "");

        for (uint256 i = 0; i < ids.length; i++) {
            uint256 id = ids[i];
            uint256 amount = amounts[i];

            uint256 fromBalance = _balances[id][from];
            require(fromBalance >= amount, "ERC1155: burn amount exceeds balance");
            unchecked {
                _balances[id][from] = fromBalance - amount;
            }
        }

        emit TransferBatch(operator, from, address(0), ids, amounts);

        _afterTokenTransfer(operator, from, address(0), ids, amounts, "");
    }

    /**
     * @dev Approve `operator` to operate on all of `owner` tokens
     *
     * Emits an {ApprovalForAll} event.
     */
    function _setApprovalForAll(
        address owner,
        address operator,
        bool approved
    ) internal virtual {
        require(owner != operator, "ERC1155: setting approval status for self");
        _operatorApprovals[owner][operator] = approved;
        emit ApprovalForAll(owner, operator, approved);
    }

    /**
     * @dev Hook that is called before any token transfer. This includes minting
     * and burning, as well as batched variants.
     *
     * The same hook is called on both single and batched variants. For single
     * transfers, the length of the `ids` and `amounts` arrays will be 1.
     *
     * Calling conditions (for each `id` and `amount` pair):
     *
     * - When `from` and `to` are both non-zero, `amount` of ``from``'s tokens
     * of token type `id` will be  transferred to `to`.
     * - When `from` is zero, `amount` tokens of token type `id` will be minted
     * for `to`.
     * - when `to` is zero, `amount` of ``from``'s tokens of token type `id`
     * will be burned.
     * - `from` and `to` are never both zero.
     * - `ids` and `amounts` have the same, non-zero length.
     *
     * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
     */
    function _beforeTokenTransfer(
        address operator,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) internal virtual {}

    /**
     * @dev Hook that is called after any token transfer. This includes minting
     * and burning, as well as batched variants.
     *
     * The same hook is called on both single and batched variants. For single
     * transfers, the length of the `id` and `amount` arrays will be 1.
     *
     * Calling conditions (for each `id` and `amount` pair):
     *
     * - When `from` and `to` are both non-zero, `amount` of ``from``'s tokens
     * of token type `id` will be  transferred to `to`.
     * - When `from` is zero, `amount` tokens of token type `id` will be minted
     * for `to`.
     * - when `to` is zero, `amount` of ``from``'s tokens of token type `id`
     * will be burned.
     * - `from` and `to` are never both zero.
     * - `ids` and `amounts` have the same, non-zero length.
     *
     * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
     */
    function _afterTokenTransfer(
        address operator,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) internal virtual {}

    function _doSafeTransferAcceptanceCheck(
        address operator,
        address from,
        address to,
        uint256 id,
        uint256 amount,
        bytes memory data
    ) private {
        if (to.isContract()) {
            try IERC1155Receiver(to).onERC1155Received(operator, from, id, amount, data) returns (bytes4 response) {
                if (response != IERC1155Receiver.onERC1155Received.selector) {
                    revert("ERC1155: ERC1155Receiver rejected tokens");
                }
            } catch Error(string memory reason) {
                revert(reason);
            } catch {
                revert("ERC1155: transfer to non-ERC1155Receiver implementer");
            }
        }
    }

    function _doSafeBatchTransferAcceptanceCheck(
        address operator,
        address from,
        address to,
        uint256[] memory ids,
        uint256[] memory amounts,
        bytes memory data
    ) private {
        if (to.isContract()) {
            try IERC1155Receiver(to).onERC1155BatchReceived(operator, from, ids, amounts, data) returns (
                bytes4 response
            ) {
                if (response != IERC1155Receiver.onERC1155BatchReceived.selector) {
                    revert("ERC1155: ERC1155Receiver rejected tokens");
                }
            } catch Error(string memory reason) {
                revert(reason);
            } catch {
                revert("ERC1155: transfer to non-ERC1155Receiver implementer");
            }
        }
    }

    function _asSingletonArray(uint256 element) private pure returns (uint256[] memory) {
        uint256[] memory array = new uint256[](1);
        array[0] = element;

        return array;
    }
}

File 25 of 36 : ICreatorToken.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "../interfaces/ICreatorTokenTransferValidator.sol";

interface ICreatorToken {
    event TransferValidatorUpdated(address oldValidator, address newValidator);

    function getTransferValidator() external view returns (ICreatorTokenTransferValidator);
    function getSecurityPolicy() external view returns (CollectionSecurityPolicy memory);
    function getWhitelistedOperators() external view returns (address[] memory);
    function getPermittedContractReceivers() external view returns (address[] memory);
    function isOperatorWhitelisted(address operator) external view returns (bool);
    function isContractReceiverPermitted(address receiver) external view returns (bool);
    function isTransferAllowed(address caller, address from, address to) external view returns (bool);
}

File 26 of 36 : TransferValidation.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "@openzeppelin/contracts/utils/Context.sol";

/**
 * @title TransferValidation
 * @author Limit Break, Inc.
 * @notice A mix-in that can be combined with ERC-721 contracts to provide more granular hooks.
 * Openzeppelin's ERC721 contract only provides hooks for before and after transfer.  This allows
 * developers to validate or customize transfers within the context of a mint, a burn, or a transfer.
 */
abstract contract TransferValidation is Context {
    
    error ShouldNotMintToBurnAddress();

    /// @dev Inheriting contracts should call this function in the _beforeTokenTransfer function to get more granular hooks.
    function _validateBeforeTransfer(address from, address to, uint256 tokenId) internal virtual {
        bool fromZeroAddress = from == address(0);
        bool toZeroAddress = to == address(0);

        if(fromZeroAddress && toZeroAddress) {
            revert ShouldNotMintToBurnAddress();
        } else if(fromZeroAddress) {
            _preValidateMint(_msgSender(), to, tokenId, msg.value);
        } else if(toZeroAddress) {
            _preValidateBurn(_msgSender(), from, tokenId, msg.value);
        } else {
            _preValidateTransfer(_msgSender(), from, to, tokenId, msg.value);
        }
    }

    /// @dev Inheriting contracts should call this function in the _afterTokenTransfer function to get more granular hooks.
    function _validateAfterTransfer(address from, address to, uint256 tokenId) internal virtual {
        bool fromZeroAddress = from == address(0);
        bool toZeroAddress = to == address(0);

        if(fromZeroAddress && toZeroAddress) {
            revert ShouldNotMintToBurnAddress();
        } else if(fromZeroAddress) {
            _postValidateMint(_msgSender(), to, tokenId, msg.value);
        } else if(toZeroAddress) {
            _postValidateBurn(_msgSender(), from, tokenId, msg.value);
        } else {
            _postValidateTransfer(_msgSender(), from, to, tokenId, msg.value);
        }
    }

    /// @dev Optional validation hook that fires before a mint
    function _preValidateMint(address caller, address to, uint256 tokenId, uint256 value) internal virtual {}

    /// @dev Optional validation hook that fires after a mint
    function _postValidateMint(address caller, address to, uint256 tokenId, uint256 value) internal virtual {}

    /// @dev Optional validation hook that fires before a burn
    function _preValidateBurn(address caller, address from, uint256 tokenId, uint256 value) internal virtual {}

    /// @dev Optional validation hook that fires after a burn
    function _postValidateBurn(address caller, address from, uint256 tokenId, uint256 value) internal virtual {}

    /// @dev Optional validation hook that fires before a transfer
    function _preValidateTransfer(address caller, address from, address to, uint256 tokenId, uint256 value) internal virtual {}

    /// @dev Optional validation hook that fires after a transfer
    function _postValidateTransfer(address caller, address from, address to, uint256 tokenId, uint256 value) internal virtual {}
}

File 27 of 36 : IERC165.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (interfaces/IERC165.sol)

pragma solidity ^0.8.0;

import "../utils/introspection/IERC165.sol";

File 28 of 36 : ICreatorTokenTransferValidator.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "./IEOARegistry.sol";
import "./ITransferSecurityRegistry.sol";
import "./ITransferValidator.sol";

interface ICreatorTokenTransferValidator is ITransferSecurityRegistry, ITransferValidator, IEOARegistry {}

File 29 of 36 : IERC1155Receiver.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.5.0) (token/ERC1155/IERC1155Receiver.sol)

pragma solidity ^0.8.0;

import "../../utils/introspection/IERC165.sol";

/**
 * @dev _Available since v3.1._
 */
interface IERC1155Receiver is IERC165 {
    /**
     * @dev Handles the receipt of a single ERC1155 token type. This function is
     * called at the end of a `safeTransferFrom` after the balance has been updated.
     *
     * NOTE: To accept the transfer, this must return
     * `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))`
     * (i.e. 0xf23a6e61, or its own function selector).
     *
     * @param operator The address which initiated the transfer (i.e. msg.sender)
     * @param from The address which previously owned the token
     * @param id The ID of the token being transferred
     * @param value The amount of tokens being transferred
     * @param data Additional data with no specified format
     * @return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` if transfer is allowed
     */
    function onERC1155Received(
        address operator,
        address from,
        uint256 id,
        uint256 value,
        bytes calldata data
    ) external returns (bytes4);

    /**
     * @dev Handles the receipt of a multiple ERC1155 token types. This function
     * is called at the end of a `safeBatchTransferFrom` after the balances have
     * been updated.
     *
     * NOTE: To accept the transfer(s), this must return
     * `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))`
     * (i.e. 0xbc197c81, or its own function selector).
     *
     * @param operator The address which initiated the batch transfer (i.e. msg.sender)
     * @param from The address which previously owned the token
     * @param ids An array containing ids of each token being transferred (order and length must match values array)
     * @param values An array containing amounts of each token being transferred (order and length must match ids array)
     * @param data Additional data with no specified format
     * @return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` if transfer is allowed
     */
    function onERC1155BatchReceived(
        address operator,
        address from,
        uint256[] calldata ids,
        uint256[] calldata values,
        bytes calldata data
    ) external returns (bytes4);
}

File 30 of 36 : IERC1155MetadataURI.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (token/ERC1155/extensions/IERC1155MetadataURI.sol)

pragma solidity ^0.8.0;

import "../IERC1155.sol";

/**
 * @dev Interface of the optional ERC1155MetadataExtension interface, as defined
 * in the https://eips.ethereum.org/EIPS/eip-1155#metadata-extensions[EIP].
 *
 * _Available since v3.1._
 */
interface IERC1155MetadataURI is IERC1155 {
    /**
     * @dev Returns the URI for token type `id`.
     *
     * If the `\{id\}` substring is present in the URI, it must be replaced by
     * clients with the actual token type ID.
     */
    function uri(uint256 id) external view returns (string memory);
}

File 31 of 36 : Address.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (utils/Address.sol)

pragma solidity ^0.8.1;

/**
 * @dev Collection of functions related to the address type
 */
library Address {
    /**
     * @dev Returns true if `account` is a contract.
     *
     * [IMPORTANT]
     * ====
     * It is unsafe to assume that an address for which this function returns
     * false is an externally-owned account (EOA) and not a contract.
     *
     * Among others, `isContract` will return false for the following
     * types of addresses:
     *
     *  - an externally-owned account
     *  - a contract in construction
     *  - an address where a contract will be created
     *  - an address where a contract lived, but was destroyed
     * ====
     *
     * [IMPORTANT]
     * ====
     * You shouldn't rely on `isContract` to protect against flash loan attacks!
     *
     * Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets
     * like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract
     * constructor.
     * ====
     */
    function isContract(address account) internal view returns (bool) {
        // This method relies on extcodesize/address.code.length, which returns 0
        // for contracts in construction, since the code is only stored at the end
        // of the constructor execution.

        return account.code.length > 0;
    }

    /**
     * @dev Replacement for Solidity's `transfer`: sends `amount` wei to
     * `recipient`, forwarding all available gas and reverting on errors.
     *
     * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
     * of certain opcodes, possibly making contracts go over the 2300 gas limit
     * imposed by `transfer`, making them unable to receive funds via
     * `transfer`. {sendValue} removes this limitation.
     *
     * https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].
     *
     * IMPORTANT: because control is transferred to `recipient`, care must be
     * taken to not create reentrancy vulnerabilities. Consider using
     * {ReentrancyGuard} or the
     * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
     */
    function sendValue(address payable recipient, uint256 amount) internal {
        require(address(this).balance >= amount, "Address: insufficient balance");

        (bool success, ) = recipient.call{value: amount}("");
        require(success, "Address: unable to send value, recipient may have reverted");
    }

    /**
     * @dev Performs a Solidity function call using a low level `call`. A
     * plain `call` is an unsafe replacement for a function call: use this
     * function instead.
     *
     * If `target` reverts with a revert reason, it is bubbled up by this
     * function (like regular Solidity function calls).
     *
     * Returns the raw returned data. To convert to the expected return value,
     * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
     *
     * Requirements:
     *
     * - `target` must be a contract.
     * - calling `target` with `data` must not revert.
     *
     * _Available since v3.1._
     */
    function functionCall(address target, bytes memory data) internal returns (bytes memory) {
        return functionCallWithValue(target, data, 0, "Address: low-level call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
     * `errorMessage` as a fallback revert reason when `target` reverts.
     *
     * _Available since v3.1._
     */
    function functionCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal returns (bytes memory) {
        return functionCallWithValue(target, data, 0, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but also transferring `value` wei to `target`.
     *
     * Requirements:
     *
     * - the calling contract must have an ETH balance of at least `value`.
     * - the called Solidity function must be `payable`.
     *
     * _Available since v3.1._
     */
    function functionCallWithValue(
        address target,
        bytes memory data,
        uint256 value
    ) internal returns (bytes memory) {
        return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
    }

    /**
     * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
     * with `errorMessage` as a fallback revert reason when `target` reverts.
     *
     * _Available since v3.1._
     */
    function functionCallWithValue(
        address target,
        bytes memory data,
        uint256 value,
        string memory errorMessage
    ) internal returns (bytes memory) {
        require(address(this).balance >= value, "Address: insufficient balance for call");
        (bool success, bytes memory returndata) = target.call{value: value}(data);
        return verifyCallResultFromTarget(target, success, returndata, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but performing a static call.
     *
     * _Available since v3.3._
     */
    function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
        return functionStaticCall(target, data, "Address: low-level static call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
     * but performing a static call.
     *
     * _Available since v3.3._
     */
    function functionStaticCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal view returns (bytes memory) {
        (bool success, bytes memory returndata) = target.staticcall(data);
        return verifyCallResultFromTarget(target, success, returndata, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but performing a delegate call.
     *
     * _Available since v3.4._
     */
    function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
        return functionDelegateCall(target, data, "Address: low-level delegate call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
     * but performing a delegate call.
     *
     * _Available since v3.4._
     */
    function functionDelegateCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal returns (bytes memory) {
        (bool success, bytes memory returndata) = target.delegatecall(data);
        return verifyCallResultFromTarget(target, success, returndata, errorMessage);
    }

    /**
     * @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling
     * the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract.
     *
     * _Available since v4.8._
     */
    function verifyCallResultFromTarget(
        address target,
        bool success,
        bytes memory returndata,
        string memory errorMessage
    ) internal view returns (bytes memory) {
        if (success) {
            if (returndata.length == 0) {
                // only check isContract if the call was successful and the return data is empty
                // otherwise we already know that it was a contract
                require(isContract(target), "Address: call to non-contract");
            }
            return returndata;
        } else {
            _revert(returndata, errorMessage);
        }
    }

    /**
     * @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the
     * revert reason or using the provided one.
     *
     * _Available since v4.3._
     */
    function verifyCallResult(
        bool success,
        bytes memory returndata,
        string memory errorMessage
    ) internal pure returns (bytes memory) {
        if (success) {
            return returndata;
        } else {
            _revert(returndata, errorMessage);
        }
    }

    function _revert(bytes memory returndata, string memory errorMessage) private pure {
        // Look for revert reason and bubble it up if present
        if (returndata.length > 0) {
            // The easiest way to bubble the revert reason is using memory via assembly
            /// @solidity memory-safe-assembly
            assembly {
                let returndata_size := mload(returndata)
                revert(add(32, returndata), returndata_size)
            }
        } else {
            revert(errorMessage);
        }
    }
}

File 32 of 36 : IERC1155.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.7.0) (token/ERC1155/IERC1155.sol)

pragma solidity ^0.8.0;

import "../../utils/introspection/IERC165.sol";

/**
 * @dev Required interface of an ERC1155 compliant contract, as defined in the
 * https://eips.ethereum.org/EIPS/eip-1155[EIP].
 *
 * _Available since v3.1._
 */
interface IERC1155 is IERC165 {
    /**
     * @dev Emitted when `value` tokens of token type `id` are transferred from `from` to `to` by `operator`.
     */
    event TransferSingle(address indexed operator, address indexed from, address indexed to, uint256 id, uint256 value);

    /**
     * @dev Equivalent to multiple {TransferSingle} events, where `operator`, `from` and `to` are the same for all
     * transfers.
     */
    event TransferBatch(
        address indexed operator,
        address indexed from,
        address indexed to,
        uint256[] ids,
        uint256[] values
    );

    /**
     * @dev Emitted when `account` grants or revokes permission to `operator` to transfer their tokens, according to
     * `approved`.
     */
    event ApprovalForAll(address indexed account, address indexed operator, bool approved);

    /**
     * @dev Emitted when the URI for token type `id` changes to `value`, if it is a non-programmatic URI.
     *
     * If an {URI} event was emitted for `id`, the standard
     * https://eips.ethereum.org/EIPS/eip-1155#metadata-extensions[guarantees] that `value` will equal the value
     * returned by {IERC1155MetadataURI-uri}.
     */
    event URI(string value, uint256 indexed id);

    /**
     * @dev Returns the amount of tokens of token type `id` owned by `account`.
     *
     * Requirements:
     *
     * - `account` cannot be the zero address.
     */
    function balanceOf(address account, uint256 id) external view returns (uint256);

    /**
     * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {balanceOf}.
     *
     * Requirements:
     *
     * - `accounts` and `ids` must have the same length.
     */
    function balanceOfBatch(address[] calldata accounts, uint256[] calldata ids)
        external
        view
        returns (uint256[] memory);

    /**
     * @dev Grants or revokes permission to `operator` to transfer the caller's tokens, according to `approved`,
     *
     * Emits an {ApprovalForAll} event.
     *
     * Requirements:
     *
     * - `operator` cannot be the caller.
     */
    function setApprovalForAll(address operator, bool approved) external;

    /**
     * @dev Returns true if `operator` is approved to transfer ``account``'s tokens.
     *
     * See {setApprovalForAll}.
     */
    function isApprovedForAll(address account, address operator) external view returns (bool);

    /**
     * @dev Transfers `amount` tokens of token type `id` from `from` to `to`.
     *
     * Emits a {TransferSingle} event.
     *
     * Requirements:
     *
     * - `to` cannot be the zero address.
     * - If the caller is not `from`, it must have been approved to spend ``from``'s tokens via {setApprovalForAll}.
     * - `from` must have a balance of tokens of type `id` of at least `amount`.
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the
     * acceptance magic value.
     */
    function safeTransferFrom(
        address from,
        address to,
        uint256 id,
        uint256 amount,
        bytes calldata data
    ) external;

    /**
     * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {safeTransferFrom}.
     *
     * Emits a {TransferBatch} event.
     *
     * Requirements:
     *
     * - `ids` and `amounts` must have the same length.
     * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the
     * acceptance magic value.
     */
    function safeBatchTransferFrom(
        address from,
        address to,
        uint256[] calldata ids,
        uint256[] calldata amounts,
        bytes calldata data
    ) external;
}

File 33 of 36 : ITransferSecurityRegistry.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "../utils/TransferPolicy.sol";

interface ITransferSecurityRegistry {
    event AddedToAllowlist(AllowlistTypes indexed kind, uint256 indexed id, address indexed account);
    event CreatedAllowlist(AllowlistTypes indexed kind, uint256 indexed id, string indexed name);
    event ReassignedAllowlistOwnership(AllowlistTypes indexed kind, uint256 indexed id, address indexed newOwner);
    event RemovedFromAllowlist(AllowlistTypes indexed kind, uint256 indexed id, address indexed account);
    event SetAllowlist(AllowlistTypes indexed kind, address indexed collection, uint120 indexed id);
    event SetTransferSecurityLevel(address indexed collection, TransferSecurityLevels level);

    function createOperatorWhitelist(string calldata name) external returns (uint120);
    function createPermittedContractReceiverAllowlist(string calldata name) external returns (uint120);
    function reassignOwnershipOfOperatorWhitelist(uint120 id, address newOwner) external;
    function reassignOwnershipOfPermittedContractReceiverAllowlist(uint120 id, address newOwner) external;
    function renounceOwnershipOfOperatorWhitelist(uint120 id) external;
    function renounceOwnershipOfPermittedContractReceiverAllowlist(uint120 id) external;
    function setTransferSecurityLevelOfCollection(address collection, TransferSecurityLevels level) external;
    function setOperatorWhitelistOfCollection(address collection, uint120 id) external;
    function setPermittedContractReceiverAllowlistOfCollection(address collection, uint120 id) external;
    function addOperatorToWhitelist(uint120 id, address operator) external;
    function addPermittedContractReceiverToAllowlist(uint120 id, address receiver) external;
    function removeOperatorFromWhitelist(uint120 id, address operator) external;
    function removePermittedContractReceiverFromAllowlist(uint120 id, address receiver) external;
    function getCollectionSecurityPolicy(address collection) external view returns (CollectionSecurityPolicy memory);
    function getWhitelistedOperators(uint120 id) external view returns (address[] memory);
    function getPermittedContractReceivers(uint120 id) external view returns (address[] memory);
    function isOperatorWhitelisted(uint120 id, address operator) external view returns (bool);
    function isContractReceiverPermitted(uint120 id, address receiver) external view returns (bool);
}

File 34 of 36 : IEOARegistry.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "@openzeppelin/contracts/utils/introspection/IERC165.sol";

interface IEOARegistry is IERC165 {
    function isVerifiedEOA(address account) external view returns (bool);
}

File 35 of 36 : ITransferValidator.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "../utils/TransferPolicy.sol";

interface ITransferValidator {
    function applyCollectionTransferPolicy(address caller, address from, address to) external view;
}

File 36 of 36 : TransferPolicy.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

enum AllowlistTypes {
    Operators,
    PermittedContractReceivers
}

enum ReceiverConstraints {
    None,
    NoCode,
    EOA
}

enum CallerConstraints {
    None,
    OperatorWhitelistEnableOTC,
    OperatorWhitelistDisableOTC
}

enum StakerConstraints {
    None,
    CallerIsTxOrigin,
    EOA
}

enum TransferSecurityLevels {
    Zero,
    One,
    Two,
    Three,
    Four,
    Five,
    Six
}

struct TransferSecurityPolicy {
    CallerConstraints callerConstraints;
    ReceiverConstraints receiverConstraints;
}

struct CollectionSecurityPolicy {
    TransferSecurityLevels transferSecurityLevel;
    uint120 operatorWhitelistId;
    uint120 permittedContractReceiversId;
}

Settings
{
  "evmVersion": "paris",
  "optimizer": {
    "enabled": true,
    "mode": "3"
  },
  "outputSelection": {
    "*": {
      "*": [
        "abi",
        "metadata"
      ],
      "": [
        "ast"
      ]
    }
  },
  "detectMissingLibraries": false,
  "forceEVMLA": false,
  "enableEraVMExtensions": false,
  "libraries": {}
}

Contract ABI

[{"inputs":[{"internalType":"string","name":"_baseURI","type":"string"},{"internalType":"address","name":"usdc_","type":"address"},{"internalType":"address","name":"signerAddress_","type":"address"},{"internalType":"address","name":"feeRecipient_","type":"address"},{"internalType":"uint96","name":"royaltyFeeNumerator_","type":"uint96"},{"internalType":"uint256","name":"initialQueueFee","type":"uint256"},{"internalType":"uint256","name":"initialLoseQueueRefund","type":"uint256"},{"internalType":"uint256","name":"initialCreateFee","type":"uint256"},{"internalType":"uint256","name":"initialFee","type":"uint256"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"AlreadyInQueue","type":"error"},{"inputs":[],"name":"AlreadyInitialized","type":"error"},{"inputs":[],"name":"BlockhashExpired","type":"error"},{"inputs":[],"name":"BlockhashNotFound","type":"error"},{"inputs":[],"name":"BlockhashNotReady","type":"error"},{"inputs":[],"name":"CreatorTokenBase__InvalidTransferValidatorContract","type":"error"},{"inputs":[],"name":"CreatorTokenBase__SetTransferValidatorFirst","type":"error"},{"inputs":[],"name":"ExceedsMaxQuantity","type":"error"},{"inputs":[],"name":"InsufficientTokensToRedeem","type":"error"},{"inputs":[],"name":"InsufficientTokensToRefund","type":"error"},{"inputs":[],"name":"InvalidNonce","type":"error"},{"inputs":[],"name":"InvalidSignature","type":"error"},{"inputs":[],"name":"LoseQueueRefundExceedsQueueFee","type":"error"},{"inputs":[],"name":"NewOwnerIsZeroAddress","type":"error"},{"inputs":[],"name":"NoHandoverRequest","type":"error"},{"inputs":[],"name":"NotInQueue","type":"error"},{"inputs":[],"name":"OnlyTokenOwnerOrMarketplaceCanTransfer","type":"error"},{"inputs":[],"name":"PaymentFailed","type":"error"},{"inputs":[],"name":"QueueAlreadyCommitted","type":"error"},{"inputs":[],"name":"QueueAlreadyProcessed","type":"error"},{"inputs":[],"name":"QueueAlreadyRevealed","type":"error"},{"inputs":[],"name":"QueueEmpty","type":"error"},{"inputs":[],"name":"QueuePeriodEnded","type":"error"},{"inputs":[],"name":"QueueStillOpen","type":"error"},{"inputs":[],"name":"RefundTransferFailed","type":"error"},{"inputs":[],"name":"SaleEnded","type":"error"},{"inputs":[],"name":"SaleNotStarted","type":"error"},{"inputs":[],"name":"ShouldNotMintToBurnAddress","type":"error"},{"inputs":[],"name":"TokenMintingDisabled","type":"error"},{"inputs":[],"name":"TokenNotRefundable","type":"error"},{"inputs":[],"name":"Unauthorized","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"receiver","type":"address"},{"indexed":false,"internalType":"uint96","name":"feeNumerator","type":"uint96"}],"name":"DefaultRoyaltySet","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"creator","type":"address"},{"indexed":false,"internalType":"uint256","name":"price","type":"uint256"}],"name":"DropCreated","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"pendingOwner","type":"address"}],"name":"OwnershipHandoverCanceled","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"pendingOwner","type":"address"}],"name":"OwnershipHandoverRequested","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"oldOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"user","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"QueueJoined","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"user","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"QueueLeft","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"minter","type":"address"},{"indexed":false,"internalType":"uint256","name":"price","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"fee","type":"uint256"}],"name":"TokenMinted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"redeemer","type":"address"}],"name":"TokenRedeemed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"minter","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"price","type":"uint256"}],"name":"TokenRefunded","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"},{"indexed":true,"internalType":"address","name":"receiver","type":"address"},{"indexed":false,"internalType":"uint96","name":"feeNumerator","type":"uint96"}],"name":"TokenRoyaltySet","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256[]","name":"ids","type":"uint256[]"},{"indexed":false,"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"TransferBatch","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"id","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"TransferSingle","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"oldValidator","type":"address"},{"indexed":false,"internalType":"address","name":"newValidator","type":"address"}],"name":"TransferValidatorUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"string","name":"value","type":"string"},{"indexed":true,"internalType":"uint256","name":"id","type":"uint256"}],"name":"URI","type":"event"},{"inputs":[],"name":"DEFAULT_OPERATOR_WHITELIST_ID","outputs":[{"internalType":"uint120","name":"","type":"uint120"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"DEFAULT_TRANSFER_SECURITY_LEVEL","outputs":[{"internalType":"enum TransferSecurityLevels","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"DEFAULT_TRANSFER_VALIDATOR","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"USDC","outputs":[{"internalType":"contract IERC20","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"account","type":"address"},{"internalType":"uint256","name":"id","type":"uint256"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"accounts","type":"address[]"},{"internalType":"uint256[]","name":"ids","type":"uint256[]"}],"name":"balanceOfBatch","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"baseURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"tokenIds","type":"uint256[]"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"uint256[]","name":"fees","type":"uint256[]"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"batchRedeem","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"marketplace","type":"address"},{"internalType":"bool","name":"isBlacklisted","type":"bool"}],"name":"blacklistMarketplace","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"blacklistedMarketplaces","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"cancelOwnershipHandover","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"address","name":"user","type":"address"}],"name":"checkQueueResult","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"claimFromQueue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"commitQueue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"pendingOwner","type":"address"}],"name":"completeOwnershipHandover","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"nonReserved","type":"uint256"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"bool","name":"_isOE","type":"bool"},{"internalType":"bool","name":"isStripe","type":"bool"},{"internalType":"bytes","name":"signature","type":"bytes"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"uint256","name":"startTimestamp","type":"uint256"},{"internalType":"uint256","name":"endTimestamp","type":"uint256"},{"internalType":"uint256","name":"minMint","type":"uint256"},{"internalType":"uint256","name":"reserved","type":"uint256"}],"name":"createDrop","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"createFee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"currentTokenId","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bool","name":"disabled","type":"bool"}],"name":"disableToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"address","name":"","type":"address"}],"name":"enteredQueue","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"fee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"fullWithdraw","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"getPermittedContractReceivers","outputs":[{"internalType":"address[]","name":"","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getSecurityPolicy","outputs":[{"components":[{"internalType":"enum TransferSecurityLevels","name":"transferSecurityLevel","type":"uint8"},{"internalType":"uint120","name":"operatorWhitelistId","type":"uint120"},{"internalType":"uint120","name":"permittedContractReceiversId","type":"uint120"}],"internalType":"struct CollectionSecurityPolicy","name":"","type":"tuple"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getTransferValidator","outputs":[{"internalType":"contract ICreatorTokenTransferValidator","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getWhitelistedOperators","outputs":[{"internalType":"address[]","name":"","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"account","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"receiver","type":"address"}],"name":"isContractReceiverPermitted","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"}],"name":"isOperatorWhitelisted","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"caller","type":"address"},{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"}],"name":"isTransferAllowed","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"joinQueue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"leaveQueue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"loseQueueRefund","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"signature","type":"bytes"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"bool","name":"isStripe","type":"bool"},{"internalType":"uint256","name":"tax","type":"uint256"}],"name":"mintToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"signature","type":"bytes"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"bool","name":"isStripe","type":"bool"},{"internalType":"uint256","name":"tax","type":"uint256"}],"name":"mintTokenByCreator","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"}],"name":"nonceUsed","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"nonces","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"result","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"nonReserved","type":"uint256"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"bool","name":"_isOE","type":"bool"},{"internalType":"uint256","name":"startTimestamp","type":"uint256"},{"internalType":"uint256","name":"endTimestamp","type":"uint256"},{"internalType":"uint256","name":"minMint","type":"uint256"},{"internalType":"uint256","name":"reserved","type":"uint256"}],"name":"ownerCreateDrop","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"ownerMintToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"ownerRedeem","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"address","name":"recipient","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"ownerRefund","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"pendingOwner","type":"address"}],"name":"ownershipHandoverExpiresAt","outputs":[{"internalType":"uint256","name":"result","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"queue","outputs":[{"internalType":"uint256","name":"reserved","type":"uint256"},{"internalType":"uint256","name":"cost","type":"uint256"},{"internalType":"uint256","name":"blockCommit","type":"uint256"},{"internalType":"uint256","name":"rng","type":"uint256"},{"internalType":"uint256","name":"entries","type":"uint256"},{"internalType":"uint256","name":"claimed","type":"uint256"},{"internalType":"uint256","name":"queueFee","type":"uint256"},{"internalType":"uint256","name":"loseQueueRefund","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"queueFee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"refundToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"requestOwnershipHandover","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"revealQueue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"},{"internalType":"uint256","name":"_salePrice","type":"uint256"}],"name":"royaltyInfo","outputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256[]","name":"ids","type":"uint256[]"},{"internalType":"uint256[]","name":"amounts","type":"uint256[]"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"safeBatchTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"id","type":"uint256"},{"internalType":"uint256","name":"amount","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":"uint256","name":"newCreateFee","type":"uint256"}],"name":"setCreateFee","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"newFee","type":"uint256"}],"name":"setFee","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newFeeRecipient","type":"address"}],"name":"setFeeRecipient","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"newLoseQueueRefund","type":"uint256"}],"name":"setNewLoseQueueRefund","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"newQueueFee","type":"uint256"}],"name":"setQueueFee","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bool","name":"refundable","type":"bool"}],"name":"setRefundableOverride","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newSigner","type":"address"}],"name":"setSigner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"enum TransferSecurityLevels","name":"level","type":"uint8"},{"internalType":"uint120","name":"operatorWhitelistId","type":"uint120"},{"internalType":"uint120","name":"permittedContractReceiversAllowlistId","type":"uint120"}],"name":"setToCustomSecurityPolicy","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"validator","type":"address"},{"internalType":"enum TransferSecurityLevels","name":"level","type":"uint8"},{"internalType":"uint120","name":"operatorWhitelistId","type":"uint120"},{"internalType":"uint120","name":"permittedContractReceiversAllowlistId","type":"uint120"}],"name":"setToCustomValidatorAndSecurityPolicy","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"setToDefaultSecurityPolicy","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"transferValidator_","type":"address"}],"name":"setTransferValidator","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"_URI","type":"string"}],"name":"setURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"signerAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"tokenData","outputs":[{"internalType":"uint256","name":"nonReserved","type":"uint256"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"uint256","name":"startTimestamp","type":"uint256"},{"internalType":"uint256","name":"endTimestamp","type":"uint256"},{"internalType":"uint256","name":"minMint","type":"uint256"},{"internalType":"address","name":"creator","type":"address"},{"internalType":"bool","name":"isOE","type":"bool"},{"internalType":"uint256","name":"reserved","type":"uint256"},{"internalType":"uint256","name":"purchased","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"tokenDisabled","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"totalMinted","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"totalRedeemed","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"totalRefunded","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"uri","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"withdraw","outputs":[],"stateMutability":"nonpayable","type":"function"}]

9c4d535b000000000000000000000000000000000000000000000000000000000000000001000c65e862a8acc14c78487ecabbbc2772396547d1166e4ba2101caeb94b1f00000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000160000000000000000000000000000000000000000000000000000000000000012000000000000000000000000075bf8f439d205b8ee0de9d3622342eb05985859b0000000000000000000000002f2a13462f6d4af64954ee84641d265932849b640000000000000000000000002f2a13462f6d4af64954ee84641d265932849b6400000000000000000000000000000000000000000000000000000000000001f400000000000000000000000000000000000000000000000000000000001e8480000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004c4b4000000000000000000000000000000000000000000000000000000000001e8480000000000000000000000000000000000000000000000000000000000000002068747470733a2f2f7777772e64796c692e696f2f6170692f6d65746164617461

Deployed Bytecode

0x00020000000000020013000000000002000000000801034f0001000000010355000000600110027000000b45031001970000000100200190000000330000c13d0000008001000039000000400010043f000000040030008c000000540000413d000000000138034f000000000208043b000000e00220027000000b600020009c0000006f0000a13d00000b610020009c000000b30000a13d00000b620020009c000000f40000213d00000b700020009c000002a90000213d00000b770020009c000006570000a13d00000b780020009c00000c8b0000613d00000b790020009c000008130000613d00000b7a0020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b5202000041000000000202041a0000000003000411000000000023004b00000de20000c13d0000001302000039000000000202041a000000000021004b000010e50000a13d00000bff01000041000000800010043f00000c000100004100002d1200010430000000a002000039000000400020043f0000000001000416000000000001004b000000540000c13d0000001f0130003900000b4601100197000000a001100039000000400010043f0000001f0430018f00000b4705300198000000a001500039000000450000613d000000000608034f000000006706043c0000000002720436000000000012004b000000410000c13d000000000004004b000000520000613d000000000258034f0000000304400210000000000501043300000000054501cf000000000545022f000000000202043b0000010004400089000000000242022f00000000024201cf000000000252019f0000000000210435000001200030008c000000560000813d000000000100001900002d1200010430000000a00200043d00000b480020009c000000540000213d0000001f01200039000000000031004b000000000400001900000b490400804100000b4901100197000000000001004b000000000500001900000b490500404100000b490010009c000000000504c019000000000005004b000000540000c13d000000a001200039000000000101043300000b480010009c0000012d0000a13d00000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d120001043000000b970020009c000000db0000213d00000bb20020009c000001ae0000a13d00000bb30020009c000002ee0000213d00000bba0020009c000006c10000a13d00000bbb0020009c00000d250000613d00000bbc0020009c000009c40000613d00000bbd0020009c000000540000c13d000000640030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000002401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000004401800370000000000401043b0000000401800370000000000301043b00000b5201000041000000000101041a0000000002000411000000000012004b00000de20000c13d0000000b0000006b00000d3a0000613d000a00000004001d000900000003001d000000000030043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a0000000a0010006c0000181d0000813d000000400100043d00000c4102000041000011fa0000013d00000b7d0020009c000001870000a13d00000b7e0020009c000001fe0000213d00000b850020009c000004be0000a13d00000b860020009c0000077f0000613d00000b870020009c000006f90000613d00000b880020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000201043b0000000601200039000000000101041a000000000001004b000010d00000c13d000000400100043d00000c4702000041000011fa0000013d00000b980020009c000001ef0000a13d00000b990020009c000003370000213d00000ba00020009c000006cf0000a13d00000ba10020009c00000d460000613d00000ba20020009c000009d80000613d00000ba30020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d2d10294b0000040f00000004010000390000000101100367000000000101043b0000001502000039000000000012041b000000000100001900002d110001042e00000b630020009c000002d70000213d00000b6a0020009c000006860000a13d00000b6b0020009c00000caf0000613d00000b6c0020009c000008230000613d00000b6d0020009c000000540000c13d000000240030008c000000540000413d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d00000b5201000041000000000101041a0000000002000411000000000012004b00000de20000c13d00000bcc010000410000000c0010043f0000000b01000029000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000be5011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000900000001001d000000000101041a000a00000001001d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b0000000a0010006c000016660000a13d00000be801000041000000000010043f00000bdb0100004100002d12000104300000001f0410003900000c51044001970000003f0440003900000c5104400197000000400500043d0000000004450019000b00000005001d000000000054004b0000000005000039000000010500403900000b480040009c000000690000213d0000000100500190000000690000c13d000000a003300039000000400040043f0000000b040000290000000004140436000a00000004001d000000c0022000390000000004210019000000000034004b000000540000213d000000000001004b0000000a060000290000014f0000613d000000000300001900000000043600190000000005230019000000000505043300000000005404350000002003300039000000000013004b000001480000413d0000000b0110002900000020011000390000000000010435000000c00100043d000900000001001d00000b4a0010009c000000540000213d000000e00100043d000800000001001d00000b4a0010009c000000540000213d000001000200043d00000b4a0020009c000000540000213d000001200100043d00000b4b0010009c000000540000213d0000000b03000029000000000403043300000b480040009c000000690000213d0000000203000039000000000503041a000000010650019000000001055002700000007f0550618f0000001f0050008c00000000070000390000000107002039000000000076004b0000104c0000c13d000000200050008c0000017f0000413d000000000030043f0000001f06400039000000050660027000000b4c0660009a000000200040008c00000b4d060040410000001f05500039000000050550027000000b4c0550009a000000000056004b0000017f0000813d000000000006041b0000000106600039000000000056004b0000017b0000413d0000001f0040008c000016570000a13d000000000030043f00000c51074001980000175b0000c13d000000200600003900000b4d05000041000017680000013d00000b8b0020009c000003490000a13d00000b8c0020009c000004820000a13d00000b8d0020009c000007270000613d00000b8e0020009c0000070d0000613d00000b8f0020009c000000540000c13d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d2d1027b10000040f000a00000001001d2d10294b0000040f0000001801000039000000200010043f0000000b010000290000000801100270000000000010043f000000400200003900000000010000192d102cd30000040f0000000b02000029000000ff0220018f0000000a0000006b0000000003000039000000010300c03900000000032301cf00000c52022002df000000000401041a000000000224016f00000d790000013d00000bc00020009c000003590000a13d00000bc10020009c0000062c0000a13d00000bc20020009c000006f90000613d00000bc30020009c000007620000613d00000bc40020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000b00000001001d0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000a00000001001d0000000b010000290000000201100039000000000101041a000b00000001001d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b0000000b0010006c000015880000813d000000400100043d00000c4802000041000011fa0000013d00000ba60020009c0000036c0000a13d00000ba70020009c0000063f0000a13d00000ba80020009c00000aa20000613d00000ba90020009c000007670000613d00000baa0020009c000000540000c13d0000000001000416000000000001004b000000540000c13d000000110100003900000c700000013d00000b7f0020009c0000061e0000a13d00000b800020009c000007f20000613d00000b810020009c0000071b0000613d00000b820020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff00100190000010770000613d0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000201100039000000000101041a000000000001004b000016630000c13d0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000102100039000000000202041a0000000601100039000000000101041a000a00000002001d000900000001001d000000000021001a000018a50000413d0000000b01000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c5302200197000000000021041b0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000401100039000000000201041a000000000002004b000018a50000613d00000009040000290000000a03400029000000010220008a000000000021041b000000400200043d0000002401200039000900000003001d000000000031043500000bd9010000410000000000120435000000000100041100000b4a01100197000a00000002001d0000000402200039000000000012043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c00001c4e0000c13d0000000004000031000000200040008c000000200400803900001c770000013d00000b710020009c000006970000a13d00000b720020009c00000cd00000613d00000b730020009c000009040000613d00000b740020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000601000039000000200010043f000000400200003900000000010000192d102cd30000040f0000000702100039000000000202041a0000000603100039000000000303041a0000000504100039000000000404041a0000000405100039000000000505041a0000000306100039000000000606041a0000000207100039000000000707041a0000000108100039000000000808041a000000000101041a000000800010043f000000a00080043f000000c00070043f000000e00060043f000001000050043f000001200040043f000001400030043f000001600020043f00000bf40100004100002d110001042e00000b640020009c000006aa0000a13d00000b650020009c00000cff0000613d00000b660020009c000009090000613d00000b670020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d00000bcc020000410000000c0020043f000000000010043f0000000c0100003900000020020000390000075d0000013d00000bb40020009c000006d40000a13d00000bb50020009c00000d650000613d00000bb60020009c000009fa0000613d00000bb70020009c000000540000c13d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000501000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000b00000002001d00000b4f0020009c000000690000213d000000000101043b0000000b040000290000004002400039000000400020043f000000000101041a0000002003400039000000a002100270000000000023043500000b4a011001980000000000140435000003260000c13d000000400100043d000b00000001001d00000b4f0010009c000000690000213d0000000b040000290000004001400039000000400010043f0000000401000039000000000101041a0000002003400039000000a002100270000000000023043500000b4a01100197000000000014043500000024010000390000000101100367000000000101043b2d1027f00000040f0000000b020000290000000002020433000027100110011a000000400300043d0000002004300039000000000014043500000b4a01200197000000000013043500000b450030009c00000b4503008041000000400130021000000c3e011001c700002d110001042e00000b9a0020009c000006df0000a13d00000b9b0020009c00000d6a0000613d00000b9c0020009c00000a260000613d00000b9d0020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000c010000390000075a0000013d00000b920020009c0000038d0000213d00000b950020009c0000073a0000613d00000b960020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f00000009010000390000063b0000013d00000bc70020009c0000049e0000213d00000bca0020009c00000afd0000613d00000bcb0020009c000000540000c13d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d0000002402800370000000000202043b2d1027bc0000040f00000d5e0000013d00000bad0020009c000004b50000213d00000bb00020009c00000b020000613d00000bb10020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000000301000039000000000101041a00000b4a0210019800000c830000613d00000bfb01000041000000800010043f0000000001000410000000840010043f0000000001000414000000040020008c000a00000002001d000012ca0000c13d0000000003000031000000600030008c00000060040000390000000004034019000012ee0000013d00000b930020009c0000074f0000613d00000b940020009c000000540000c13d000000a40030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d0000002401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000404200039000000000148034f000000000101043b00000b480010009c000000690000213d0000001f0610003900000c51066001970000003f0660003900000c510660019700000bdc0060009c000000690000213d00000024022000390000008006600039000000400060043f000000800010043f0000000002210019000000000032004b000000540000213d000000000908034f0000002002400039000000000328034f00000c51041001980000001f0510018f000000a002400039000003bf0000613d000000a006000039000000000703034f000000007807043c0000000006860436000000000026004b000003bb0000c13d000000000005004b000003cc0000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000a00110003900000000000104350000004401900370000000000101043b000a00000001001d0000006401900370000000000201043b000000000002004b0000000001000039000000010100c039000900000002001d000000000012004b000000540000c13d0000008401900370000000000101043b000800000001001d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000a02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000181a0000c13d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000a02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000001000411000000000010043f0000000d01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b0000000b01000029000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000600000001001d0000000301100039000000000101041a000700000001001d000000000001004b00001e1d0000c13d000000400100043d000000a0021000390000000803000029000000000032043500000080021000390000000903000029000000000032043500000060021000390000000a03000029000000000032043500000040021000390000000b030000290000000000320435000000a0020000390000000002210436000000000300041100000b4a03300197000a00000003001d000000000032043500000be90010009c000000690000213d000000c003100039000000400030043f00000b450020009c00000b45020080410000004002200210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000200010043f00000bea01000041000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000beb011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000700000002001d000000000101043b000000800200043d000000400020008c000020fd0000613d000000410020008c00001f3a0000c13d000000e00200043d000000f802200270000000200020043f000000c00200043d000021020000013d00000b900020009c00000a890000613d00000b910020009c000000540000c13d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d2d1027b10000040f000a00000001001d2d10294b0000040f0000000b01000029000000000010043f0000000f01000039000000200010043f000000400200003900000000010000192d102cd30000040f000000000301041a00000c53023001970000000a0300002900000a9d0000013d00000bc80020009c00000b140000613d00000bc90020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000201043b00000be300200198000000540000c13d000000010100003900000c4c0020009c000012c30000a13d00000c4d0020009c00000eba0000613d00000c4e0020009c00000eba0000613d00000c4f0020009c00000eba0000613d000012c70000013d00000bae0020009c00000b1b0000613d00000baf0020009c000000540000c13d0000000001000416000000000001004b000000540000c13d00000014010000390000075e0000013d00000b890020009c00000c6c0000613d00000b8a0020009c000000540000c13d000000840030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b480010009c000000540000213d0000002302100039000000000032004b000000540000813d0000000402100039000000000228034f000000000402043b00000b480040009c000000690000213d00000005024002100000003f0520003900000bfe0550019700000bdc0050009c000000690000213d0000008005500039000000400050043f000000800040043f00000024011000390000000002120019000000000032004b000000540000213d000000000708034f000000000608034f000000000004004b000004eb0000613d0000008004000039000000000516034f000000000505043b000000200440003900000000005404350000002001100039000000000021004b000004e40000413d0000002401600370000000000101043b000b00000001001d0000004401600370000000000101043b00000b480010009c000000540000213d0000002302100039000000000032004b000000000400001900000b490400804100000b4902200197000000000002004b000000000500001900000b490500404100000b490020009c000000000504c019000000000005004b000000540000c13d0000000402100039000000000226034f000000000202043b00000b480020009c000000690000213d00000005042002100000003f0540003900000bfe05500197000000400600043d0000000005560019000a00000006001d000000000065004b0000000006000039000000010600403900000b480050009c000000690000213d0000000100600190000000690000c13d000000400050043f0000000a050000290000000005250436000900000005001d00000024011000390000000004140019000000000034004b000000540000213d000000000607034f000000000002004b000005230000613d0000000a02000029000000000516034f000000000505043b000000200220003900000000005204350000002001100039000000000041004b0000051c0000413d0000006401600370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000000400001900000b490400804100000b4901100197000000000001004b000000000500001900000b490500404100000b490010009c000000000504c019000000000005004b000000540000c13d0000000404200039000000000146034f000000000101043b00000b480010009c000000690000213d0000001f0510003900000c51055001970000003f0550003900000c5105500197000000400600043d0000000005560019000800000006001d000000000065004b0000000006000039000000010600403900000b480050009c000000690000213d0000000100600190000000690000c13d0000002402200039000000400050043f00000008050000290000000005150436000700000005001d0000000002210019000000000032004b000000540000213d0000002002400039000000000327034f00000c51041001980000001f0510018f00000007024000290000055a0000613d000000000603034f0000000707000029000000006806043c0000000007870436000000000027004b000005560000c13d000000000005004b000005670000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000070110002900000000000104350000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000181a0000c13d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000001000411000000000010043f0000000d01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b000000400100043d000000400210003900000080040000390000000000420435000000200210003900000000030004110000000000320435000000a003100039000000800500043d0000000000530435000000c003100039000000000005004b000005cc0000613d00000000060000190000002004400039000000000704043300000000037304360000000106600039000000000056004b000005c60000413d00000060041000390000000b0500002900000000005404350000000004130049000000200440008a000000800510003900000000004504350000000a0400002900000000040404330000000003430436000000000004004b000005e00000613d00000000050000190000000a060000290000002006600039000000000706043300000000037304360000000105500039000000000045004b000005da0000413d0000000003130049000000200430008a00000000004104350000001f0330003900000c51043001970000000003140019000000000043004b0000000004000039000000010400403900000b480030009c000000690000213d0000000100400190000000690000c13d000000400030043f00000b450020009c00000b45020080410000004002200210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000200010043f00000bea01000041000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000beb011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000b00000002001d000000000101043b00000008020000290000000002020433000000400020008c000024b80000613d000000410020008c00001f3a0000c13d000000080300002900000060023000390000000002020433000000f802200270000000200020043f00000040023000390000000002020433000024bf0000013d00000b830020009c00000c750000613d00000b840020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000a010000390000075a0000013d00000bc50020009c00000d7d0000613d00000bc60020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d000000000010043f0000000f01000039000000200010043f0000004002000039000000000100001900000cc80000013d00000bab0020009c00000de60000613d00000bac0020009c000000540000c13d0000000002000416000000000002004b000000540000c13d0000000302000039000000000202041a00000b4a0220019800000fce0000613d00000bfb03000041000000800030043f0000000003000410000000840030043f0000000003000414000000040020008c000b00000002001d000010e90000c13d0000000003000031000000600030008c000000600400003900000000040340190000110d0000013d00000b7b0020009c00000eb50000613d00000b7c0020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000801000039000000200010043f000000400200003900000000010000192d102cd30000040f0000000702100039000000000202041a0000000603100039000000000303041a0000000504100039000000000404041a0000000405100039000000000505041a0000000306100039000000000606041a0000000207100039000000000707041a0000000108100039000000000808041a000000000101041a000000800010043f000000a00080043f000000c00070043f000000e00060043f000001000050043f00000b4a01400197000001200010043f00000c03004001980000000001000039000000010100c039000001400010043f000001600030043f000001800020043f00000c040100004100002d110001042e00000b6e0020009c00000ebd0000613d00000b6f0020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d2d10294b0000040f000000170100003900000d760000013d00000b750020009c00000fc70000613d00000b760020009c000000540000c13d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000002401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000000401800370000000000101043b000000000010043f000000070100003900000cbf0000013d00000b680020009c00000fd60000613d00000b690020009c000000540000c13d000000240030008c000000540000413d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d00000b5201000041000000000101041a0000000005000411000000000015004b00000de20000c13d0000000b06000029000000000006004b000013820000c13d00000bda01000041000000000010043f00000bdb0100004100002d120001043000000bbe0020009c000010280000613d00000bbf0020009c000000540000c13d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000b010000390000075a0000013d00000ba40020009c000010520000613d00000ba50020009c000006d80000613d000000540000013d00000bb80020009c0000107a0000613d00000bb90020009c000000540000c13d0000000001000416000000000001004b000000540000c13d0000000101000039000000800010043f00000bcd0100004100002d110001042e00000b9e0020009c000010950000613d00000b9f0020009c000000540000c13d0000000001000416000000000001004b000000540000c13d0000001603000039000000000203041a000000010420019000000001012002700000007f0110618f0000001f0010008c00000000050000390000000105002039000000000552013f00000001005001900000104c0000c13d000000800010043f000000000004004b000011900000613d000000000030043f000000000001004b000013920000c13d000000a0010000390000139d0000013d0000000001000416000000000001004b000000540000c13d000000c001000039000000400010043f0000000401000039000000800010043f00000c4901000041000000a00010043f0000002001000039000000c00010043f0000008001000039000000e0020000392d1027770000040f000000c00110008a00000b450010009c00000b4501008041000000600110021000000c4a011001c700002d110001042e0000000001000416000000000001004b000000540000c13d0000000001000412001100000001001d001000000000003d000080050100003900000044030000390000000004000415000000110440008a000000050440021000000bd5020000412d102ce80000040f00000c710000013d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d2d10280c0000040f000000000100001900002d110001042e000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b5202000041000000000202041a0000000003000411000000000023004b00000de20000c13d0000001302000039000000000012041b0000001402000039000000000302041a000000000013004b00000a240000a13d000010e60000013d00000b5201000041000000000101041a0000000005000411000000000015004b00000de20000c13d000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000b540400004100000000060000192d102d060000040f0000000100200190000000540000613d00000b5201000041000000000001041b000000000100001900002d110001042e000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d000000000010043f0000000d01000039000000200010043f000000400200003900000000010000192d102cd30000040f000000000101041a000000800010043f00000bcd0100004100002d110001042e0000000001000416000000000001004b000000540000c13d000000030100003900000c700000013d00000bcc010000410000000c0010043f0000000001000411000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000be5011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000001041b000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000020300003900000c250400004100000a200000013d000000640030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000002401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000004401800370000000000401043b0000000401800370000000000201043b00000b5201000041000000000101041a0000000003000411000000000013004b00000de20000c13d000900000004001d000a00000002001d000000000020043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d00000c100020009c000000690000213d000000000101043b0000012003200039000000400030043f000000000301041a00000000043204360000000103100039000000000303041a000800000004001d00000000003404350000000203100039000000000303041a000000400420003900000000003404350000000303100039000000000303041a000000600420003900000000003404350000000403100039000000000303041a000000800420003900000000003404350000000503100039000000000303041a000000a00420003900000b4a05300197000000000054043500000c03003001980000000003000039000000010300c039000000c00420003900000000003404350000000603100039000000000303041a000000e004200039000000000034043500000100022000390000000701100039000000000101041a00000000001204350000000a01000029000000000010043f0000000a01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000090020002a000018a50000413d0000000902200029000000000021041b000000400100043d000700000001001d00000c110010009c000000690000213d00000007020000290000002001200039000600000001001d000000400010043f0000000000020435000000400100043d0000000b0000006b000018ba0000c13d000000640210003900000c13030000410000000000320435000000440210003900000c140300004100000000003204350000002402100039000000210300003900001b4f0000013d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000002401800370000000000201043b000000000002004b0000000001000039000000010100c039000a00000002001d000000000012004b000000540000c13d00000000020004110000000b0020006c000013470000c13d00000b5b01000041000000800010043f0000002001000039000000840010043f0000002901000039000000a40010043f00000c0901000041000000c40010043f00000c0a01000041000000e40010043f00000c0b0100004100002d1200010430000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000002401800370000000000201043b00000b4a0020009c000000540000213d0000000401800370000000000101043b2d1028b50000040f000000000001004b0000000001000039000000010100c03900000d5e0000013d000000c40030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d0000002401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000404200039000000000148034f000000000101043b00000b480010009c000000690000213d0000001f0610003900000c51066001970000003f0660003900000c510660019700000bdc0060009c000000690000213d00000024022000390000008006600039000000400060043f000000800010043f0000000002210019000000000032004b000000540000213d000000000908034f0000002002400039000000000328034f00000c51041001980000001f0510018f000000a002400039000008510000613d000000a006000039000000000703034f000000007807043c0000000006860436000000000026004b0000084d0000c13d000000000005004b0000085e0000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000a00110003900000000000104350000004401900370000000000101043b000a00000001001d00000b4a0010009c000000540000213d0000006401900370000000000101043b000900000001001d0000008401900370000000000201043b000000000002004b0000000001000039000000010100c039000800000002001d000000000012004b000000540000c13d000000a401900370000000000101043b000700000001001d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000902000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000181a0000c13d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000902000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000001000411000000000010043f0000000d01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b000000400100043d000000a0021000390000000703000029000000000032043500000080021000390000000803000029000000000032043500000060021000390000000903000029000000000032043500000040021000390000000b030000290000000000320435000000a0020000390000000002210436000000000300041100000b4a03300197000000000032043500000be90010009c000000690000213d000000c003100039000000400030043f00000b450020009c00000b45020080410000004002200210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000200010043f00000bea01000041000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000beb011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000900000002001d000000000101043b000000800200043d000000400020008c000020540000613d000000410020008c00001f3a0000c13d000000e00200043d000000f802200270000000200020043f000000c00200043d000020590000013d0000000001000416000000000001004b000000540000c13d00000012010000390000075e0000013d000000840030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000002401800370000000000101043b000a00000001001d000000060010008c000000540000213d0000004401800370000000000101043b000900000001001d00000bce0010009c000000540000213d0000006401800370000000000101043b000800000001001d00000bce0010009c000000540000213d00000b5201000041000000000101041a00000b4a011001970000000002000411000000000012004b000010a20000c13d0000000b010000292d10280c0000040f00000bcf0100004100000000001004430000000b010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000a02000029000000000021043500000bd1010000410000000000130435000000000100041000000b4a02100197000a00000003001d0000000401300039000700000002001d000000000021043500000000010004140000000b02000029000000040020008c000009590000613d0000000a0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000b020000292d102d060000040f000000600310027000000b450030019d000000010020019000001ac60000613d0000000a0100002900000b480010009c000000690000213d0000000a01000029000000400010043f00000bcf0100004100000000001004430000000b010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000902000029000000000021043500000bd3010000410000000000130435000a00000003001d00000004013000390000000702000029000000000021043500000000010004140000000b02000029000000040020008c0000098b0000613d0000000a0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000b020000292d102d060000040f000000600310027000000b450030019d000000010020019000001ca90000613d0000000a0100002900000b480010009c000000690000213d0000000a01000029000000400010043f00000bcf0100004100000000001004430000000b010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000802000029000000000021043500000bd4010000410000000000130435000a00000003001d00000004013000390000000702000029000000000021043500000000010004140000000b02000029000000040020008c000009bd0000613d0000000a0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000b020000292d102d060000040f000000600310027000000b450030019d000000010020019000001f940000613d0000000a0100002900000b480010009c000000690000213d0000000a01000029000000400010043f000000000100001900002d110001042e000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d000000000010043f0000000e01000039000000200010043f00000040020000390000000001000019000b0000000803532d102cd30000040f0000000b0200035f0000002402200370000000000202043b00000cc40000013d000000640030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d000000060010008c000000540000213d0000002401800370000000000101043b000a00000001001d00000bce0010009c000000540000213d0000004401800370000000000101043b000900000001001d00000bce0010009c000000540000213d00000b5201000041000000000101041a00000b4a011001970000000002000411000000000012004b000010a20000c13d0000000301000039000000000101041a00000b4a021001980000167b0000c13d00000c1f01000041000000800010043f00000c000100004100002d120001043000000bcc010000410000000c0010043f0000000001000411000000000010043f00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000b00000001001d000000000100041400000b450010009c00000b4501008041000000c00110021000000be5011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b0200002900000c3f0220009a000000000021041b000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000020300003900000c400400004100000000050004112d102d060000040f0000000100200190000000540000613d000000000100001900002d110001042e0000000001000416000000000001004b000000540000c13d00000b5201000041000000000101041a00000b4a011001970000000002000411000000000012004b000010a20000c13d00000bcf01000041000000000010044300000c1b010000410000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000400300043d000000000101043b000000000001004b000015b30000613d00000c1c0100004100000000001304350000000401300039000000000001043500000b450030009c00000b450100004100000000010340190000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bd8011001c700000c1b02000041000b00000003001d2d102d0b0000040f0000000b0b000029000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000000057b001900000a610000613d000000000801034f00000000090b0019000000008a08043c0000000009a90436000000000059004b00000a5d0000c13d000000000006004b00000a6e0000613d000000000171034f0000000306600210000000000705043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f0000000000150435000000000003001f0000000100200190000015b20000613d0000001f01400039000000600210018f0000000001b20019000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200030008c000000540000413d0000000b020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001a2b0000c13d0000000003010019000015b30000013d000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d2d1027b10000040f000b00000001001d2d10294b0000040f00000004010000390000000101100367000000000101043b000000000010043f0000000901000039000000200010043f000000400200003900000000010000192d102cd30000040f000000000301041a00000c53023001970000000b03000029000000000003004b000000010220c1bf000000000021041b000000000100001900002d110001042e000000440030008c000000540000413d0000000002000416000000000002004b000000540000c13d0000000402800370000000000202043b00000b480020009c000000540000213d0000002304200039000000000034004b000000540000813d0000000404200039000000000448034f000000000504043b00000b480050009c000000690000213d00000005045002100000003f0640003900000bfe0660019700000bdc0060009c000000690000213d0000008006600039000000400060043f000000800050043f00000024022000390000000004240019000000000034004b000000540000213d000000000908034f000000000708034f000000000005004b00000acc0000613d000000a005000039000000000627034f000000000606043b00000b4a0060009c000000540000213d00000000056504360000002002200039000000000042004b00000ac40000413d0000002402700370000000000202043b00000b480020009c000000540000213d0000002304200039000000000034004b000000000500001900000b490500404100000b4904400197000000000004004b000000000600001900000b490600204100000b490040009c000000000605c019000000000006004b000000540000613d0000000404200039000000000447034f000000000404043b00000b480040009c000000690000213d00000005054002100000003f0650003900000bfe06600197000000400700043d0000000006670019000800000007001d000000000076004b0000000007000039000000010700403900000b480060009c000000690000213d0000000100700190000000690000c13d000000400060043f00000008060000290000000006460436000700000006001d00000024022000390000000005250019000000000035004b000000540000213d000000000004004b00001b120000c13d000000800200043d000000000002004b000000000200001900001b210000613d00001b460000013d0000000001000416000000000001004b000000540000c13d00000010010000390000075e0000013d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b5202000041000000000302041a0000000002000411000000000032004b00000de20000c13d000000000001004b000011cf0000c13d00000bf101000041000000800010043f00000c000100004100002d12000104300000000001000416000000000001004b000000540000c13d00000c1b01000041000000800010043f00000bcd0100004100002d110001042e000000a40030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d0000002402800370000000000202043b000700000002001d00000b4a0020009c000000540000213d0000004402800370000000000202043b00000b480020009c000000540000213d0000002304200039000000000034004b000000540000813d0000000404200039000000000448034f000000000504043b00000b480050009c000000690000213d00000005045002100000003f0640003900000bfe0660019700000bdc0060009c000000690000213d0000008006600039000000400060043f000000800050043f00000024022000390000000004240019000000000034004b000000540000213d000000000908034f000000000708034f000000000005004b00000b4d0000613d0000008005000039000000000627034f000000000606043b000000200550003900000000006504350000002002200039000000000042004b00000b460000413d0000006402700370000000000202043b00000b480020009c000000540000213d0000002304200039000000000034004b000000000500001900000b490500804100000b4904400197000000000004004b000000000600001900000b490600404100000b490040009c000000000605c019000000000006004b000000540000c13d0000000404200039000000000447034f000000000404043b00000b480040009c000000690000213d00000005054002100000003f0650003900000bfe06600197000000400700043d0000000006670019000400000007001d000000000076004b0000000007000039000000010700403900000b480060009c000000690000213d0000000100700190000000690000c13d000000400060043f00000004060000290000000006460436000300000006001d00000024022000390000000005250019000000000035004b000000540000213d000000000709034f000000000004004b00000b820000613d0000000404000029000000000627034f000000000606043b000000200440003900000000006404350000002002200039000000000052004b00000b7b0000413d0000008402700370000000000402043b00000b480040009c000000540000213d0000002302400039000000000032004b000000000500001900000b490500804100000b4902200197000000000002004b000000000600001900000b490600404100000b490020009c000000000605c019000000000006004b000000540000c13d0000000405400039000000000257034f000000000202043b00000b480020009c000000690000213d0000001f0620003900000c51066001970000003f0660003900000c5106600197000000400700043d0000000006670019000200000007001d000000000076004b0000000007000039000000010700403900000b480060009c000000690000213d0000000100700190000000690000c13d0000002404400039000000400060043f00000002060000290000000006260436000100000006001d0000000004420019000000000034004b000000540000213d0000002003500039000000000439034f00000c51052001980000001f0620018f000000010350002900000bb90000613d000000000704034f0000000108000029000000007907043c0000000008980436000000000038004b00000bb50000c13d000000000006004b00000bc60000613d000000000454034f0000000305600210000000000603043300000000065601cf000000000656022f000000000404043b0000010005500089000000000454022f00000000045401cf000000000464019f000000000043043500000001022000290000000000020435000b0b4a0010019b00000000010004110000000b0010006c00001e7e0000c13d00000004010000290000000001010433000000800200043d000600000002001d000000000012004b00001fa10000c13d000000070100002900080b4a0010019c0000101e0000613d000000060000006b000020b50000c13d000000400100043d000000400200003900000000022104360000004003100039000000800400043d00000000004304350000006003100039000000000004004b00000be80000613d000000800500003900000000060000190000002005500039000000000705043300000000037304360000000106600039000000000046004b00000be20000413d00000000041300490000000000420435000000040200002900000000040204330000000002430436000000000004004b00000bf70000613d000000000300001900000004050000290000002005500039000000000605043300000000026204360000000103300039000000000043004b00000bf10000413d000000000212004900000b450020009c00000b4502008041000000600220021000000b450010009c00000b45010080410000004001100210000000000112019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000121019f00000b53011001c70000800d02000039000000040300003900000c380400004100000000050004110000000b0600002900000008070000292d102d060000040f0000000100200190000000540000613d00000bcf01000041000000000010044300000007010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b00000a240000613d000000400300043d0000004401300039000000a002000039000000000021043500000024013000390000000b02000029000000000021043500000c39010000410000000000130435000000040130003900000000020004110000000000210435000000a401300039000000800200043d0000000000210435000a00000003001d000000c401300039000000000002004b00000c390000613d000000800300003900000000040000190000002003300039000000000503043300000000015104360000000104400039000000000024004b00000c330000413d0000000a030000290000000002310049000000040220008a00000064033000390000000000230435000000040200002900000000020204330000000001210436000000000002004b00000c4b0000613d000000000300001900000004050000290000002005500039000000000405043300000000014104360000000103300039000000000023004b00000c450000413d0000000a030000290000000002310049000000040220008a00000084033000390000000000230435000000020200002900000000020204330000000001210436000000000002004b000000010600002900000c5e0000613d000000000300001900000000041300190000000005630019000000000505043300000000005404350000002003300039000000000023004b00000c570000413d0000000003120019000000000003043500000000030004140000000804000029000000040040008c0000231c0000c13d0000000005000415000000130550008a00000005055002100000000003000031000000200030008c00000020040000390000000004034019000023510000013d0000000001000416000000000001004b000000540000c13d00000b5201000041000000000101041a00000b4a01100197000000800010043f00000bcd0100004100002d110001042e000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000000301000039000000000101041a00000b4a02100198000011eb0000c13d0000008001000039000000010200018f000000000021043500000b450010009c00000b4501008041000000400110021000000bf3011001c700002d110001042e0000000001000416000000000001004b000000540000c13d000000e001000039000000400010043f000000800000043f000000a00000043f000000c00000043f0000000301000039000000000101041a00000b4a02100198000010a60000c13d0000014001000039000000400010043f000000e001000039000000e00000043f000001000000043f0000000002000019000000000300001900000040041000390000000000340435000000400300043d00000000022304360000002001100039000000000101043300000bce011001970000000000120435000000000104043300000bce011001970000004002300039000000000012043500000b450030009c00000b4503008041000000400130021000000c02011001c700002d110001042e000000440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b00000b4a0010009c000000540000213d0000002402800370000000000202043b000b00000002001d00000b4a0020009c000000540000213d000000000010043f0000000101000039000000200010043f000000400200003900000000010000192d102cd30000040f0000000b02000029000000000020043f000000200010043f000000000100001900000040020000392d102cd30000040f000000000101041a000000ff001001900000000001000039000000010100c039000000800010043f00000bcd0100004100002d110001042e000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000303100039000000000203041a000000000002004b000011f80000c13d000a00000003001d0000000201100039000000000101041a000b00000001001d00000bf6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000900000001001d0000000b02000029000000000021004b000015c60000813d000000400100043d00000bfa02000041000011fa0000013d0000000001000416000000000001004b000000540000c13d00000b5201000041000000000101041a0000000002000411000000000012004b00000de20000c13d00000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000400b00043d00000bd70100004100000000001b04350000000401b0003900000000030004100000000000310435000000000100041400000b4a02200197000000040020008c000a00000002001d000013b00000c13d0000000004000031000000200040008c0000002004008039000013db0000013d000000640030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000002401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000004401800370000000000401043b0000000401800370000000000301043b00000b5201000041000000000101041a0000000002000411000000000012004b00000de20000c13d0000000b0000006b0000144f0000c13d00000b5b01000041000000800010043f0000002001000039000000840010043f0000002a01000039000000a40010043f00000c2a01000041000000c40010043f00000c2901000041000000e40010043f00000c0b0100004100002d1200010430000000e40030008c000000540000413d0000000001000416000000000001004b000000540000c13d2d1027a60000040f000b00000001001d2d10294b0000040f00000001010003670000000402100370000000000202043b0000002403100370000000000303043b0000006404100370000000000504043b0000008404100370000000000604043b000000a404100370000000000704043b000000c401100370000000000801043b00000000010004110000000b040000292d102a810000040f000000400200043d000000000012043500000b450020009c00000b4502008041000000400120021000000bf3011001c700002d110001042e0000000001000416000000000001004b000000540000c13d00000013010000390000075e0000013d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d2d10294b0000040f0000001101000039000000000201041a00000b58022001970000000b03000029000000000232019f000000000021041b000000000100001900002d110001042e000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000405200039000000000158034f000000000101043b00000b480010009c000000690000213d0000001f0610003900000c51066001970000003f0660003900000c510660019700000bdc0060009c000000690000213d00000024022000390000008006600039000000400060043f000000800010043f0000000002210019000000000032004b000000540000213d0000002002500039000000000328034f00000c51051001980000001f0610018f000000a00250003900000da70000613d000000a007000039000000000803034f000000008908043c0000000007970436000000000027004b00000da30000c13d000000000006004b00000db40000613d000000000353034f0000000305600210000000000602043300000000065601cf000000000656022f000000000303043b0000010005500089000000000353022f00000000035301cf000000000363019f0000000000320435000000a001100039000000000001043500000b5201000041000000000101041a0000000002000411000000000012004b00000de20000c13d000000800200043d00000b480020009c000000690000213d0000001601000039000000000501041a000000010050019000000001035002700000007f0330618f0000001f0030008c00000000060000390000000106002039000000000565013f00000001005001900000104c0000c13d000000200030008c00000dda0000413d000000000010043f0000001f05200039000000050550027000000b550550009a000000200020008c00000b56050040410000001f03300039000000050330027000000b550330009a000000000035004b00000dda0000813d000000000005041b0000000105500039000000000035004b00000dd60000413d0000001f0020008c00001aa70000a13d000000000010043f00000c510420019800001ad30000c13d000000a00500003900000b560300004100001ae10000013d00000c4b01000041000000000010043f00000bdb0100004100002d1200010430000000840030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000004401800370000000000101043b000b00000001001d0000002401800370000000000101043b000900000001001d0000000401800370000000000101043b000a00000001001d0000006401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000404200039000000000148034f000000000101043b00000b480010009c000000690000213d0000001f0610003900000c51066001970000003f0660003900000c510660019700000bdc0060009c000000690000213d00000024022000390000008006600039000000400060043f000000800010043f0000000002210019000000000032004b000000540000213d0000002002400039000000000328034f00000c51041001980000001f0510018f000000a00240003900000e190000613d000000a006000039000000000703034f000000007807043c0000000006860436000000000026004b00000e150000c13d000000000005004b00000e260000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000a00110003900000000000104350000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000181a0000c13d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000001000411000000000010043f0000000d01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b000000400100043d00000080021000390000000b03000029000000000032043500000060021000390000000903000029000000000032043500000040021000390000000a030000290000000000320435000000800200003900000000022104360000000003000411000000000032043500000c2d0010009c000000690000213d000000a003100039000000400030043f00000b450020009c00000b45020080410000004002200210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000200010043f00000bea01000041000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000beb011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000b00000002001d000000000101043b000000800200043d000000400020008c00001f060000613d000000410020008c00001f3a0000c13d000000e00200043d000000f802200270000000200020043f000000c00200043d00001f0b0000013d0000000001000416000000000001004b000000540000c13d0000001501000039000000000101041a000000800010043f00000bcd0100004100002d110001042e000001440030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000004401800370000000000201043b000000000002004b0000000001000039000000010100c039000b00000002001d000000000012004b000000540000c13d0000006401800370000000000201043b000000000002004b0000000001000039000000010100c039000a00000002001d000000000012004b000000540000c13d0000008401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000404200039000000000148034f000000000101043b00000b480010009c000000690000213d0000001f0610003900000c51066001970000003f0660003900000c510660019700000bdc0060009c000000690000213d00000024022000390000008006600039000000400060043f000000800010043f0000000002210019000000000032004b000000540000213d0000002002400039000000000328034f00000c51041001980000001f0510018f000000a00240003900000ef70000613d000000a006000039000000000703034f000000007807043c0000000006860436000000000026004b00000ef30000c13d000000000005004b00000f040000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000a00110003900000000000104350000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000a4020000390000000102200367000000000202043b000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000181a0000c13d0000000001000411000000000010043f0000000e01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000a4020000390000000102200367000000000202043b000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000001000411000000000010043f0000000d01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b0000000102000367000000c401200370000000000101043b000900000001001d000000000001004b00000f6d0000c13d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d0000000102000367000000000101043b000900000001001d000000e401200370000000000401043b000000010140008a000000090010006c00001e2b0000413d000000400100043d0000002003100039000000000500041100000000005304350000000405200370000000000505043b000000400610003900000000005604350000002405200370000000000505043b000000a0061000390000000a07000029000000000076043500000080061000390000000b07000029000000000076043500000060061000390000000000560435000000a405200370000000000505043b00000100061000390000000000460435000000e00410003900000009060000290000000000640435000000c00410003900000000005404350000010404200370000000000404043b000001200510003900000000004504350000012402200370000000000202043b000001400410003900000000002404350000014002000039000000000021043500000bf20010009c000000690000213d0000016002100039000000400020043f00000b450030009c00000b45030080410000004002300210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000200010043f00000bea01000041000000000010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000beb011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000800000002001d000000000101043b000000800200043d000000400020008c0000216f0000613d000000410020008c00001f3a0000c13d000000e00200043d000000f802200270000000200020043f000000c00200043d000021740000013d0000000002000416000000000002004b000000540000c13d0000000302000039000000000202041a00000b4a02200198000010b20000c13d000000a001000039000000400010043f0000008002000039000000800000043f000000400100043d000b00000001001d2d1027890000040f000013a60000013d000000a40030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000901043b00000b4a0090009c000000540000213d0000002401800370000000000101043b000800000001001d00000b4a0010009c000000540000213d0000008401800370000000000201043b00000b480020009c000000540000213d0000002301200039000000000031004b000000540000813d0000000404200039000000000148034f000000000101043b00000b480010009c000000690000213d0000001f0510003900000c51055001970000003f0550003900000c510550019700000bdc0050009c000000690000213d00000024022000390000008005500039000000400050043f000000800010043f0000000002210019000000000032004b000000540000213d000900000009001d0000002002400039000000000328034f00000c51041001980000001f0510018f000000a0024000390000100a0000613d000000a006000039000000000703034f000000007807043c0000000006860436000000000026004b000010060000c13d000000000005004b000010170000613d000000000343034f0000000304500210000000000502043300000000054501cf000000000545022f000000000303043b0000010004400089000000000343022f00000000034301cf000000000353019f0000000000320435000000a00110003900000000000104350000000002000411000000090020006c0000192b0000c13d000000080000006b000019c30000c13d000000400100043d000000640210003900000c3a030000410000000000320435000000440210003900000c3b0300004100000000003204350000002402100039000000250300003900001b4f0000013d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000012001000039000000400010043f0000010001000039000001000000043f0000000402800370000000000202043b0000000003010019000000090020008c0000000a1220011a000000f804100210000000010130008a000000000501043300000c4305500197000000000445019f00000c44044001c70000000000410435000010330000213d0000010102300089000000210330008a00000000002304350000001604000039000000000204041a000000010520019000000001092002700000007f0990618f0000001f0090008c00000000060000390000000106002039000000000662013f0000000100600190000010bf0000613d00000c3501000041000000000010043f0000002201000039000000040010043f00000bd80100004100002d1200010430000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000147c0000c13d000000400100043d00000c2402000041000011fa0000013d000000640030008c000000540000413d0000000001000416000000000001004b000000540000c13d0000000401800370000000000101043b000b00000001001d00000b4a0010009c000000540000213d0000002401800370000000000101043b000a00000001001d00000b4a0010009c000000540000213d0000004401800370000000000101043b000900000001001d00000b4a0010009c000000540000213d00000001020000390000000301000039000000000101041a00000b4a03100198000016200000c13d000000800100003900000c850000013d000000240030008c000000540000413d0000000001000416000000000001004b000000540000c13d2d10294b0000040f00000004010000390000000101100367000000000101043b0000001202000039000000000012041b000000000100001900002d110001042e00000bef01000041000000800010043f00000c000100004100002d120001043000000bfb01000041000000e00010043f0000000001000410000000e40010043f0000000001000414000000040020008c000011960000c13d0000000003000031000000600030008c00000060040000390000000004034019000011ba0000013d00000bfb03000041000000800030043f0000000003000410000000840030043f0000000003000414000000040020008c000b00000002001d000012000000c13d0000000003000031000000600030008c00000060040000390000000004034019000012240000013d000000400800043d000000000005004b000012a70000613d000000000040043f000000000009004b000012aa0000613d00000b5602000041000000200480003900000000050000190000000006540019000000000702041a000000000076043500000001022000390000002005500039000000000095004b000010c80000413d000012aa0000013d000900000002001d0000000201200039000000000101041a000a00000001001d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b0000000a0010006c000015070000a13d000000400100043d00000c0f02000041000011fa0000013d0000001402000039000000000012041b000000000100001900002d110001042e00000b450030009c00000b4503008041000000c00130021000000bfc011001c72d102d0b0000040f000000600310027000000b4503300197000000600030008c000000600400003900000000040340190000001f0640018f000000600740019000000080057001bf000010fd0000613d0000008008000039000000000901034f000000009a09043c0000000008a80436000000000058004b000010f90000c13d000000000006004b0000110a0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000013760000613d0000001f02400039000000e00220018f0000008004200039000000400040043f000000600030008c000000540000413d000000e005200039000000400050043f000000800500043d000000060050008c000000540000213d0000000000540435000000a00400043d00000bce0040009c000000540000213d000000a0052000390000000000450435000000c00500043d00000bce0050009c000000540000213d000000c002200039000000000052043500000c2b02000041000000400500043d0000000000250435000a00000005001d0000000402500039000000000042043500000000020004140000000b04000029000000040040008c0000113d0000613d0000000a0100002900000b450010009c00000b4501008041000000400110021000000b450020009c00000b4502008041000000c002200210000000000112019f00000bd8011001c70000000b020000292d102d0b0000040f000000600310027000000b450030019d00000b450330019700000001002001900000196b0000613d00000c51053001980000001f0630018f0000000a04500029000011470000613d000000000701034f0000000a08000029000000007907043c0000000008980436000000000048004b000011430000c13d000000000006004b000011540000613d000000000151034f0000000305600210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001404350000001f0130003900000c51011001970000000a02100029000000000012004b0000000001000039000000010100403900000b480020009c000000690000213d0000000100100190000000690000c13d000000400020043f00000bec0030009c000000540000213d000000200030008c000000540000413d0000000a01000029000000000101043300000b480010009c000000540000213d0000000a033000290000000a011000290000001f04100039000000000034004b000000000500001900000b490500804100000b490440019700000b4906300197000000000764013f000000000064004b000000000400001900000b490400404100000b490070009c000000000405c019000000000004004b000000540000c13d000000001401043400000b480040009c000000690000213d00000005054002100000003f0650003900000bfe06600197000000000626001900000b480060009c000000690000213d000000400060043f00000000004204350000000004150019000000000034004b000000540000213d000000000041004b00000fd20000813d0000000003020019000000001501043400000b4a0050009c000000540000213d00000020033000390000000000530435000000000041004b000011880000413d00000fd20000013d00000c5302200197000000a00020043f000000000001004b000000c001000039000000a0010060390000139d0000013d00000b450010009c00000b4501008041000000c00110021000000c01011001c72d102d0b0000040f000000e00a000039000000600310027000000b4503300197000000600030008c000000600400003900000000040340190000001f0640018f0000006007400190000000e005700039000011aa0000613d000000000801034f000000008908043c000000000a9a043600000000005a004b000011a60000c13d000000000006004b000011b70000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000013fa0000613d0000001f01400039000000e00410018f000000e001400039000000400010043f000000600030008c000000540000413d0000014002400039000000400020043f000000e00200043d000000060020008c000000540000213d0000000000210435000001000300043d00000bce0030009c000000540000213d00000100044001bf0000000000340435000001200300043d00000bce0030009c00000c9e0000a13d000000540000013d00000bd903000041000000800030043f00000b4a02200197000000840020043f000000a40010043f00000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c000015d90000c13d000000000a0000310000002000a0008c000000200a008039000015fe0000013d00000bfb01000041000000800010043f0000000001000410000000840010043f0000000001000414000000040020008c000a00000002001d000014060000c13d0000000003000031000000600030008c000000600400003900000000040340190000142a0000013d000000400100043d00000bf502000041000000000021043500000b450010009c00000b4501008041000000400110021000000bdf011001c700002d120001043000000b450030009c00000b4503008041000000c00130021000000bfc011001c72d102d0b0000040f000000800a000039000000600310027000000b4503300197000000600030008c000000600400003900000000040340190000001f0640018f000000600740019000000080057001bf000012140000613d000000000801034f000000008908043c000000000a9a043600000000005a004b000012100000c13d000000000006004b000012210000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000014700000613d0000001f02400039000000e00220018f0000008004200039000000400040043f000000600030008c000000540000413d000000e005200039000000400050043f000000800500043d000000060050008c000000540000213d0000000000540435000000a00400043d00000bce0040009c000000540000213d000000a0052000390000000000450435000000c00400043d00000bce0040009c000000540000213d000000c002200039000000000042043500000bfd02000041000000400500043d0000000000250435000a00000005001d0000000402500039000000000042043500000000020004140000000b04000029000000040040008c000012540000613d0000000a0100002900000b450010009c00000b4501008041000000400110021000000b450020009c00000b4502008041000000c002200210000000000112019f00000bd8011001c70000000b020000292d102d0b0000040f000000600310027000000b450030019d00000b45033001970000000100200190000019770000613d00000c51053001980000001f0630018f0000000a045000290000125e0000613d000000000701034f0000000a08000029000000007907043c0000000008980436000000000048004b0000125a0000c13d000000000006004b0000126b0000613d000000000151034f0000000305600210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001404350000001f0130003900000c51011001970000000a02100029000000000012004b0000000001000039000000010100403900000b480020009c000000690000213d0000000100100190000000690000c13d000000400020043f00000bec0030009c000000540000213d000000200030008c000000540000413d0000000a01000029000000000101043300000b480010009c000000540000213d0000000a033000290000000a011000290000001f04100039000000000034004b000000000500001900000b490500804100000b490440019700000b4906300197000000000764013f000000000064004b000000000400001900000b490400404100000b490070009c000000000405c019000000000004004b000000540000c13d000000001401043400000b480040009c000000690000213d00000005054002100000003f0650003900000bfe06600197000000000626001900000b480060009c000000690000213d000000400060043f00000000004204350000000004150019000000000034004b000000540000213d000000000041004b00000fd20000813d0000000003020019000000001501043400000b4a0050009c000000540000213d00000020033000390000000000530435000000000041004b0000129f0000413d00000fd20000013d00000c5302200197000000200480003900000000002404350000000002890019000000200420003900000c4505000041000000000054043500000021022000390000000003030433000a00000003001d000b00000008001d000900000009001d2d10276a0000040f00000009020000290000000a0320002900000001023000390000000b01000029000000000021043500000021023000392d1027580000040f0000002001000039000000400200043d000a00000002001d00000000021204360000000b010000292d1027770000040f0000000a02000029000013a70000013d00000c1c0020009c00000eba0000613d00000c500020009c00000eba0000613d000000800000043f00000bcd0100004100002d110001042e00000b450010009c00000b4501008041000000c00110021000000bfc011001c72d102d0b0000040f000000600310027000000b4503300197000000600030008c000000600400003900000000040340190000001f0640018f000000600740019000000080057001bf000012de0000613d0000008008000039000000000901034f000000009a09043c0000000008a80436000000000058004b000012da0000c13d000000000006004b000012eb0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000015ba0000613d0000001f01400039000000e00110018f0000008002100039000000400020043f000000600030008c000000540000413d000000e004100039000000400040043f000000800400043d000000060040008c000000540000213d0000000000420435000000a00200043d00000bce0020009c000000540000213d000000a0041000390000000000240435000000c00400043d00000bce0040009c000000540000213d000000c0011000390000000000410435000000400500043d00000024015000390000000b04000029000000000041043500000c3c010000410000000000150435000900000005001d0000000401500039000000000021043500000000010004140000000a02000029000000040020008c0000144d0000613d000000090200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000a020000292d102d0b0000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000009057000290000132b0000613d000000000801034f0000000909000029000000008a08043c0000000009a90436000000000059004b000013270000c13d000000000006004b000013380000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000019ad0000c13d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000013420000c13d00001afc0000013d000000000020043f0000000101000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c53022001970000000a03000029000000000232019f000000000021041b000000400100043d000000000031043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b50011001c70000800d02000039000000030300003900000c08040000410000000005000411000018a10000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000137d0000c13d00001afc0000013d000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000b54040000412d102d060000040f0000000100200190000000540000613d00000b52010000410000000b02000029000000000021041b000000000100001900002d110001042e00000b560200004100000000040000190000000003040019000000000402041a000000a005300039000000000045043500000001022000390000002004300039000000000014004b000013940000413d000000c001300039000000800210008a00000080010000392d1027580000040f0000002001000039000000400200043d000b00000002001d000000000212043600000080010000392d1027770000040f0000000b02000029000000000121004900000b450010009c00000b4501008041000000600110021000000b450020009c00000b45020080410000004002200210000000000121019f00002d110001042e00000b4500b0009c00000b450300004100000000030b4019000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000bd8011001c7000b0000000b001d2d102d0b0000040f0000000b0b000029000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000000057b0019000013cb0000613d000000000801034f00000000090b0019000000008a08043c0000000009a90436000000000059004b000013c70000c13d000000000006004b000013d80000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000016080000613d0000001f01400039000000600110018f0000000002b10019000000000012004b00000000010000390000000101004039000b00000002001d00000b480020009c000000690000213d0000000100100190000000690000c13d0000000b01000029000000400010043f000000200040008c000000540000413d00000000010b04330000000b030000290000002402300039000000000012043500000bd9010000410000000000130435000000000100041100000b4a011001970000000402300039000000000012043500000000010004140000000a02000029000000040020008c000017270000c13d000000200a000039000017520000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000014010000c13d00001afc0000013d00000b450010009c00000b4501008041000000c00110021000000bfc011001c72d102d0b0000040f000000600310027000000b4503300197000000600030008c000000600400003900000000040340190000001f0640018f000000600740019000000080057001bf0000141a0000613d0000008008000039000000000901034f000000009a09043c0000000008a80436000000000058004b000014160000c13d000000000006004b000014270000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000016140000613d0000001f01400039000000e00110018f0000008002100039000000400020043f000000600030008c000000540000413d000000e004100039000000400040043f000000800400043d000000060040008c000000540000213d0000000000420435000000a00200043d00000bce0020009c000000540000213d000000a0041000390000000000240435000000c00200043d00000bce0020009c000000540000213d000000c0011000390000000000210435000000400500043d00000024015000390000000b04000029000000000041043500000c0c010000410000000000150435000900000005001d0000000401500039000000000021043500000000010004140000000a02000029000000040020008c000019830000c13d0000002004000039000019ad0000013d000a00000004001d000900000003001d000000000030043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a0000000a0010006c000018810000813d000000400100043d00000c4202000041000011fa0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000014770000c13d00001afc0000013d0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d000a00000002001d00000c200020009c000000690000213d000000000101043b0000000a040000290000010002400039000000400020043f000000000201041a00000000022404360000000103100039000000000303041a00000000003204350000000202100039000000000202041a000000400340003900000000002304350000000302100039000000000202041a0000006003400039000900000003001d00000000002304350000000402100039000000000202041a0000008003400039000700000003001d00000000002304350000000502100039000000000202041a000000a003400039000800000003001d00000000002304350000000602100039000000000202041a000000c0034000390000000000230435000000e0024000390000000701100039000000000101041a00000000001204350000000b01000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000200041100000b4a02200197000600000002001d000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff00100190000500000000001d00001b5c0000613d00000009010000290000000001010433000000000001004b000500000000001d00001b5c0000613d0000000a02000029000000000302043300000008020000290000000002020433000a00000003001d000000000032004b000500000000001d00001b5c0000813d00000007020000290000000003020433000900000003001d0000000a0030006c00001b5a0000a13d000000400200043d00000040032000390000000604000029000000000043043500000040030000390000000003320436000000000013043500000c210020009c000000690000213d0000006001200039000000400010043f00000b450030009c00000b45030080410000004001300210000000000202043300000b450020009c00000b45020080410000006002200210000000000112019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b00000009101000fa0000000a0010006c0000000001000039000000010100403900001b5b0000013d0000000b01000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff00100190000018b70000c13d0000001301000039000000000201041a00000009010000290000000101100039000000000101041a000a00000002001d000900000001001d000000000012001a000018a50000413d0000000b01000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c530220019700000001022001bf000000000021041b0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000401100039000000000201041a000000010220003a000018a50000613d00000009040000290000000a03400029000000000021041b000000400400043d0000004401400039000900000003001d0000000000310435000000000100041000000b4a011001970000002402400039000000000012043500000bf0010000410000000000140435000000000100041100000b4a01100197000a00000004001d0000000402400039000000000012043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c00001ced0000c13d0000000004000031000000200040008c000000200400803900001d160000013d0000000a02000029000000000102041a000000000001004b000000d80000613d0000000201200039000b00000001001d000000000201041a000900000002001d00000c530020009c000018a50000813d00000bf6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b00000009020000290000010002200039000000000021004b000015a70000a13d0000000a020000290000000302200039000000000202041a000000000002004b000015ab0000613d0000000b02000029000000000202041a000000000002004b00001ab70000c13d00000c540010009c000018a50000213d00000005011000390000000b02000029000000000012041b000000000100001900002d110001042e000000400300043d00000c1e01000041000000000013043500000b450030009c00000b4503008041000000400130021000000bdf011001c700002d12000104300000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000015c10000c13d00001afc0000013d00000bf70100004100000000001004430000000400200443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d0000000b03000029000000000101043b000000000001004b000018a30000c13d000000400100043d00000bf902000041000011fa0000013d00000b450010009c00000b4501008041000000c00110021000000c3d011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000000a040019000000200640019000000080046001bf000015ee0000613d0000008007000039000000000801034f000000008908043c0000000007970436000000000047004b000015ea0000c13d000000000005004b000015fb0000613d000000000661034f0000000305500210000000000704043300000000075701cf000000000757022f000000000606043b0000010005500089000000000656022f00000000055601cf000000000575019f0000000000540435000000000003001f00000001002001900000171b0000613d000000800100003900000000020a0019000b0000000a001d2d1027580000040f0000000b0100002900000080021001bf00000080010000392d1027fe0000040f000000000100001900002d110001042e0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000160f0000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000161b0000c13d00001afc0000013d00000bcf010000410000000000100443000800000003001d0000000400300443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400200043d00000044012000390000000903000029000000000031043500000024012000390000000a03000029000000000031043500000be0010000410000000000120435000a00000002001d00000004012000390000000b02000029000000000021043500000000010004140000000802000029000000040020008c000016500000613d0000000a0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000b5c011001c700000008020000292d102d0b0000040f000000600110027000000b450010019d000000010020019000001ab10000613d0000000a0100002900000b480010009c000000690000213d0000000a01000029000000400010043f000000010200003900000c850000013d000000000004004b00000000050000190000165c0000613d0000000a050000290000000005050433000000030640021000000c550660027f00000c5506600167000000000565016f0000000104400210000000000445019f000017740000013d000000400100043d00000c0502000041000011fa0000013d0000000901000029000000000001041b00000b5201000041000000000501041a000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000b54040000410000000b060000292d102d060000040f0000000100200190000000540000613d0000000b0100002900000b5202000041000000000012041b000000000100001900002d110001042e00000bcf010000410000000000100443000800000002001d0000000400200443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000b02000029000000000021043500000bd1010000410000000000130435000000000100041000000b4a02100197000b00000003001d0000000401300039000700000002001d000000000021043500000000010004140000000802000029000000040020008c000016aa0000613d0000000b0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c700000008020000292d102d060000040f000000600310027000000b450030019d000000010020019000001af00000613d0000000b0100002900000b480010009c000000690000213d0000000b01000029000000400010043f00000bcf01000041000000000010044300000008010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000a02000029000000000021043500000bd3010000410000000000130435000b00000003001d00000004013000390000000702000029000000000021043500000000010004140000000802000029000000040020008c000016dc0000613d0000000b0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c700000008020000292d102d060000040f000000600310027000000b450030019d000000010020019000001cb60000613d0000000b0100002900000b480010009c000000690000213d0000000b01000029000000400010043f00000bcf01000041000000000010044300000008010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000902000029000000000021043500000bd4010000410000000000130435000b00000003001d00000004013000390000000702000029000000000021043500000000010004140000000802000029000000040020008c00001aa00000613d0000000b0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c700000008020000292d102d060000040f000000600310027000000b450030019d000000010020019000001aa00000c13d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000017160000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000017220000c13d00001afc0000013d0000000b0200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000a020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000000a04001900000020064001900000000b04600029000017420000613d000000000701034f0000000b08000029000000007907043c0000000008980436000000000048004b0000173e0000c13d000000000005004b0000174f0000613d000000000661034f0000000305500210000000000704043300000000075701cf000000000757022f000000000606043b0000010005500089000000000656022f00000000055601cf000000000575019f0000000000540435000000000003001f0000000100200190000018ab0000613d0000000b0100002900000000020a0019000a0000000a001d2d1027580000040f0000000b010000290000000a021000292d1027fe0000040f000000000100001900002d110001042e00000b4d050000410000002006000039000000010870008a000000050880027000000b4e0880009a0000000b0a0000290000000009a600190000000009090433000000000095041b00000020066000390000000105500039000000000085004b000017610000c13d000000000047004b000017720000813d0000000307400210000000f80770018f00000c550770027f00000c55077001670000000b066000290000000006060433000000000676016f000000000065041b000000010440021000000001044001bf000001a00500043d000500000005001d000001800500043d000700000005001d000001600500043d000600000005001d000001400500043d000400000005001d000000000043041b000000400300043d00000b4b04100197000027100040008c000017940000a13d000000640130003900000b5d020000410000000000210435000000440130003900000b5e02000041000000000021043500000024013000390000002a02000039000000000021043500000b5b01000041000000000013043500000004013000390000002002000039000000000021043500000b450030009c00000b4503008041000000400130021000000b5f011001c700002d120001043000030b4a0020019c000017a60000c13d000000440130003900000b5a02000041000000000021043500000024013000390000001902000039000000000021043500000b5b01000041000000000013043500000004013000390000002002000039000000000021043500000b450030009c00000b4503008041000000400130021000000b5c011001c700002d120001043000000b4f0030009c000000690000213d0000004002300039000000400020043f0000002002300039000000000042043500000003050000290000000000530435000000a001100210000000000151019f0000000402000039000000000012041b000000400100043d000000000041043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b50011001c70000800d02000039000000020300003900000b51040000412d102d060000040f0000000100200190000000540000613d00002710010000390000001002000039000000000012041b000000000600041100000b5201000041000000000061041b000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000b540400004100000000050000192d102d060000040f0000000100200190000000540000613d000000090100002900000b4a01100197000000800010043f0000000b02000029000000000302043300000b480030009c000000690000213d0000001602000039000000000502041a000000010050019000000001045002700000007f0440618f0000001f0040008c00000000060000390000000106002039000000000565013f00000001005001900000104c0000c13d000000200040008c000017f80000413d000000000020043f0000001f05300039000000050550027000000b550550009a000000200030008c00000b56050040410000001f04400039000000050440027000000b550440009a000000000045004b000017f80000813d000000000005041b0000000105500039000000000045004b000017f40000413d0000001f0030008c0000002004000039000000010500003900001bef0000a13d000000000020043f00000c510830019800000b560600004100000000070400190000000b0b0000290000180d0000613d0000002007000039000000010980008a000000050990027000000b570990009a000000000ab70019000000000a0a04330000000000a6041b00000020077000390000000106600039000000000096004b000018060000c13d000000000038004b000018170000813d0000000308300210000000f80880018f00000c550880027f00000c55088001670000000b077000290000000007070433000000000787016f000000000076041b0000000106300210000000000305001900001bf90000013d000000400100043d00000c2c02000041000011fa0000013d0000000901000029000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000400200043d00000c100020009c000000690000213d000000000301043b0000012001200039000000400010043f000000000103041a00000000041204360000000101300039000000000101041a00000000001404350000000204300039000000000404041a000000400520003900000000004504350000000304300039000000000404041a000000600520003900000000004504350000000404300039000000000404041a000000800520003900000000004504350000000504300039000000000404041a000000a00520003900000b4a06400197000000000065043500000c03004001980000000004000039000000010400c039000000c00520003900000000004504350000000604300039000000000404041a000000e005200039000000000045043500000100022000390000000703300039000000000303041a00000000003204350008000a001000bd000000000001004b000018590000613d00000008011000f90000000a0010006c000018a50000c13d0000000901000029000000000010043f0000000b01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a0000000a030000290000000002320019000000000021041b0000000b0100002900000009020000292d1029550000040f000000400100043d0000002002100039000000080300002900000000003204350000000a02000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000030300003900000c2f04000041000018a00000013d0000000901000029000000000010043f0000000c01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a0000000a0020002a000018a50000413d0000000a030000290000000002320019000000000021041b0000000b0100002900000009020000292d1029550000040f000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000c150400004100000009050000290000000b0600002900000a210000013d00000c560030009c000019640000a13d00000c3501000041000000000010043f0000001101000039000000040010043f00000bd80100004100002d12000104300000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000018b20000c13d00001afc0000013d000000400100043d00000c0d02000041000011fa0000013d00000b4f0010009c000000690000213d0000004002100039000000400020043f00000020021000390000000a03000029000000000032043500000001020000390000000000210435000000400100043d00000b4f0010009c000000690000213d0000004003100039000000400030043f00000020031000390000000904000029000000000043043500000000002104350000000a01000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000090020002a000018a50000413d00000009030000290000000002320019000000000021041b000000400100043d000000200210003900000000003204350000000a02000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000040300003900000be104000041000000000500041100000000060000190000000b070000292d102d060000040f0000000100200190000000540000613d00000bcf0100004100000000001004430000000b010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000400200043d000500000002001d000000000101043b000000000001004b00001e2e0000c13d000000080100002900000000010104330000001202000039000000000202041a000000050400002900000020034000390000000000230435000000000014043500000b450040009c00000b45040080410000004001400210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000030300003900000c12040000410000000a05000029000018a10000013d0000000001000411000000000010043f0000000f01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff0010019000001b0f0000c13d0000000901000029000000000010043f0000000101000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff001001900000101c0000c13d000000400100043d000000640210003900000c31030000410000000000320435000000440210003900000c3203000041000000000032043500000024021000390000002e0300003900001b4f0000013d0000010002300039000000090020006b00001ab40000813d0000000a02000029000000000012041b000000000100001900002d110001042e0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000019720000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000197e0000c13d00001afc0000013d000000090200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd2011001c70000000a020000292d102d0b0000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000009057000290000199d0000613d000000000801034f0000000909000029000000008a08043c0000000009a90436000000000059004b000019990000c13d000000000006004b000019aa0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f000000010020019000001aba0000613d0000001f01400039000000600210018f0000000901200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200030008c000000540000413d00000009020000290000000003020433000000000003004b0000000002000039000000010200c039000000000023004b000000540000c13d000000010220018f00000c850000013d000000400100043d000700000001001d00000b4f0010009c000000690000213d00000001030003670000004401300370000000000101043b00000007040000290000004002400039000000400020043f000000010200003900000000042404360000000000140435000000400400043d00000b4f0040009c000000690000213d0000006403300370000000000303043b0000004005400039000000400050043f00000020054000390000000000350435000000000024043500000007020000290000000002020433000600000002001d000000000002004b00001cc60000613d000000000100041100050b4a0010019b0000000005000019000000090400002900000007020000290000000603000029000019e90000013d0000000105500039000000000035004b00001cc30000813d0000000001020433000000000051004b000026120000a13d000000000004004b000019e60000613d0000000301000039000000000101041a00000b4a06100198000019e60000613d000a00000005001d00000bcf010000410000000000100443000b00000006001d0000000400600443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b0000000904000029000000540000613d000000400500043d0000004401500039000000080200002900000000002104350000002401500039000000000041043500000be001000041000000000015043500000004015000390000000502000029000000000021043500000000010004140000000b02000029000000040020008c00001a240000613d00000b450050009c00000b45030000410000000003054019000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000b5c011001c7000b00000005001d2d102d0b0000040f0000000b050000290000000904000029000000600310027000000b450030019d000000010020019000001ef90000613d00000b480050009c000000690000213d000000400050043f000000070200002900000006030000290000000a05000029000019e60000013d0000000302000039000000000402041a000000200210003900000c1b030000410000000000320435000b00000004001d00000b4a02400197000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000010300003900000c1d040000412d102d060000040f0000000100200190000000540000613d0000000b0100002900000b580110019700000c1b011001c70000000302000039000000000012041b00000bcf01000041000000000010044300000c1b010000410000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000102000039000000000021043500000bd101000041000000000013043500000004013000390000000002000410000000000021043500000b450030009c000b00000003001d00000b450100004100000000010340190000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bd2011001c700000c1b020000412d102d060000040f000000600310027000000b450030019d000000010020019000001c9c0000613d0000000b0100002900000b480010009c000000690000213d0000000b01000029000000400010043f00000bcf01000041000000000010044300000c1b010000410000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400300043d00000024013000390000000102000039000000000021043500000bd301000041000000000013043500000004013000390000000002000410000000000021043500000b450030009c000b00000003001d00000b450100004100000000010340190000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bd2011001c700000c1b020000412d102d060000040f000000600310027000000b450030019d000000010020019000001fab0000613d0000000b0100002900000b480010009c000000690000213d0000000b01000029000000400010043f000000000100001900002d110001042e000000000002004b000000000300001900001aab0000613d000000a00300043d000000030420021000000c550440027f00000c5504400167000000000443016f000000010320021000001aec0000013d000000400100043d000000000200001900000c850000013d000000400100043d00000bf802000041000011fa0000013d000000400100043d00000c4602000041000011fa0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001ac10000c13d00001afc0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001ace0000c13d00001afc0000013d00000b56030000410000002006000039000000010540008a000000050550027000000b570550009a000000000706001900000080066000390000000006060433000000000063041b00000020067000390000000103300039000000000053004b00001ad80000c13d000000a005700039000000000024004b00001aea0000813d0000000304200210000000f80440018f00000c550440027f00000c55044001670000000005050433000000000445016f000000000043041b00000001030000390000000104200210000000000234019f000000000021041b000000000100001900002d110001042e00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001af80000c13d000000000005004b00001b090000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000600130021000000b450020009c00000b45020080410000004002200210000000000112019f00002d1200010430000000400100043d00000bde02000041000011fa0000013d0000000803000029000000000429034f000000000404043b000000200330003900000000004304350000002002200039000000000052004b00001b130000413d00000008020000290000000002020433000000800300043d000000000023004b00001b460000c13d00000b480020009c000000690000213d00000005032002100000003f0430003900000c2805400197000000400400043d000600000004001d0000000004450019000000000054004b0000000005000039000000010500403900000b480040009c000000690000213d0000000100500190000000690000c13d000000400040043f00000006040000290000000002240436000500000002001d0000001f0230018f000000000003004b00001b3b0000613d00000005040000290000000003340019000000001501043c0000000004540436000000000034004b00001b370000c13d000000000002004b000000800100043d000000000001004b00001c190000c13d000000400200043d000b00000002001d0000002001000039000000000212043600000006010000292d1027990000040f000013a60000013d000000400100043d000000640210003900000c26030000410000000000320435000000440210003900000c2703000041000000000032043500000024021000390000002903000039000000000032043500000b5b02000041000000000021043500000004021000390000002003000039000000000032043500000b450010009c00000b4501008041000000400110021000000b5f011001c700002d12000104300000000101000039000500000001001d0000000b01000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000c5302200197000000000021041b0000000b01000029000000000010043f000000050000006b00001bb20000c13d0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000201043b0000000101200039000000000101041a0000000702200039000000000202041a000000000012001a000018a50000413d0000000001120019000000400300043d0000002402300039000000000012043500000bd9010000410000000000130435000b00000003001d00000004013000390000000602000029000000000021043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c00001d3a0000c13d0000000003000031000000200030008c0000002004000039000000000403401900001d630000013d0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000a00000001001d0000000901000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff0010019000001d7b0000c13d0000000b01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000201043b000000000102041a0000000502200039000000000302041a000000000013004b000018a50000213d00000c550030009c000018a50000613d0000000104300039000000000042041b000000000031004b0000200f0000c13d0000000a010000290000000501100039000000000101041a00000c03001001980000200f0000c13d000000400100043d00000c2302000041000011fa0000013d000000000003004b000000000600001900001bf40000613d0000000a060000290000000006060433000000030730021000000c550770027f00000c5507700167000000000676016f0000000103300210000000000336019f000000000032041b000000080200002900000b4a022001970000001103000039000000000603041a00000b5806600197000000000226019f000000000023041b0000001702000039000000000302041a00000b580330019700000003033001af000000000032041b00000012020000390000000503000029000000000032041b00000013020000390000000403000029000000000032041b00000014020000390000000603000029000000000032041b00000015020000390000000703000029000000000032041b000001400000044300000160001004430000010000400443000001200050044300000b590100004100002d110001042e000000000300001900000008010000290000000001010433000000000031004b000026120000a13d000a00000003001d0000000503300210000000a0013000390000000001010433000b0b4a0010019c000080100200003900001e740000613d000900000003001d00000007013000290000000001010433000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c72d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000060200002900000000020204330000000a03000029000000000032004b000026120000a13d00000009040000290000000502400029000000000101043b000000000101041a00000000001204350000000103300039000000800100043d000000000013004b00001c1a0000413d00001b3f0000013d0000000a0300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000bd2011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000a0570002900001c670000613d000000000801034f0000000a09000029000000008a08043c0000000009a90436000000000059004b00001c630000c13d000000000006004b00001c740000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f000000010020019000001d2e0000613d0000001f01400039000000600210018f0000000a01200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200040008c000000540000413d0000000a020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d790000613d0000000902000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b50011001c70000800d02000039000000030300003900000c06040000410000204e0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001ca40000c13d00001afc0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001cb10000c13d00001afc0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001cbe0000c13d00001afc0000013d00000044010000390000000101100367000000000101043b000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f00000001002001900000000902000029000000540000613d000000000101043b000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000301041a00000001010003670000006402100370000000000202043b000b00000003001d000000000023004b00001d7e0000813d000000400100043d000000640210003900000c36030000410000000000320435000000440210003900000c370300004100001e7a0000013d0000000a0300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000b5c011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000a0570002900001d060000613d000000000801034f0000000a09000029000000008a08043c0000000009a90436000000000059004b00001d020000c13d000000000006004b00001d130000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f000000010020019000001e5c0000613d0000001f01400039000000600210018f0000000a01200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200040008c000000540000413d0000000a020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b000020400000c13d00000bf102000041000011fa0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001d350000c13d00001afc0000013d0000000b0300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000bd2011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000b0570002900001d530000613d000000000801034f0000000b09000029000000008a08043c0000000009a90436000000000059004b00001d4f0000c13d000000000006004b00001d600000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f000000010020019000001e680000613d0000001f01400039000000600210018f0000000b01200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200030008c000000540000413d0000000b020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00000a240000c13d00000c0702000041000011fa0000013d000000400100043d00000c2202000041000011fa0000013d0000004401100370000000000101043b000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f00000001002001900000000902000029000000540000613d000000000101043b000000000020043f000000200010043f00000064010000390000000101100367000000000101043b000a00000001001d000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d0000000a030000290000000b02300069000000000101043b000000000021041b00000044010000390000000101100367000000000101043b000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000802000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d00000001030003670000006402300370000000000202043b000000000101043b000000000401041a000000000024001a000018a50000413d0000000004240019000000000041041b0000004401300370000000000101043b000000400300043d00000020043000390000000000240435000000000013043500000b450030009c00000b45030080410000004001300210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000040300003900000be1040000410000000005000411000000090600002900000008070000292d102d060000040f0000000100200190000000540000613d00000bcf01000041000000000010044300000008010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000090200002900000a240000613d000000400400043d0000002401400039000000000021043500000be201000041000000000014043500000004014000390000000002000411000000000021043500000001010003670000004402100370000000000202043b000000440340003900000000002304350000006401100370000000000101043b0000008402400039000000a003000039000000000032043500000064024000390000000000120435000000a402400039000000800100043d0000000000120435000b00000004001d000000c402400039000000000001004b00001e100000613d00000000030000190000000004230019000000a005300039000000000505043300000000005404350000002003300039000000000013004b00001e090000413d0000000002210019000000000002043500000000020004140000000803000029000000040030008c0000229b0000c13d00000000050004150000000d0550008a00000005055002100000000004000031000000200040008c0000002004008039000022ce0000013d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000070010006c0000043f0000a13d000000400100043d00000c1a02000041000011fa0000013d00000005030000290000008401300039000000a002000039000000000021043500000064013000390000000902000029000000000021043500000044013000390000000a02000029000000000021043500000be20100004100000000001304350000000401300039000000000200041100000000002104350000002401300039000000000001043500000007010000290000000001010433000000a4023000390000000000120435000000c402300039000000000001004b000000060600002900001e4f0000613d000000000300001900000000042300190000000005630019000000000505043300000000005404350000002003300039000000000013004b00001e480000413d0000000002210019000000000002043500000000020004140000000b03000029000000040030008c00001ead0000c13d00000000050004150000000f0550008a00000005055002100000000004000031000000200040008c000000200400803900001ee00000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001e630000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001e6f0000c13d00001afc0000013d000000400100043d000000640210003900000c29030000410000000000320435000000440210003900000c2a03000041000000000032043500000024021000390000002a0300003900001b4f0000013d000000000010043f0000000f01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff00100190000020510000c13d0000000b01000029000000000010043f0000000101000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000000ff0010019000000bcc0000c13d0000195a0000013d0000001f0110003900000c5101100197000000c40110003900000b450010009c00000b45010080410000006001100210000000050300002900000b450030009c00000b45030080410000004003300210000000000131019f00000b450020009c00000b4502008041000000c002200210000000000112019f0000000b020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f0000002007400190000000050570002900001ecd0000613d000000000801034f0000000509000029000000008a08043c0000000009a90436000000000059004b00001ec90000c13d000000000006004b00001eda0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f00000000050004150000000e0550008a0000000505500210000000010020019000001fb80000613d0000001f01400039000000600110018f0000000502100029000000000012004b0000000001000039000000010100403900000b480020009c000000690000213d0000000100100190000000690000c13d0000000003020019000000400020043f000000200040008c000000540000413d0000000501000029000000000101043300000be300100198000000540000c13d0000000502500270000000000201001f00000be40110019700000be20010009c000021650000c13d000500000003001d000019150000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001f010000c13d00001afc0000013d000000c00200043d000000ff032002700000001b03300039000000200030043f00000bec02200197000000600020043f000000000010043f000000a00100043d000000400010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bed011001c700000001020000392d102d0b0000040f0000000109000039000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000200640019000000001046001bf00001f250000613d000000000701034f000000007807043c0000000009890436000000000049004b00001f210000c13d000000010220018f000000000005004b00001f330000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000000003001f0000000001020433000000600000043f0000000b02000029000000400020043f000000000003004b00001f3e0000c13d00000c3001000041000000000010043f00000bdb0100004100002d12000104300000001102000039000000000202041a000000000112013f00000b4a00100198000026180000c13d0000000a01000029000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000b00000001001d0000000a010000290000000801100270000000000010043f0000001801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d0000000a02000029000000ff0220018f000000000101043b000000000101041a000000000121022f000000010010019000001f8d0000c13d0000000b010000290000000301100039000000000101041a000800000001001d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000080010006c00001f8d0000a13d0000000a01000029000000000010043f0000000a01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d0000000b020000290000000402200039000000000202041a000000000101043b000000000101041a000000000021004b000026200000a13d0000000b010000290000000101100039000000000101041a000b0009001000be0000222d0000c13d000000400100043d00001d790000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001f9c0000c13d00001afc0000013d000000400100043d000000640210003900000c33030000410000000000320435000000440210003900000c340300004100000000003204350000002402100039000000280300003900001b4f0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b00001fb30000c13d00001afc0000013d000000040230008c000024090000413d000000000400043d00000be304400197000000000501043b00000be405500197000000000445019f000000000040043f00000be40440019700000b5b0040009c000024090000c13d000000440030008c000024090000413d000000040510037000000c51062001980000001f0720018f000000400400043d000000000164001900001fd10000613d000000000805034f0000000009040019000000008a08043c0000000009a90436000000000019004b00001fcd0000c13d000000000007004b00001fde0000613d000000000565034f0000000306700210000000000701043300000000076701cf000000000767022f000000000505043b0000010006600089000000000565022f00000000056501cf000000000575019f0000000000510435000000000504043300000b480050009c000024090000213d0000002401500039000000000031004b000024090000213d0000000001450019000000000301043300000b480030009c000024090000213d000000000224001900000000063100190000002006600039000000000026004b000024090000213d00000000023500190000003f0220003900000c51022001970000000004420019000000000024004b0000000002000039000000010200403900000b480040009c000000690000213d0000000100200190000000690000c13d0000000003040019000000400040043f000000000001004b000024090000613d00000b5b020000410000000004030019000b00000003001d000000000023043500000004023000390000002003000039000000000032043500000024024000392d1027770000040f0000000b02000029000000000121004900000b450010009c00000b450100804100000b450020009c00000b450200804100000060011002100000004002200210000000000121019f00002d12000104300000000b01000029000000000010043f0000000a01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b000000400300043d00000c110030009c000000690000213d0000002001300039000000400010043f000000000003043500000000010004110000000b020000292d102b540000040f0000000a010000290000000101100039000000000101041a0000001202000039000000000202041a000000400300043d00000020043000390000000000240435000000000013043500000b450030009c00000b45030080410000004001300210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000030300003900000c12040000410000204e0000013d0000000902000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b50011001c70000800d02000039000000030300003900000c0e040000410000000b05000029000000000600041100000a210000013d000000400100043d00000bf102000041000011fa0000013d000000c00200043d000000ff032002700000001b03300039000000200030043f00000bec02200197000000600020043f000000000010043f000000a00100043d000000400010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bed011001c700000001020000392d102d0b0000040f0000000109000039000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000200640019000000001046001bf000020730000613d000000000701034f000000007807043c0000000009890436000000000049004b0000206f0000c13d000000010220018f000000000005004b000020810000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000000003001f0000000001020433000000600000043f0000000902000029000000400020043f000000000003004b00001f3a0000613d0000001102000039000000000202041a000000000112013f00000b4a001001980000216c0000c13d0000000b01000029000000000010043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000900000001001d0000000501100039000000000101041a00000b4a011001970000000002000411000000000012004b000020a70000613d00000b5201000041000000000101041a00000b4a01100197000000000012004b000022ec0000c13d00000009010000290000000301100039000000000101041a000600000001001d000000000001004b000022640000c13d000000080000006b000022ef0000613d0000000a010000290000000b0200002900000009030000292d1029f70000040f000000000100001900002d110001042e000000000100041100050b4a0010019b00000000030000190000000602000029000020bd0000013d0000000103300039000000000023004b000021bc0000813d000000800100043d000000000031004b000026120000a13d0000000b0000006b000020ba0000613d0000000301000039000000000101041a00000b4a04100198000020ba0000613d000900000003001d00000bcf010000410000000000100443000a00000004001d0000000400400443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000000001004b000000540000613d000000400400043d00000044014000390000000802000029000000000021043500000024014000390000000b02000029000000000021043500000be001000041000000000014043500000004014000390000000502000029000000000021043500000000010004140000000a02000029000000040020008c000020f70000613d00000b450040009c00000b45030000410000000003044019000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000b5c011001c7000a00000004001d2d102d0b0000040f0000000a04000029000000600310027000000b450030019d00000001002001900000236e0000613d00000b480040009c000000690000213d000000400040043f00000006020000290000000903000029000020ba0000013d000000c00200043d000000ff032002700000001b03300039000000200030043f00000bec02200197000000600020043f000000000010043f000000a00100043d000000400010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bed011001c700000001020000392d102d0b0000040f0000000109000039000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000200640019000000001046001bf0000211c0000613d000000000701034f000000007807043c0000000009890436000000000049004b000021180000c13d000000010220018f000000000005004b0000212a0000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000000003001f0000000001020433000000600000043f0000000702000029000000400020043f000000000003004b00001f3a0000613d0000001102000039000000000202041a000000000112013f00000b4a00100198000021b90000c13d000000090000006b000026c70000c13d0000001201000039000000000201041a000700000002001d000000080020002a000018a50000413d00000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b00000006010000290000000101100039000000000101041a000000400400043d00000044034000390000000000130435000000000100041000000b4a011001970000002403400039000000000013043500000bf0010000410000000000140435000900000004001d00000004014000390000000a030000290000000000310435000000000100041400000b4a02200197000500000002001d000000040020008c0000237b0000c13d0000000004000031000000200040008c0000002004008039000023a50000013d00000b5b01000041000900000003001d000000000013043500000004013000392d102cb80000040f0000000902000029000024100000013d00000bee0100004100000009020000290000261a0000013d000000c00200043d000000ff032002700000001b03300039000000200030043f00000bec02200197000000600020043f000000000010043f000000a00100043d000000400010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bed011001c700000001020000392d102d0b0000040f0000000109000039000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000200640019000000001046001bf0000218e0000613d000000000701034f000000007807043c0000000009890436000000000049004b0000218a0000c13d000000010220018f000000000005004b0000219c0000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000000003001f0000000001020433000000600000043f0000000802000029000000400020043f000000000003004b00001f3a0000613d0000001102000039000000000202041a000000000112013f00000b4a001001980000222a0000c13d0000000a0000006b000022730000613d00000001010003670000000402100370000000000202043b0000002403100370000000000303043b000000e404100370000000000604043b0000010404100370000000000704043b0000012401100370000000000801043b00000000010004110000000b04000029000000090500002900000d5d0000013d00000bee0100004100000007020000290000261a0000013d000000800100043d000000000001004b00000bd70000613d000000000200001900000004010000290000000001010433000000000021004b000026120000a13d000600000002001d0000000501200210000000a002100039000000000302043300000003011000290000000001010433000900000001001d000a00000003001d000000000030043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000500090010007400001ce60000413d0000000a01000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000b02000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000502000029000000000021041b0000000a01000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000802000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a0000000903000029000000000032001a000018a50000413d0000000002320019000000000021041b00000006020000290000000102200039000000800100043d000000000012004b000021c00000413d00000bd70000013d00000bee0100004100000008020000290000261a0000013d0000000a01000029000000000010043f0000000b01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a00000009030000290000000002320019000000000021041b00000000010004110000000a020000292d1029550000040f000000400300043d00000024013000390000000b02000029000000000021043500000bd9010000410000000000130435000000000100041100000b4a01100197000800000003001d0000000402300039000000000012043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c000024590000c13d0000000004000031000000200040008c0000002004008039000024820000013d00000be6010000410000000000100443000000000100041400000b450010009c00000b4501008041000000c00110021000000be7011001c70000800b020000392d102d0b0000040f0000000100200190000026110000613d000000000101043b000000060010006c00001e2b0000213d000020ad0000013d0000001701000039000000000101041a0000001502000039000000000202041a00000008040000290000004403400039000000000023043500000b4a011001970000002402400039000000000012043500000bf0010000410000000000140435000000000100041100000b4a011001970000000402400039000000000012043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c000024190000c13d0000000003000031000000200030008c00000020040000390000000004034019000024420000013d0000001f0110003900000c5101100197000000c40110003900000b450010009c00000b450100804100000060011002100000000b0300002900000b450030009c00000b45030080410000004003300210000000000131019f00000b450020009c00000b4502008041000000c002200210000000000112019f00000008020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000b05700029000022bb0000613d000000000801034f0000000b09000029000000008a08043c0000000009a90436000000000059004b000022b70000c13d000000000006004b000022c80000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f00000000050004150000000c0550008a00000005055002100000000100200190000023d50000613d0000001f01400039000000600110018f0000000b02100029000000000012004b0000000001000039000000010100403900000b480020009c000000690000213d0000000100100190000000690000c13d0000000003020019000000400020043f000000200040008c000000540000413d0000000b01000029000000000101043300000be300100198000000540000c13d0000000502500270000000000201001f00000be40110019700000be20010009c00000a240000613d00000b5b01000041000a00000003001d000000000013043500000004013000392d102cb80000040f0000000a02000029000024100000013d000000400100043d00000bef02000041000011fa0000013d0000001201000039000000000201041a000600000002001d000000070020002a000018a50000413d00000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b00000009010000290000000101100039000000000101041a000000400400043d00000044034000390000000000130435000000000100041000000b4a011001970000002403400039000000000013043500000bf0010000410000000000140435000800000004001d00000004014000390000000a030000290000000000310435000000000100041400000b4a02200197000500000002001d000000040020008c000026230000c13d0000000004000031000000200040008c00000020040080390000264d0000013d0000001f0220003900000c51022001970000000a040000290000000001410049000000000121001900000b450010009c00000b4501008041000000600110021000000b450040009c00000b450200004100000000020440190000004002200210000000000121019f00000b450030009c00000b4503008041000000c002300210000000000112019f00000008020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000a057000290000233e0000613d000000000801034f0000000a09000029000000008a08043c0000000009a90436000000000059004b0000233a0000c13d000000000006004b0000234b0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000005000415000000120550008a00000005055002100000000100200190000023ef0000613d0000001f01400039000000600110018f0000000a02100029000000000012004b0000000001000039000000010100403900000b480020009c000000690000213d0000000100100190000000690000c13d0000000004020019000000400020043f000000200030008c000000540000413d0000000a01000029000000000101043300000be300100198000000540000c13d0000000502500270000000000201001f00000be40110019700000c390010009c00000a240000613d00000b5b01000041000b00000004001d000000000014043500000004014000392d102cb80000040f0000240f0000013d00000b45033001970000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000023760000c13d00001afc0000013d000000090200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000b5c011001c700000005020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000905700029000023950000613d000000000801034f0000000909000029000000008a08043c0000000009a90436000000000059004b000023910000c13d000000000006004b000023a20000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000024ac0000613d0000001f01400039000000600110018f0000000903100029000000000013004b00000000020000390000000102004039000400000003001d00000b480030009c000000690000213d0000000100200190000000690000c13d0000000402000029000000400020043f000000200040008c000000540000413d00000009020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b000026650000613d000000070300002900000008023000290000001703000039000000000303041a00000004050000290000004404500039000000000024043500000b4a023001970000002403500039000000000023043500000bf002000041000000000025043500000004025000390000000a03000029000000000032043500000000020004140000000503000029000000040030008c0000268c0000c13d000000040110002900000b480010009c000000690000213d000000400010043f000026be0000013d000000040230008c000024090000413d000000000400043d00000be304400197000000000501043b00000be405500197000000000445019f000000000040043f00000be40440019700000b5b0040009c000024090000c13d000000440030008c000024090000413d000000040510037000000c51062001980000001f0720018f000000400400043d000000000164001900001fd10000613d000000000805034f0000000009040019000000008a08043c0000000009a90436000000000019004b000023ea0000c13d00001fd10000013d000000040230008c000024090000413d000000000400043d00000be304400197000000000501043b00000be405500197000000000445019f000000000040043f000000440030008c000024090000413d00000be40440019700000b5b0040009c000024090000c13d000000040510037000000c51062001980000001f0720018f000000400400043d000000000164001900001fd10000613d000000000805034f0000000009040019000000008a08043c0000000009a90436000000000019004b000024040000c13d00001fd10000013d000000400200043d000b00000002001d00000b5b01000041000000000012043500000004012000392d102cc50000040f0000000b02000029000000000121004900000b450010009c00000b4501008041000000600110021000000b450020009c00000b45020080410000004002200210000000000121019f00002d1200010430000000080300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000b5c011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000805700029000024320000613d000000000801034f0000000809000029000000008a08043c0000000009a90436000000000059004b0000242e0000c13d000000000006004b0000243f0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000026680000613d0000001f01400039000000600210018f0000000801200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200030008c000000540000413d00000008020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d2c0000613d000021aa0000013d000000080300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000bd2011001c72d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000805700029000024720000613d000000000801034f0000000809000029000000008a08043c0000000009a90436000000000059004b0000246e0000c13d000000000006004b0000247f0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000026740000613d0000001f01400039000000600210018f0000000801200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200040008c000000540000413d00000008020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d790000613d00000020021000390000000b0300002900000000003204350000000902000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000030300003900000c2f040000410000000a05000029000000000600041100000a210000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000024b30000c13d00001afc0000013d000000080200002900000040022000390000000002020433000000ff032002700000001b03300039000000200030043f00000bec02200197000000600020043f000000000010043f00000007010000290000000001010433000000400010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bed011001c700000001020000392d102d0b0000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0540018f000000200640019000000001046001bf000024da0000613d000000000701034f0000000108000039000000007907043c0000000008980436000000000048004b000024d60000c13d000000010220018f000000000005004b000024e80000613d000000000161034f0000000305500210000000000604043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000140435000000000003001f0000000001020433000000600000043f0000000b02000029000000400020043f000000000003004b00001f3a0000613d0000001102000039000000000202041a000000000112013f00000b4a00100198000026180000c13d000000800100043d000000000001004b00000a240000613d000000000200041100050b4a0020019b000b00000000001d0000000a0200002900000000020204330000000b0020006c000026120000a13d0000000b020000290000000503200210000700000003001d00000009023000290000000002020433000000000002004b000025690000613d0000001701000039000000000101041a000000400400043d0000004403400039000000000023043500000b4a011001970000002402400039000000000012043500000bf0010000410000000000140435000800000004001d00000004014000390000000502000029000000000021043500000bd5010000410000000000100443000000000100041200000004001004430000002400000443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd6011001c700008005020000392d102d0b0000040f0000000100200190000026110000613d000000000201043b000000000100041400000b4a02200197000000040020008c0000252a0000c13d0000000004000031000000200040008c0000002004008039000025520000013d000000080300002900000b450030009c00000b4503008041000000400330021000000b450010009c00000b4501008041000000c001100210000000000131019f00000b5c011001c72d102d060000040f000000600310027000000b4503300197000000200030008c0000002004000039000000000403401900000020064001900000000805600029000025420000613d000000000701034f0000000808000029000000007907043c0000000008980436000000000058004b0000253e0000c13d0000001f074001900000254f0000613d000000000661034f0000000307700210000000000805043300000000087801cf000000000878022f000000000606043b0000010007700089000000000676022f00000000067601cf000000000686019f0000000000650435000000000003001f00000001002001900000274c0000613d0000001f01400039000000600210018f0000000801200029000000000021004b0000000002000039000000010200403900000b480010009c000000690000213d0000000100200190000000690000c13d000000400010043f000000200040008c000000540000413d00000008020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d2c0000613d000000800100043d0000000b0010006c000026120000a13d0000000701000029000000a001100039000700000001001d0000000001010433000000000010043f0000000c01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000201041a000000010220003a000018a50000613d000000000021041b000000800100043d0000000b0010006c000026120000a13d000000400100043d0000000002000411000000000002004b000027390000613d00000b4f0010009c000000690000213d000000070200002900000000030204330000004002100039000000400020043f0000002002100039000800000003001d000000000032043500000001020000390000000000210435000000400100043d00000b4f0010009c000000690000213d0000004002100039000000400020043f0000002002100039000000010300003900000000003204350000000000310435000000400100043d00000c110010009c000000690000213d0000002002100039000000400020043f00000000000104350000000801000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b000000000101041a000600000001001d000000000001004b000027420000613d0000000801000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000002000411000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000000540000613d000000000101043b0000000602000029000000010220008a000000000021041b000000400100043d0000002002100039000000010300003900000000003204350000000802000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000040300003900000be1040000410000000005000411000000000605001900000000070000192d102d060000040f0000000100200190000000540000613d000000400100043d00000c110010009c000000690000213d0000002002100039000000400020043f0000000000010435000000800100043d0000000b0010006c000026120000a13d00000007010000290000000005010433000000000100041400000b450010009c00000b4501008041000000c00110021000000b53011001c70000800d02000039000000030300003900000c150400004100000000060004112d102d060000040f0000000100200190000000540000613d0000000b02000029000b00010020003d000000800100043d0000000b0010006b000024fa0000413d00000a240000013d000000000001042f00000c3501000041000000000010043f0000003201000039000000040010043f00000bd80100004100002d120001043000000bee010000410000000b02000029000000000012043500000b450020009c00000b4502008041000000400120021000000bdf011001c700002d1200010430000000400100043d00000c2e02000041000011fa0000013d000000080200002900000b450020009c00000b4502008041000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000b5c011001c700000005020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000008057000290000263d0000613d000000000801034f0000000809000029000000008a08043c0000000009a90436000000000059004b000026390000c13d000000000006004b0000264a0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000026800000613d0000001f01400039000000600110018f0000000803100029000000000013004b00000000020000390000000102004039000400000003001d00000b480030009c000000690000213d0000000100200190000000690000c13d0000000402000029000000400020043f000000200040008c000000540000413d00000008020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b000026cd0000c13d00000bf10100004100000004020000290000261a0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000266f0000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b0000267b0000c13d00001afc0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000026870000c13d00001afc0000013d000000040100002900000b450010009c00000b4501008041000000400110021000000b450020009c00000b4502008041000000c002200210000000000112019f00000b5c011001c700000005020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000405700029000026a60000613d000000000801034f0000000409000029000000008a08043c0000000009a90436000000000059004b000026a20000c13d000000000006004b000026b30000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000100200190000026ee0000613d0000001f01400039000000600110018f000000040110002900000b480010009c000000690000213d000000400010043f000000200030008c000000540000413d00000004020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d2c0000613d00000000010004110000000b0200002900000006030000292d1029f70000040f000000000100001900002d110001042e000000060300002900000007023000290000001703000039000000000303041a00000004050000290000004404500039000000000024043500000b4a023001970000002403500039000000000023043500000bf002000041000000000025043500000004025000390000000a03000029000000000032043500000000020004140000000503000029000000040030008c000026fa0000c13d000000040110002900000b480010009c000000690000213d000000400010043f00000004020000290000000002020433000000000002004b0000000003000039000000010300c039000000000032004b000000540000c13d000000000002004b00001d2c0000613d000020af0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000026f50000c13d00001afc0000013d000000040100002900000b450010009c00000b4501008041000000400110021000000b450020009c00000b4502008041000000c002200210000000000112019f00000b5c011001c700000005020000292d102d060000040f000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f00000020074001900000000405700029000027140000613d000000000801034f0000000409000029000000008a08043c0000000009a90436000000000059004b000027100000c13d000000000006004b000027210000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f00000001002001900000272d0000613d0000001f01400039000000600110018f000000040110002900000b480010009c000000690000213d000000400010043f000000200030008c000026e40000813d000000540000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000027340000c13d00001afc0000013d000000640210003900000c18030000410000000000320435000000440210003900000c190300004100000000003204350000002402100039000000230300003900001b4f0000013d000000400100043d000000640210003900000c16030000410000000000320435000000440210003900000c170300004100000000003204350000002402100039000000240300003900001b4f0000013d0000001f0530018f00000b4706300198000000400200043d000000000462001900001afc0000613d000000000701034f0000000008020019000000007907043c0000000008980436000000000048004b000027530000c13d00001afc0000013d0000001f0220003900000c51022001970000000001120019000000000021004b0000000002000039000000010200403900000b480010009c000027640000213d0000000100200190000027640000c13d000000400010043f000000000001042d00000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d1200010430000000000003004b000027740000613d000000000400001900000000052400190000000006140019000000000606043300000000006504350000002004400039000000000034004b0000276d0000413d00000000012300190000000000010435000000000001042d00000000430104340000000001320436000000000003004b000027830000613d000000000200001900000000051200190000000006240019000000000606043300000000006504350000002002200039000000000032004b0000277c0000413d000000000213001900000000000204350000001f0230003900000c51022001970000000001210019000000000001042d00000020030000390000000004310436000000000302043300000000003404350000004001100039000000000003004b000027980000613d00000000040000190000002002200039000000000502043300000b4a0550019700000000015104360000000104400039000000000034004b000027910000413d000000000001042d000000000301001900000000040104330000000001420436000000000004004b000027a50000613d00000000020000190000002003300039000000000503043300000000015104360000000102200039000000000042004b0000279f0000413d000000000001042d00000044010000390000000101100367000000000101043b000000000001004b0000000002000039000000010200c039000000000021004b000027af0000c13d000000000001042d000000000100001900002d120001043000000024010000390000000101100367000000000101043b000000000001004b0000000002000039000000010200c039000000000021004b000027ba0000c13d000000000001042d000000000100001900002d1200010430000100000000000200010b4a0010019c000027dc0000613d000000000020043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000027da0000613d000000000101043b0000000102000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000027da0000613d000000000101043b000000000101041a000000000001042d000000000100001900002d1200010430000000400100043d000000640210003900000c29030000410000000000320435000000440210003900000c2a03000041000000000032043500000024021000390000002a03000039000000000032043500000b5b02000041000000000021043500000004021000390000002003000039000000000032043500000b450010009c00000b4501008041000000400110021000000b5f011001c700002d1200010430000000000301001900000000011200a9000000000003004b000027f70000613d00000000033100d9000000000023004b000027f80000c13d000000000001042d00000c3501000041000000000010043f0000001101000039000000040010043f00000bd80100004100002d1200010430000000000212004900000bec0020009c0000280a0000213d0000001f0020008c0000280a0000a13d0000000001010433000000000001004b0000000002000039000000010200c039000000000021004b0000280a0000c13d000000000001042d000000000100001900002d1200010430000400000000000200000b5202000041000000000202041a00000b4a032001970000000002000411000000000032004b000028a40000c13d00000bcf020000410000000000200443000200000001001d0000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f0000000100200190000028a70000613d0000000102000039000000020300002900000b4a05300197000000000101043b000000000001004b000200000005001d000028800000613d000000400b00043d00000c1c0100004100000000001b04350000000401b0003900000000000104350000000001000414000000040050008c000028370000c13d0000000001000415000000040110008a00000005011002100000000003000031000000200030008c00000020040000390000000004034019000028680000013d00000b4500b0009c00000b450200004100000000020b4019000000400220021000000b450010009c00000b4501008041000000c001100210000000000121019f00000bd8011001c7000000000205001900010000000b001d2d102d0b0000040f000000010b000029000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000000057b0019000028530000613d000000000801034f00000000090b0019000000008a08043c0000000009a90436000000000059004b0000284f0000c13d000000000006004b000028600000613d000000000171034f0000000306600210000000000705043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f0000000000150435000000000003001f0000000001000415000000030110008a0000000501100210000000010020019000000002050000290000000102000039000028800000613d0000001f02400039000000600420018f0000000002b40019000000000042004b0000000004000039000000010400403900000b480020009c000028af0000213d0000000100400190000028af0000c13d000000400020043f0000001f0030008c000028a20000a13d00000000020b0433000000000002004b0000000003000039000000010300c039000000000032004b000028a20000c13d0000000501100270000000000102001f000000000002004b00000000020000390000000102006039000000400100043d000000000005004b000028850000613d0000000100200190000028a80000c13d0000000302000039000000000302041a00000020021000390000000000520435000100000003001d00000b4a02300197000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d02000039000000010300003900000c1d040000412d102d060000040f00000002030000290000000100200190000028a20000613d000000010100002900000b5801100197000000000131019f0000000302000039000000000012041b000000000001042d000000000100001900002d1200010430000000400100043d00000bef02000041000028a90000013d000000000001042f00000c1e02000041000000000021043500000b450010009c00000b4501008041000000400110021000000bdf011001c700002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d12000104300006000000000002000500000002001d000600000001001d000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029430000613d000000400400043d00000c570040009c000029450000813d000000000101043b0000010002400039000000400020043f000000000201041a00000000022404360000000103100039000000000303041a00000000003204350000000202100039000000000202041a000000400340003900000000002304350000000302100039000000000202041a0000006003400039000400000003001d00000000002304350000000402100039000000000202041a0000008003400039000100000003001d00000000002304350000000502100039000000000202041a000000a003400039000200000003001d00000000002304350000000602100039000000000202041a000000c0034000390000000000230435000300000004001d000000e0024000390000000701100039000000000101041a00000000001204350000000601000029000000000010043f0000000701000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029430000613d000000000101043b000000050200002900000b4a02200197000600000002001d000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029430000613d000000000101043b000000000101041a000000ff001001900000293f0000613d00000004010000290000000002010433000000000002004b0000293f0000613d0000000301000029000000000301043300000002010000290000000001010433000000000031004b0000000001000019000029400000813d00000001010000290000000001010433000000000031004b000029410000a13d000400000001001d000500000003001d000000400100043d00000040031000390000000604000029000000000043043500000040030000390000000003310436000000000023043500000c210010009c000029450000213d0000006002100039000000400020043f00000b450030009c00000b45030080410000004002300210000000000101043300000b450010009c00000b45010080410000006001100210000000000121019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f0000000100200190000029430000613d000000000101043b00000004101000fa000000050010006c00000000010000390000000101004039000000000001042d0000000001000019000000000001042d0000000101000039000000000001042d000000000100001900002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d120001043000000b5201000041000000000101041a0000000002000411000000000012004b000029510000c13d000000000001042d00000c4b01000041000000000010043f00000bdb0100004100002d12000104300004000000000002000000400400043d00040b4a0010019c000029d00000613d00000c580040009c000029ca0000813d0000004001400039000000400010043f0000002001400039000000000021043500000001010000390000000000140435000000400400043d00000b4f0040009c000029ca0000213d0000004005400039000000400050043f000000200540003900000000003504350000000000140435000000400100043d00000c110010009c000029ca0000213d000300000003001d0000002003100039000000400030043f0000000000010435000200000002001d000000000020043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029c80000613d000000000101043b0000000402000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029c80000613d000000000101043b000000000101041a0001000300100074000029e30000413d0000000201000029000000000010043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029c80000613d000000000101043b0000000402000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f0000000100200190000029c80000613d000000000101043b0000000102000029000000000021041b000000400100043d0000002002100039000000030300002900000000003204350000000202000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d020000390000000403000039000000000500041100000be104000041000000040600002900000000070000192d102d060000040f0000000100200190000029c80000613d000000400100043d00000c110010009c000029ca0000213d0000002002100039000000400020043f0000000000010435000000000001042d000000000100001900002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d1200010430000000640140003900000c18030000410000000000310435000000440140003900000c1903000041000000000031043500000024014000390000002303000039000000000031043500000b5b01000041000000000014043500000004014000390000002003000039000000000031043500000b450040009c00000b4504008041000000400140021000000b5f011001c700002d1200010430000000400100043d000000640210003900000c16030000410000000000320435000000440210003900000c1703000041000000000032043500000024021000390000002403000039000000000032043500000b5b02000041000000000021043500000004021000390000002003000039000000000032043500000b450010009c00000b4501008041000000400110021000000b5f011001c700002d12000104300003000000000002000300000003001d000100000001001d000200000002001d000000000020043f0000000901000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002a680000613d000000000101043b000000000101041a000000ff0010019000002a700000c13d0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002a680000613d0000000303000029000000000203041a0000000603300039000000000303041a000000000101043b0000000401100039000000000101041a000000000113004b00002a220000a13d000000000012001a00002a6a0000413d000000000212001900000003030000290000000701300039000000000401041a0000000503300039000000000303041a00000c0303300198000000000500001900002a2c0000c13d000000000542004b00002a6a0000413d000000010240003a00002a6a0000613d000000000021041b00000000005301a000002a730000613d0000000201000029000000000010043f0000000a01000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002a680000613d000000000101043b000000000201041a000000010220003a00002a6a0000613d000000000021041b000000400300043d00000c590030009c00002a7b0000813d0000002001300039000000400010043f0000000000030435000000010100002900000002020000292d102b540000040f00000003010000290000000101100039000000000101041a0000001202000039000000000202041a000000400300043d00000020043000390000000000240435000000000013043500000b450030009c00000b45030080410000004001300210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f000000010200002900000b4a0620019700000bdd011001c70000800d02000039000000030300003900000c120400004100000002050000292d102d060000040f000000010020019000002a680000613d000000000001042d000000000100001900002d120001043000000c3501000041000000000010043f0000001101000039000000040010043f00000bd80100004100002d1200010430000000400100043d00000c220200004100002a750000013d000000400100043d00000c2302000041000000000021043500000b450010009c00000b4501008041000000400110021000000bdf011001c700002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d1200010430000c0000000000020000001009000039000000000a09041a000000010aa000390000000000a9041b000000400b00043d00000c5a00b0009c00002b4e0000813d0000012009b00039000000400090043f000000e009b00039000100000008001d000a00000009001d0000000000890435000000000004004b0000000004000039000000010400c039000000c008b00039000900000008001d00000000004804350000008004b00039000600000004001d00000000007404350000006004b00039000500000004001d00000000006404350000004004b00039000300000004001d00000000005404350000002004b00039000200000004001d000000000034043500000000002b043500000b4a01100197000000a002b00039000b00000001001d000400000002001d000000000012043500070000000b001d0000010001b00039000800000001001d00000000000104350000000000a0043f0000000801000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c70000801002000039000c00000003001d2d102d0b0000040f000000010020019000002b4c0000613d00000007020000290000000002020433000000000101043b000000000021041b000000020200002900000000020204330000000103100039000000000023041b000000030200002900000000020204330000000203100039000000000023041b000000050200002900000000020204330000000303100039000000000023041b000000060200002900000000020204330000000403100039000000000023041b0000000402000029000000000202043300000b4a022001970000000503100039000000000403041a00000c5b04400197000000000224019f00000009040000290000000004040433000000000004004b00000c5c040000410000000004006019000000000242019f000000000023041b0000000a0200002900000000020204330000000603100039000000000023041b000000070110003900000008020000290000000002020433000000000021041b0000001001000039000000000501041a000000400100043d0000000c02000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b50011001c70000800d02000039000000030300003900000c5d04000041000a00000005001d0000000b060000292d102d060000040f000000010020019000002b4c0000613d0000000c050000290000000104000029000000000004004b00002b490000613d000000400600043d00000c200060009c00002b4e0000213d0000001301000039000000000101041a0000001402000039000000000202041a0000010003600039000000400030043f000000e003600039000b00000003001d0000000000230435000000c002600039000900000002001d00000000001204350000002001600039000600000001001d00000000005104350000000000460435000000a001600039000800000001001d00000000000104350000008001600039000700000001001d00000000000104350000006001600039000500000001001d0000000000010435000c00000006001d0000004001600039000400000001001d00000000000104350000000a01000029000000000010043f0000000601000039000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002b4c0000613d0000000c020000290000000002020433000000000101043b000000000021041b000000060200002900000000020204330000000103100039000000000023041b000000040200002900000000020204330000000203100039000000000023041b000000050200002900000000020204330000000303100039000000000023041b000000070200002900000000020204330000000403100039000000000023041b000000080200002900000000020204330000000503100039000000000023041b000000090200002900000000020204330000000603100039000000000023041b00000007011000390000000b020000290000000002020433000000000021041b0000001001000039000000000101041a000000000001042d000000000100001900002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d12000104300006000000000002000000400500043d00000b4a0410019800002c2b0000613d000200000001001d000100000003001d000400000004001d00000c580050009c00002cb20000813d0000004003500039000000400030043f0000002003500039000000000023043500000001040000390000000000450435000000400100043d00000b4f0010009c00002cb20000213d0000004003100039000000400030043f000000200310003900000000004304350000000000410435000300000002001d000000000020043f000000200000043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002c290000613d000000000101043b0000000402000029000000000020043f000000200010043f000000000100041400000b450010009c00000b4501008041000000c00110021000000bdd011001c700008010020000392d102d0b0000040f000000010020019000002c290000613d000000000101043b000000000201041a000000010220003a00002c3e0000613d000000000021041b000000400100043d0000002002100039000000010300003900000000003204350000000302000029000000000021043500000b450010009c00000b45010080410000004001100210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000bdd011001c70000800d020000390000000403000039000000000500041100000be104000041000000000600001900000004070000292d102d060000040f000000010020019000002c290000613d00000bcf01000041000000000010044300000002010000290000000400100443000000000100041400000b450010009c00000b4501008041000000c00110021000000bd0011001c700008002020000392d102d0b0000040f000000010020019000002c440000613d000000000101043b000000000001004b00002c280000613d000000400b00043d0000008401b00039000000a00200003900000000002104350000006401b00039000000010200003900000000002104350000004401b000390000000302000029000000000021043500000be20100004100000000001b04350000000401b00039000000000200041100000000002104350000002401b000390000000000010435000000a403b00039000000010100002900000000210104340000000000130435000000c403b00039000000000001004b00002bd10000613d000000000400001900000000053400190000000006420019000000000606043300000000006504350000002004400039000000000014004b00002bca0000413d0000000002310019000000000002043500000000040004140000000402000029000000040020008c00002bdf0000c13d0000000005000415000000060550008a00000005055002100000000003000031000000200030008c0000002004000039000000000403401900002c130000013d0000001f0110003900000c5101100197000000c40110003900000b450010009c00000b4501008041000000600110021000000b4500b0009c00000b450300004100000000030b40190000004003300210000000000131019f00000b450040009c00000b4504008041000000c003400210000000000113019f00040000000b001d2d102d060000040f000000040b000029000000600310027000000b4503300197000000200030008c000000200400003900000000040340190000001f0640018f000000200740019000000000057b001900002c000000613d000000000801034f00000000090b0019000000008a08043c0000000009a90436000000000059004b00002bfc0000c13d000000000006004b00002c0d0000613d000000000771034f0000000306600210000000000805043300000000086801cf000000000868022f000000000707043b0000010006600089000000000767022f00000000066701cf000000000686019f0000000000650435000000000003001f0000000005000415000000050550008a0000000505500210000000010020019000002c4b0000613d0000001f01400039000000600110018f0000000004b10019000000000014004b0000000001000039000000010100403900000b480040009c00002cb20000213d000000010010019000002cb20000c13d000000400040043f000000200030008c00002c290000413d00000000010b043300000be30010019800002c290000c13d0000000502500270000000000201001f00000be40110019700000be20010009c00002c450000c13d000000000001042d000000000100001900002d1200010430000000640250003900000c13030000410000000000320435000000440250003900000c1403000041000000000032043500000024025000390000002103000039000000000032043500000b5b02000041000000000025043500000004025000390000002003000039000000000032043500000b450050009c00000b4505008041000000400150021000000b5f011001c700002d120001043000000c3501000041000000000010043f0000001101000039000000040010043f00000bd80100004100002d1200010430000000000001042f00000b5b0100004100000000001404350000000401400039000400000004001d2d102cb80000040f00002c860000013d000000040230008c00002c800000413d000000000400043d00000be304400197000000000501043b00000be405500197000000000445019f000000000040043f000000440030008c00002c800000413d00000be40440019700000b5b0040009c00002c800000c13d000000040510037000000c51062001980000001f0720018f000000400400043d000000000164001900002c640000613d000000000805034f0000000009040019000000008a08043c0000000009a90436000000000019004b00002c600000c13d000000000007004b00002c710000613d000000000565034f0000000306700210000000000701043300000000076701cf000000000767022f000000000505043b0000010006600089000000000565022f00000000056501cf000000000575019f0000000000510435000000000504043300000b480050009c00002c800000213d0000002401500039000000000031004b00002c800000213d0000000001450019000000000301043300000b480030009c00002c800000213d000000000224001900000000063100190000002006600039000000000026004b00002c900000a13d000000400200043d000400000002001d00000b5b01000041000000000012043500000004012000392d102cc50000040f0000000402000029000000000121004900000b450010009c00000b4501008041000000600110021000000b450020009c00000b45020080410000004002200210000000000121019f00002d120001043000000000023500190000003f0220003900000c51022001970000000004420019000000000024004b0000000002000039000000010200403900000b480040009c00002cb20000213d000000010020019000002cb20000c13d0000000003040019000000400040043f000000000001004b00002c800000613d00000b5b020000410000000004030019000400000003001d000000000023043500000004023000390000002003000039000000000032043500000024024000392d1027770000040f0000000402000029000000000121004900000b450010009c00000b450100804100000b450020009c00000b450200804100000060011002100000004002200210000000000121019f00002d120001043000000c3501000041000000000010043f0000004101000039000000040010043f00000bd80100004100002d1200010430000000600210003900000c5e030000410000000000320435000000400210003900000c5f030000410000000000320435000000200210003900000028030000390000000000320435000000200200003900000000002104350000008001100039000000000001042d000000600210003900000c60030000410000000000320435000000400210003900000c61030000410000000000320435000000200210003900000034030000390000000000320435000000200200003900000000002104350000008001100039000000000001042d000000000001042f00000b450010009c00000b4501008041000000400110021000000b450020009c00000b45020080410000006002200210000000000112019f000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000b53011001c700008010020000392d102d0b0000040f000000010020019000002ce60000613d000000000101043b000000000001042d000000000100001900002d120001043000000000050100190000000000200443000000050030008c00002cf60000413d000000040100003900000000020000190000000506200210000000000664001900000005066002700000000006060031000000000161043a0000000102200039000000000031004b00002cee0000413d00000b450030009c00000b45030080410000006001300210000000000200041400000b450020009c00000b4502008041000000c002200210000000000112019f00000c62011001c700000000020500192d102d0b0000040f000000010020019000002d050000613d000000000101043b000000000001042d000000000001042f00002d09002104210000000102000039000000000001042d0000000002000019000000000001042d00002d0e002104230000000102000039000000000001042d0000000002000019000000000001042d00002d100000043200002d110001042e00002d1200010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000000000000000000000000000000000000000000000000000001ffffffe000000000000000000000000000000000000000000000000000000000ffffffe0000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000ffffffffffffffffffffffffbfa87805ed57dc1f0d489ce33be4c4577d74ccde357eeeee058a32c55c44a532405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5acebfa87805ed57dc1f0d489ce33be4c4577d74ccde357eeeee058a32c55c44a531000000000000000000000000000000000000000000000000ffffffffffffffbf02000000000000000000000000000000000000200000000000000000000000008a8bae378cb731c5c40b632330c6836c2f916f48edb967699c86736f9a6a76efffffffffffffffffffffffffffffffffffffffffffffffffffffffff7487392702000000000000000000000000000000000000000000000000000000000000008be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e027cceb82823caa45ba60387709961a73050623da2232f8fd178296384aedbd77d833147d7dc355ba459fc788f669e58cfaf9dc25ddcd0702e87d69c7b512428927cceb82823caa45ba60387709961a73050623da2232f8fd178296384aedbd76ffffffffffffffffffffffff00000000000000000000000000000000000000000000000200000000000000000000000000000080000001000000000000000000455243323938313a20696e76616c69642072656365697665720000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000002073616c65507269636500000000000000000000000000000000000000000000455243323938313a20726f79616c7479206665652077696c6c20657863656564000000000000000000000000000000000000008400000000000000000000000000000000000000000000000000000000000000000000000000000000715018a500000000000000000000000000000000000000000000000000000000b2db919a00000000000000000000000000000000000000000000000000000000def25aca00000000000000000000000000000000000000000000000000000000f242432900000000000000000000000000000000000000000000000000000000fa914ed400000000000000000000000000000000000000000000000000000000fa914ed500000000000000000000000000000000000000000000000000000000fd762d9200000000000000000000000000000000000000000000000000000000fee81cf400000000000000000000000000000000000000000000000000000000f242432a00000000000000000000000000000000000000000000000000000000f2fde38b00000000000000000000000000000000000000000000000000000000e985e9c400000000000000000000000000000000000000000000000000000000e985e9c500000000000000000000000000000000000000000000000000000000eefdc1df00000000000000000000000000000000000000000000000000000000f04e283e00000000000000000000000000000000000000000000000000000000def25acb00000000000000000000000000000000000000000000000000000000e74b981b00000000000000000000000000000000000000000000000000000000d007af5b00000000000000000000000000000000000000000000000000000000d8d07ed900000000000000000000000000000000000000000000000000000000d8d07eda00000000000000000000000000000000000000000000000000000000ddca3f4300000000000000000000000000000000000000000000000000000000ddf0b00900000000000000000000000000000000000000000000000000000000d007af5c00000000000000000000000000000000000000000000000000000000d4f4ddaa00000000000000000000000000000000000000000000000000000000be537f4200000000000000000000000000000000000000000000000000000000be537f4300000000000000000000000000000000000000000000000000000000c0bc62f700000000000000000000000000000000000000000000000000000000c6af66b900000000000000000000000000000000000000000000000000000000b2db919b00000000000000000000000000000000000000000000000000000000b4b5b48f000000000000000000000000000000000000000000000000000000008da5cb5a000000000000000000000000000000000000000000000000000000009d645a4300000000000000000000000000000000000000000000000000000000a22cb46400000000000000000000000000000000000000000000000000000000a22cb46500000000000000000000000000000000000000000000000000000000a9fc664e00000000000000000000000000000000000000000000000000000000ae796ab3000000000000000000000000000000000000000000000000000000009d645a44000000000000000000000000000000000000000000000000000000009d7f4ebf0000000000000000000000000000000000000000000000000000000095be539f0000000000000000000000000000000000000000000000000000000095be53a00000000000000000000000000000000000000000000000000000000095d89b410000000000000000000000000000000000000000000000000000000096949420000000000000000000000000000000000000000000000000000000008da5cb5b0000000000000000000000000000000000000000000000000000000091eb290e000000000000000000000000000000000000000000000000000000007f631e460000000000000000000000000000000000000000000000000000000083e096cd0000000000000000000000000000000000000000000000000000000083e096ce0000000000000000000000000000000000000000000000000000000089a30271000000000000000000000000000000000000000000000000000000008d1d9520000000000000000000000000000000000000000000000000000000007f631e4700000000000000000000000000000000000000000000000000000000809a619e000000000000000000000000000000000000000000000000000000007ecebdff000000000000000000000000000000000000000000000000000000007ecebe00000000000000000000000000000000000000000000000000000000007f58b4bf00000000000000000000000000000000000000000000000000000000715018a6000000000000000000000000000000000000000000000000000000007d5c3ff1000000000000000000000000000000000000000000000000000000002e1a7d4c000000000000000000000000000000000000000000000000000000005beaa0480000000000000000000000000000000000000000000000000000000069fe0e2c000000000000000000000000000000000000000000000000000000006c19e782000000000000000000000000000000000000000000000000000000006c19e783000000000000000000000000000000000000000000000000000000006c3b8699000000000000000000000000000000000000000000000000000000006e85a0d90000000000000000000000000000000000000000000000000000000069fe0e2d000000000000000000000000000000000000000000000000000000006c0360eb00000000000000000000000000000000000000000000000000000000612107da00000000000000000000000000000000000000000000000000000000612107db00000000000000000000000000000000000000000000000000000000613471620000000000000000000000000000000000000000000000000000000062914849000000000000000000000000000000000000000000000000000000005beaa049000000000000000000000000000000000000000000000000000000005d4c1d460000000000000000000000000000000000000000000000000000000042d96dd6000000000000000000000000000000000000000000000000000000004e1273f3000000000000000000000000000000000000000000000000000000004e1273f40000000000000000000000000000000000000000000000000000000054d1f13d000000000000000000000000000000000000000000000000000000005b7633d00000000000000000000000000000000000000000000000000000000042d96dd700000000000000000000000000000000000000000000000000000000495c8bf9000000000000000000000000000000000000000000000000000000002eb2c2d5000000000000000000000000000000000000000000000000000000002eb2c2d6000000000000000000000000000000000000000000000000000000002fc47b24000000000000000000000000000000000000000000000000000000002e1a7d4d000000000000000000000000000000000000000000000000000000002e8da829000000000000000000000000000000000000000000000000000000000e89341b000000000000000000000000000000000000000000000000000000001b25b076000000000000000000000000000000000000000000000000000000001ed74927000000000000000000000000000000000000000000000000000000001ed749280000000000000000000000000000000000000000000000000000000025692962000000000000000000000000000000000000000000000000000000002a55205a000000000000000000000000000000000000000000000000000000001b25b077000000000000000000000000000000000000000000000000000000001c33b32800000000000000000000000000000000000000000000000000000000134954b700000000000000000000000000000000000000000000000000000000134954b8000000000000000000000000000000000000000000000000000000001647795e000000000000000000000000000000000000000000000000000000001b24e9df000000000000000000000000000000000000000000000000000000000e89341c000000000000000000000000000000000000000000000000000000000fa7b7b30000000000000000000000000000000000000000000000000000000002fe53040000000000000000000000000000000000000000000000000000000006fdde020000000000000000000000000000000000000000000000000000000006fdde0300000000000000000000000000000000000000000000000000000000098144d4000000000000000000000000000000000000000000000000000000000dce83c70000000000000000000000000000000000000000000000000000000002fe53050000000000000000000000000000000000000000000000000000000004845e3e000000000000000000000000000000000000000000000000000000000146354500000000000000000000000000000000000000000000000000000000014635460000000000000000000000000000000000000000000000000000000001ffc9a700000000000000000000000000000000000000000000000000000000009a9b7b0000000000000000000000000000000000000000000000000000000000fdd58e00000000000000000000000000000000000000000000000000000000389a75e100000000000000000000000000000000000000200000008000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffff1806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b830200000200000000000000000000000000000024000000000000000000000000da0194c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000440000000000000000000000002304aa02000000000000000000000000000000000000000000000000000000008d74431400000000000000000000000000000000000000000000000000000000310ab089e4439a4c15d089f94afb7896ff553aecb10793d0ab882de59d99a32e020000020000000000000000000000000000004400000000000000000000000070a08231000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000a9059cbb00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000007448fbae00000000000000000000000000000000000000040000001c0000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f02000000000000000000000000000000000000400000000000000000000000008ee600cb000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000285fb8c800000000000000000000000000000000000000000000000000000000c3d58168c5ae7397731d063d5bbf3d657854427343f4c083240f7aacaa2d0f62f23a6e610000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000200000000c0000000000000000796b89b91644bc98cd93958e4c9038275d622183e25ac5af08cc6b5d955391320200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000000000006f5e8818000000000000000000000000000000000000000000000000ffffffffffffff3f0000000019457468657265756d205369676e6564204d6573736167653a0a3332020000000000000000000000000000000000003c0000000400000000000000007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000000000800000000000000000000000008baa579f000000000000000000000000000000000000000000000000000000002d0a346e0000000000000000000000000000000000000000000000000000000023b872dd00000000000000000000000000000000000000000000000000000000f499da2000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000fffffffffffffe9f0000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000010000000080000000000000000048b6e6df0000000000000000000000000000000000000000000000000000000042cbb15ccdc3cad6266b0e7a08c0454b23bf29dc2df74b6f3c209e9336465bd180b41246c05cbb406f874e82aa2faf7db11bba9792fe09929e56ef1eee2c2da3c212ef7d00000000000000000000000000000000000000000000000000000000feea0d9900000000000000000000000000000000000000000000000000000000bd8c6ccc00000000000000000000000000000000000000000000000000000000b955455200000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000080000000000000000017e94a6c000000000000000000000000000000000000000000000000000000007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe02f34bba70000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000040000008000000000000000000000000000000000000000000000000000000024000000e0000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000ff000000000000000000000000000000000000000000000000000000000000000000000000000001200000008000000000000000007820c10a00000000000000000000000000000000000000000000000000000000321aa27e9c5c4ca98453ba7da9a1af4aa7bfed3bab5098e02fee58ce3cafe6b7cbe4e8c30000000000000000000000000000000000000000000000000000000017307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c31455243313135353a2073657474696e6720617070726f76616c2073746174757320666f722073656c66000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000009445f53000000000000000000000000000000000000000000000000000000000f91d7f9b00000000000000000000000000000000000000000000000000000000ad3d6587006c45fb2f92060267e172188795374f8f5bdf4187d50c571cce287fc19c461c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000fffffffffffffedf000000000000000000000000000000000000000000000000ffffffffffffffdf81fd5f457056a8b19e623dc52551a385bfcafd0914d3942446ecab71d19b123b7300000000000000000000000000000000000000000000000000000000000000455243313135353a206d696e7420746f20746865207a65726f20616464726573ecb0813fff72f72d5c424535fe69f97316a856e5cd5830226c189a4a8662e2c1616e636500000000000000000000000000000000000000000000000000000000455243313135353a206275726e20616d6f756e7420657863656564732062616c6573730000000000000000000000000000000000000000000000000000000000455243313135353a206275726e2066726f6d20746865207a65726f20616464720bd8a3eb000000000000000000000000000000000000000000000000000000000000000000000000000000000000721c310194ccfc01e523fc93c9cccfa2a0ac01ffc9a700000000000000000000000000000000000000000000000000000000cc5dc080ff977b3c3a211fa63ab74f90f658f5ba9d3236e92c8f59570f442aac32483afb0000000000000000000000000000000000000000000000000000000039ffc7ba00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000fffffffffffffeff000000000000000000000000000000000000000000000000ffffffffffffff9f48c460c800000000000000000000000000000000000000000000000000000000d76288d70000000000000000000000000000000000000000000000000000000038685a6b00000000000000000000000000000000000000000000000000000000fa7b8eab7da67f412cc9575ed43464468f9bfbae89d1675917346ca6d8fe3c92206d69736d617463680000000000000000000000000000000000000000000000455243313135353a206163636f756e747320616e6420696473206c656e67746800000000000000000000000000000000000000000000003fffffffffffffffe0616c6964206f776e657200000000000000000000000000000000000000000000455243313135353a2061646472657373207a65726f206973206e6f74206120763fe5df9900000000000000000000000000000000000000000000000000000000756688fe00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff5fbf7c9c2f00000000000000000000000000000000000000000000000000000000ed7318a9455ec161085222a6e508a46debace6235bba0202c768d3840f809c85000000000000000000000000000000000000000000000000000000008baa579f6572206f7220617070726f766564000000000000000000000000000000000000455243313135353a2063616c6c6572206973206e6f7420746f6b656e206f776e6d69736d61746368000000000000000000000000000000000000000000000000455243313135353a2069647320616e6420616d6f756e7473206c656e677468204e487b710000000000000000000000000000000000000000000000000000000072207472616e7366657200000000000000000000000000000000000000000000455243313135353a20696e73756666696369656e742062616c616e636520666f4a39dc06d4c0dbc64b70af90fd698a233a518aa5d07e595d983b8c0526c8f7fbbc197c81000000000000000000000000000000000000000000000000000000006472657373000000000000000000000000000000000000000000000000000000455243313135353a207472616e7366657220746f20746865207a65726f206164d72dde5e0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000440000008000000000000000000000000000000000000000000000000000000040000000000000000000000000fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffd5d00dbf36a107da19e49527a7176a1babf963b4b0ff8cde35ee35d6cd8f1f9ac7e1de6d0175500000000000000000000000000000000000000000000000000000000f342c3d80000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff30000000000000000000000000000000000000000000000000000000000000002f000000000000000000000000000000000000000000000000000000000000002b8acba10000000000000000000000000000000000000000000000000000000075e52f4f000000000000000000000000000000000000000000000000000000004b092bc80000000000000000000000000000000000000000000000000000000044594c49000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000000000000082b429002a552059ffffffffffffffffffffffffffffffffffffffffffffffffffffffff2a55205a00000000000000000000000000000000000000000000000000000000d9b67a260000000000000000000000000000000000000000000000000000000086455d28000000000000000000000000000000000000000000000000000000000e89341c00000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffafffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffeff000000000000000000000000000000000000000000000000ffffffffffffff00000000000000000000000000000000000000000000000000ffffffffffffffc0000000000000000000000000000000000000000000000000ffffffffffffffe0000000000000000000000000000000000000000000000000fffffffffffffee0ffffffffffffffffffffff0000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000d8e6d657f706eb987a687ae78b967b4b1cf806551ebeb3a85471d9b8cf6c04a06420746f6b656e73000000000000000000000000000000000000000000000000455243313135353a204552433131353552656365697665722072656a65637465526563656976657220696d706c656d656e746572000000000000000000000000455243313135353a207472616e7366657220746f206e6f6e2d45524331313535020000020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000009f7c100f70662a0265ba602b28ba858122801c33365a6115d3a9be44d9e446c6

Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)

000000000000000000000000000000000000000000000000000000000000012000000000000000000000000075bf8f439d205b8ee0de9d3622342eb05985859b0000000000000000000000002f2a13462f6d4af64954ee84641d265932849b640000000000000000000000002f2a13462f6d4af64954ee84641d265932849b6400000000000000000000000000000000000000000000000000000000000001f400000000000000000000000000000000000000000000000000000000001e8480000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004c4b4000000000000000000000000000000000000000000000000000000000001e8480000000000000000000000000000000000000000000000000000000000000002068747470733a2f2f7777772e64796c692e696f2f6170692f6d65746164617461

-----Decoded View---------------
Arg [0] : _baseURI (string): https://www.dyli.io/api/metadata
Arg [1] : usdc_ (address): 0x75Bf8F439d205B8eE0DE9d3622342eb05985859B
Arg [2] : signerAddress_ (address): 0x2f2A13462f6d4aF64954ee84641D265932849b64
Arg [3] : feeRecipient_ (address): 0x2f2A13462f6d4aF64954ee84641D265932849b64
Arg [4] : royaltyFeeNumerator_ (uint96): 500
Arg [5] : initialQueueFee (uint256): 2000000
Arg [6] : initialLoseQueueRefund (uint256): 0
Arg [7] : initialCreateFee (uint256): 5000000
Arg [8] : initialFee (uint256): 2000000

-----Encoded View---------------
11 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000120
Arg [1] : 00000000000000000000000075bf8f439d205b8ee0de9d3622342eb05985859b
Arg [2] : 0000000000000000000000002f2a13462f6d4af64954ee84641d265932849b64
Arg [3] : 0000000000000000000000002f2a13462f6d4af64954ee84641d265932849b64
Arg [4] : 00000000000000000000000000000000000000000000000000000000000001f4
Arg [5] : 00000000000000000000000000000000000000000000000000000000001e8480
Arg [6] : 0000000000000000000000000000000000000000000000000000000000000000
Arg [7] : 00000000000000000000000000000000000000000000000000000000004c4b40
Arg [8] : 00000000000000000000000000000000000000000000000000000000001e8480
Arg [9] : 0000000000000000000000000000000000000000000000000000000000000020
Arg [10] : 68747470733a2f2f7777772e64796c692e696f2f6170692f6d65746164617461


[ 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.